# Type: Input # Category: Task # Description: Finishes current task # Author: Andriy Lesyuk use utf8; new Orangutan::Context( response => [ '^End time is ([0-9]{1,2}(?:[:-][0-9]{2})? *(?:(?:a\.?|p\.?)m\.?)?)!*\.*$', '^(?:Set|change) end time to ([0-9]{1,2}(?:[:-][0-9]{2})? *(?:(?:a\.?|p\.?)m\.?)?)!*\.*$', '^Done(?: (?:at|in|on) ([0-9]{1,2}(?:[:-][0-9]{2})? *(?:(?:a\.?|p\.?)m\.?)?))?!*\.*$', '^I did it(?: (?:at|in|on) ([0-9]{1,2}(?:[:-][0-9]{2})? *(?:(?:a\.?|p\.?)m\.?)?))?!*\.*$', '^(?:I(?: have|\'ve)? )?(?:finished|completed)(?: (?:it|(?:the )?(?:current )?task))?'. '(?: (?:at|in|on) ([0-9]{1,2}(?:[:-][0-9]{2})? *(?:(?:a\.?|p\.?)m\.?)?))?!*\.*$', '^(?:(?:The )?task(?: has been)? )?completed(?: (?:at|in|on) ([0-9]{1,2}(?:[:-][0-9]{2})? *(?:(?:a\.?|p\.?)m\.?)?))?!*\.*$', '^(?:(?:Just|please) )?(?:stop|finish|end|abort|close)(?: (?:it|(?:(?:my|the|this) )?(?:current )?task))?'. '(?: (?:at|in|on|using) ([0-9]{1,2}(?:[:-][0-9]{2})? *(?:(?:a\.?|p\.?)m\.?)?))?!*\.*$' ], handler => sub { my ($context, $user, $item, $time) = @_; my $task = $user->GetTask; if ($task) { if ($time) { my $date = new Orangutan::Date($time, $task->GetStart->Date); if ($date) { if ($date->Date < $task->GetStart->Date) { $user->SendMessage([ "You think a task can be started after it was finished?..", "End time cannot be earlier than task's start time!", sprintf("Task's start time is %02d:%02d... I can't use %02d:%02d as an end time!", $task->GetStart->GetTime, $date->GetTime) ]); return; } elsif ($date->Date == $task->GetStart->Date) { $user->SendMessage([ "Hey! You specified the same time (as when task started).", "Task cannot end at the same moment it starts... Add at least a minute!", "Wow! I understand that some tasks can take a second... But I can't add this to Redmine! :(" ]); return; } else { $task->SetEnd($date); } } else { $user->SendMessage([ 'End time for the task is invalid!', "Seems you have made a mistake in time...", "I can't accept this... Please give correct time!" ]); return; } } else { my $elapsed = $task->GetStart->Elapsed; if ($elapsed > 0) { if ($task->GetStart->Elapsed >= 86400) { $user->SendMessage([ 'Cannot stop it using current time!', "Can't stop this task using current time!", "I can't save it using current time as end time!" ]); if (!$user->GetResponse('LongTask')) { $user->AddRequestResponse($main::config->Context('LongTask')); } return; } else { $task->SetEnd; } } else { if ($elapsed == 0) { $user->SendMessage([ 'Wow!.. You are fast!..', 'Hey! Less than a minute! Cool!', 'You are really fast...' ]); } $task->SetEnd(new Orangutan::Date($task->GetStart->Date + 60)); } } my $message = Orangutan::Context::Random('Ok.', 'Got it.', 'Cool.'); # Fill in missing data if (!defined($task->GetActivity('id'))) { my $default_activity = $main::query->GetDefaultActivity($task->GetProject('id')); if (defined($default_activity)) { $task->SetActivity( id => $default_activity->{'id'}, name => $default_activity->{'name'} ); $message .= ' '.Orangutan::Context::Random('Submitting', 'Posting', 'Saving').': "'; $message .= sprintf("%02d:%02d - %02d:%02d ", $task->GetStart->GetTime, $task->GetEnd->GetTime); my $duration = $task->GetDuration; $message .= sprintf("(%d:%02d): ", int($duration / 3600), int(($duration % 3600) / 60)); $message .= $task->GetName.' '; if ($task->GetIssue) { $message .= sprintf("on #%d ", $task->GetIssue); } $message .= 'for '.$task->GetProject; $message .= '".'; my $format = Orangutan::Context::Random( "I don't have any information regarding activity so using the default one which is \"%s\"...", "You did not tell me the activity name so I'm using \"%s\"..." ); $message .= ' '.sprintf($format, $first_activity->{'name'}); } else { $user->SendMessage([ 'You need to do something with activity for this task...', 'You must set activity to be able to stop the task!' ]); return; } } else { $message .= ' '.Orangutan::Context::Random( 'Putting into Redmine', 'Saving task in Redmine', 'Adding to your time log in Redmine' ).': '; $message .= '"'.sprintf("%02d:%02d - %02d:%02d ", $task->GetStart->GetTime, $task->GetEnd->GetTime); my $duration = $task->GetDuration; $message .= sprintf("(%d:%02d): ", int($duration / 3600), int(($duration % 3600) / 60)); $message .= $task->GetName.' '; if ($task->GetIssue) { $message .= sprintf("on #%d ", $task->GetIssue); } $message .= 'for '.$task->GetProject.' ('.$task->GetActivity.')"'; $message .= '.'; } # Get free periods my @periods = $user->GetFreePeriods($task->GetStart, $task->GetEnd); if ((scalar @periods == 1) && ($task->GetDuration > 0) && ($periods[0][0] == $task->GetStart->Date) && ($periods[0][1] == $task->GetEnd->Date)) { if ($task->GetStart->WorkDayStart->Date != $task->GetEnd->WorkDayStart->Date) { my $copy = new Orangutan::Task($task); $task->SetEnd($task->GetStart->WorkDayEnd); $user->SubmitTask; $user->SetTask($copy); $copy->SetStart($copy->GetEnd->WorkDayStart); $user->SubmitTask; } else { $user->SubmitTask; } $user->FireEvent('task', 'end', $task); $user->SendMessage($message); } else { $user->SendMessage([ 'Looks like you added some tasks to Redmine while working on this one. Now they conflict...', "Can't add this task because it conflicts with some other tasks in Redmine...", "Time of this task conflicts with the time of another task in Redmine...", "Geeze... You should not be adding tasks into Redmine directly while using me!.. :(" ]); if ((scalar @periods > 0) && ($task->GetDuration > 0)) { $user->SendMessage([ "You can fix this by (one of):", "We can solve this by doing one of the following:", "Now you should do one of the following:" ]); $user->SendMessage(" o Remove time entry you added in Redmine (use Redmine)."); $user->SendMessage(" o Remove your current task here."); if ($periods[$#periods][1] == $task->GetEnd->Date) { my $format = Orangutan::Context::Random( ' o Set start time of the task to %02d:%02d.', ' o Change start time to %02d:%02d.' ); my $startdate = new Orangutan::Date($periods[$#periods][0]); $user->SendMessage(sprintf($format, $startdate->GetTime)); } if ($periods[0][0] == $task->GetStart->Date) { my $format = Orangutan::Context::Random( ' o Change end time of the task to %02d:%02d.', ' o Set end time of the task to %02d:%02d.', " o Adjust task's end time to %02d:%02d." ); my $enddate = new Orangutan::Date($periods[0][1]); $user->SendMessage(sprintf($format, $enddate->GetTime)); } foreach my $period (@periods) { if (($period->[0] != $task->GetStart->Date) && ($period->[1] != $task->GetEnd->Date)) { my $format = Orangutan::Context::Random( ' o Change start time to %02d:%02d and end time to %02d:%02d.', ' o Set start time to %02d:%02d and end time to %02d.' ); my $startdate = new Orangutan::Date($periods->[0]); my $enddate = new Orangutan::Date($periods->[1]); $user->SendMessage(sprintf($format, $startdate->GetTime, $enddate->GetTime)); } } } } } else { $user->SendMessage([ 'You did what? I have no information regarding what you were working on...', 'Oh... You should tell me when you start working on a task! Sorry...', 'You did not tell me that you were working on something...' ]); } }, filter => sub { my ($context, $user, $message) = @_; if (${$message} =~ s/^вщту$/done/i) { $user->SendMessage([ 'I guess you forgot to switch language...', 'Looks like you wanted to say "done"...', 'Assuming you meant "done"...' ]); return 1; } else { return 0; } }, help => { title => 'How can I stop the current task?', question => '^(?:How )?(?:(?:can|do) I |to )(?:stop|close|finish|end|abort) (?:(?:the|a) )?(?:current )?task\?*!*\.*$', answer => "When you complete your task do not forget to stop it. ". "When stopping the task you can optionally specify the end time.\n". "Sample requests:\n". " o The task has been completed at 19:00\n". " o I have finished it at 13:00\n". " o Stop at 12:00\n". " o I did it!\n". " o Done\n". "Be sure that the end time specified is later than the start time of the current task! ". "It can be a future time.", weight => 640 }, weight => 90 ); # kate: syntax perl