async def check_answers(self, context, answers): """ Run the checks on their answers to make sure their values are valid :param answers: :return: """ now = datetime.today() start = datetime.strptime( lib.find(answers, 'stage', 1)['answer'] + ' ' + lib.find(answers, 'stage', 2)['answer'], '%d-%m-%Y %H:%M') end = datetime.strptime( lib.find(answers, 'stage', 3)['answer'] + ' ' + lib.find(answers, 'stage', 4)['answer'], '%d-%m-%Y %H:%M') # Check that the end date is later than the start date. if start > end: await context.send( context.message.author.mention + ', ' + lib.get_string('event:err:dates', context.guild.id)) return False # Check that dates are in the future if start < now or end < now: await context.send( context.message.author.mention + ', ' + lib.get_string('event:err:dates:past', context.guild.id)) return False return True
async def run_stage_five(self, context, answers): """ Ask the stage 5 question - Confirmation :param context: :return: """ prompt = lib.get_string('event:schedule:question:5', context.guild.id).format( lib.find(answers, 'stage', 1)['answer'] + ', ' + lib.find(answers, 'stage', 2)['answer'], lib.find(answers, 'stage', 3)['answer'] + ', ' + lib.find(answers, 'stage', 4)['answer'] ) argument = {'prompt': prompt, 'check': lambda resp: resp in ('yes', 'y', 'no', 'n'), 'error': 'err:yesorno'} response = await self.prompt(context, argument, True, self.PROMPT_TIMEOUT) if not response: return False response = response.content.lower() # If there response was one of the exit commands, then stop. if response in ('exit', 'quit', 'cancel'): return False # We got a response, now do we need to check the type or do any extra content checks? if not await self.check_content(argument, response, context): # If it didn't meet the check conditions, try again. return await self.run_stage_five(context) # If they said no, tell them to start it again. if response in ('no', 'n'): await context.send(lib.get_string('event:schedule:restart', context.guild.id)) return False return response in ('yes', 'y')
def apply(self, branch_name, apply_listener=ApplyListener()): """Applies this split over the commits to the named branch and returns the tip commit. An ApplyListener callback can be passed to track progress of the split; otherwise, a no-op ApplyListener is used. If there are no (new) commits to split None is returned.""" commits = list(self.commits()) if not commits: return None commit_count = len(commits) apply_listener.on_start(commit_count) try: if not commits: return None parent = None branch = lib.find(self._repo.branches, lambda branch: branch.name == branch_name, lambda: self._repo.create_head(branch_name)) for commit in commits: index_path = '/tmp/%s.index' % branch_name if os.path.exists(index_path): os.remove(index_path) index = git.IndexFile(self._repo, index_path) for item in self._subtrees(commit): if self._is_included(item): index.add([item]) else: index.add( item.traverse( lambda item, depth: self._is_included(item))) synthetic_tree = index.write_tree() parents = [] if parent is None else [parent] parent = self._copy_commit(commit, synthetic_tree, parents) apply_listener.on_commit(commit, parent) branch.commit = parent return parent finally: apply_listener.on_finish()
def apply(self, branch_name, apply_listener = ApplyListener()): """Applies this split over the commits to the named branch and returns the tip commit. An ApplyListener callback can be passed to track progress of the split; otherwise, a no-op ApplyListener is used. If there are no (new) commits to split None is returned.""" commits = list(self.commits()) if not commits: return None commit_count = len(commits) apply_listener.on_start(commit_count) try: if not commits: return None parent = None branch = lib.find(self._repo.branches, lambda branch: branch.name == branch_name, lambda: self._repo.create_head(branch_name)) for commit in commits: index_path = '/tmp/%s.index' % branch_name if os.path.exists(index_path): os.remove(index_path) index = git.IndexFile(self._repo, index_path) for item in self._subtrees(commit): if self._is_included(item): index.add([item]) else: index.add(item.traverse(lambda item, depth: self._is_included(item))) synthetic_tree = index.write_tree() parents = [] if parent is None else [ parent ] parent = self._copy_commit(commit, synthetic_tree, parents) apply_listener.on_commit(commit, parent) branch.commit = parent return parent finally: apply_listener.on_finish()
async def run_schedule(self, context): """ Schedule the event to start and end at a specific datetime :param context: :return: """ user = User(context.message.author.id, context.guild.id, context) event = Event.get_by_guild(user.get_guild()) # Do they have the permissions to rename an event? self.check_permissions(context) # Make sure the event is running if event is None: return await context.send( user.get_mention() + ', ' + lib.get_string('event:err:noexists', user.get_guild())) # Make sure the event is running if event.is_running(): return await context.send( user.get_mention() + ', ' + lib.get_string('event:err:alreadyrunning', user.get_guild())) # Do they have a timezone set in their user settings? user_timezone = user.get_setting('timezone') if user_timezone is None: return await context.send( user.get_mention() + ', ' + lib.get_string('event:err:timezonenotset', user.get_guild())) timezone = pytz.timezone(user_timezone) time = datetime.now(timezone).strftime('%H:%M:%S') offset = datetime.now(timezone).strftime('%z') # Print the pre-schedule information to check their timezone is correct. await context.send(user.get_mention() + ', ' + lib.get_string('event:preschedule', user.get_guild( )).format(user_timezone, time, offset)) # We now have various stages to go through, so we loop through the stages, ask the question and store the user input as the answer. answers = [] # Stage 1 - Start date answer = await self.run_stage_one(context) if not answer: return answers.append({'stage': 1, 'answer': answer}) # Stage 2 - Start time answer = await self.run_stage_two(context) if not answer: return answers.append({'stage': 2, 'answer': answer}) # Stage 3 - End date answer = await self.run_stage_three(context) if not answer: return answers.append({'stage': 3, 'answer': answer}) # Stage 4 - End time answer = await self.run_stage_four(context) if not answer: return answers.append({'stage': 4, 'answer': answer}) # Stage 5 - Confirmation answer = await self.run_stage_five(context, answers) if not answer: return answers.append({'stage': 5, 'answer': answer}) # Now run the checks to make sure the end date is later than start date, etc... check = await self.check_answers(context, answers) if not check: return # Now convert those start and end times to UTC timestamps start = datetime.strptime( lib.find(answers, 'stage', 1)['answer'] + ' ' + lib.find(answers, 'stage', 2)['answer'], '%d-%m-%Y %H:%M') end = datetime.strptime( lib.find(answers, 'stage', 3)['answer'] + ' ' + lib.find(answers, 'stage', 4)['answer'], '%d-%m-%Y %H:%M') adjusted_start = int(timezone.localize(start).timestamp()) adjusted_end = int(timezone.localize(end).timestamp()) # Schedule the event with those timestamps event.set_startdate(adjusted_start) event.set_enddate(adjusted_end) event.set_channel(context.message.channel.id) event.save() # Remove any tasks we already had saved for this event. Task.cancel('event', event.get_id()) # Schedule the tasks to run at those times. Task.schedule(Event.TASKS['start'], event.get_start_time(), 'event', event.get_id()) Task.schedule(Event.TASKS['end'], event.get_end_time(), 'event', event.get_id()) return await context.send( user.get_mention() + ', ' + lib.get_string('event:scheduled', user.get_guild()).format( event.get_title(), start, end))