ticketing escalation, part 1, RT#8254
[freeside.git] / FS / FS / Cron / rt_tasks.pm
1 package FS::Cron::rt_tasks;
2
3 use strict;
4 use vars qw( @ISA @EXPORT_OK $DEBUG );
5 use Exporter;
6 use FS::UID qw( dbh driver_name );
7 use FS::Record qw(qsearch qsearchs);
8 use FS::TicketSystem;
9 use FS::Conf;
10
11 use Date::Parse qw(str2time);
12
13 @ISA = qw( Exporter );
14 @EXPORT_OK = qw ( rt_escalate );
15 $DEBUG = 0;
16
17 my %void = ();
18
19 sub rt_escalate {
20   my %opt = @_;
21   # RT_External installations should have their own cron scripts for this
22   my $system = $FS::TicketSystem::system;
23   return if $system ne 'RT_Internal';
24
25   my $conf = new FS::Conf;
26   return if !$conf->exists('ticket_system-escalation');
27
28   FS::TicketSystem->init;
29   $DEBUG = 1 if $opt{'v'};
30   RT::Config->Set( LogToScreen => 'debug' ) if $DEBUG;
31   
32   #we're at now now (and later).
33   my $time = $opt{'d'} ? str2time($opt{'d'}) : $^T;
34   $time += $opt{'y'} * 86400 if $opt{'y'};
35   my $error = '';
36
37   my $session = FS::TicketSystem->session();
38   my $CurrentUser = $session->{'CurrentUser'}
39     or die "Failed to create RT session";
40  
41   # load some modules that aren't handled in FS::TicketSystem 
42   foreach (qw(
43     Search::ActiveTicketsInQueue 
44     Action::EscalatePriority
45     )) {
46     eval "use RT::$_";
47     die $@ if $@;
48   }
49
50   # adapted from rt-crontool
51   # Mechanics:
52   # We're using EscalatePriority, so search in all queues that have a 
53   # priority range defined. Select all active tickets in those queues and
54   # LinearEscalate them.
55
56   # to make some actions work without complaining
57   %void = map { $_ => "RT::$_"->new($CurrentUser) }
58     (qw(Scrip ScripAction));
59
60   # Most of this stuff is common to any condition -> action processing 
61   # we might want to do, but escalation is the only one we do now.
62   my $queues = RT::Queues->new($CurrentUser);
63   $queues->UnLimit;
64   while (my $queue = $queues->Next) {
65     if ( $queue->InitialPriority == $queue->FinalPriority ) {
66       warn "Queue '".$queue->Name."' (skipped)\n" if $DEBUG;
67       next;
68     }
69     warn "Queue '".$queue->Name."'\n" if $DEBUG;
70     my $tickets = RT::Tickets->new($CurrentUser);
71     my $search = RT::Search::ActiveTicketsInQueue->new(
72       TicketsObj  => $tickets,
73       Argument    => $queue->Name,
74       CurrentUser => $CurrentUser,
75     );
76     $search->Prepare;
77     while (my $ticket = $tickets->Next) {
78       warn 'Ticket #'.$ticket->Id()."\n" if $DEBUG;
79       # We don't need transaction stuff from rt-crontool here
80       action($ticket, 'EscalatePriority', "CurrentTime:$time");
81     }
82   }
83   return;
84 }
85
86 sub action {
87   my $ticket = shift;
88   my $CurrentUser = $ticket->CurrentUser;
89
90   my $action = shift;
91   my $argument = shift;
92
93   $action = "RT::Action::$action";
94   my $action_obj = $action->new(
95     TicketObj     => $ticket,
96     Argument      => $argument,
97     Scrip         => $void{'Scrip'},
98     ScripAction   => $void{'ScripAction'},
99     CurrentUser   => $CurrentUser,
100   );
101   return unless $action_obj->Prepare;
102   warn "Action prepared: $action\n" if $DEBUG;
103   $action_obj->Commit;
104   warn "Action committed: $action\n" if $DEBUG;
105   return;
106 }
107
108 1;