This commit was generated by cvs2svn to compensate for changes in r11022,
[freeside.git] / httemplate / view / cust_main / packages / status.html
1 <TD CLASS="inv" BGCOLOR="<% $bgcolor %>">
2   <TABLE CLASS="inv" BORDER=0 CELLSPACING=0 CELLPADDING=0 WIDTH="100%">
3
4 %#this should use cust_pkg->status and cust_pkg->statuscolor eventually
5
6 % if ( $cust_pkg->order_date ) {
7     <% pkg_status_row($cust_pkg, 'Ordered', 'order_date', %opt ) %>
8 % }
9
10 % if ( $cust_pkg->get('cancel') ) { #status: cancelled
11 %   my $cpr = $cust_pkg->last_cust_pkg_reason('cancel');
12
13     <% pkg_status_row($cust_pkg, 'Cancelled', 'cancel', 'color'=>'FF0000', %opt ) %>
14
15     <% pkg_status_row_colspan( $cust_pkg,
16          ( $cpr ? $cpr->reasontext. ' by '. $cpr->otaker : '' ), '',
17          'align'=>'right', 'color'=>'ff0000', 'size'=>'-2', 'colspan'=>$colspan,
18          %opt
19        )
20     %>
21
22 %   unless ( $cust_pkg->get('setup') ) { 
23
24         <% pkg_status_row_colspan( $cust_pkg, 'Never billed', '', 'colspan'=>$colspan, %opt, ) %>
25
26 %   } else { 
27
28        <% pkg_status_row( $cust_pkg, 'Setup', 'setup', %opt ) %>
29        <% pkg_status_row_changed( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
30        <% pkg_status_row_if( $cust_pkg, $last_bill_or_renewed, 'last_bill', %opt, curuser=>$curuser ) %>
31        <% pkg_status_row_if( $cust_pkg, 'Suspended', 'susp', %opt, curuser=>$curuser ) %>
32
33 %   } 
34 %
35 % } else { 
36 %
37 %   if ( $cust_pkg->get('susp') ) { #status: suspended
38 %     my $cpr = $cust_pkg->last_cust_pkg_reason('susp');
39
40     <% pkg_status_row( $cust_pkg, 'Suspended', 'susp', 'color'=>'FF9900', %opt ) %>
41
42     <% pkg_status_row_colspan( $cust_pkg,
43          ( $cpr ? $cpr->reasontext. ' by '. $cpr->otaker : '' ), '',
44          'align'=>'right', 'color'=>'FF9900', 'size'=>'-2', 'colspan'=>$colspan,
45          %opt,
46        )
47     %>
48
49     <% pkg_status_row_noauto( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
50
51     <% pkg_status_row_discount( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
52
53 %   unless ( $cust_pkg->get('setup') ) { 
54       <% pkg_status_row_colspan( $cust_pkg, 'Never billed', '', 'colspan'=>$colspan, %opt ) %>
55 %   } else { 
56       <% pkg_status_row($cust_pkg, 'Setup', 'setup', %opt ) %>
57 %   } 
58
59     <% pkg_status_row_changed( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
60     <% pkg_status_row_if( $cust_pkg, $last_bill_or_renewed, 'last_bill', %opt, curuser=>$curuser ) %>
61 %   if ( $part_pkg->option('suspend_bill', 1) ) {
62       <% pkg_status_row_if( $cust_pkg, 'Next&nbsp;bill', 'bill', %opt, curuser=>$curuser ) %>
63 %   }
64     <% pkg_status_row_if( $cust_pkg, 'Expires', 'expire', %opt, curuser=>$curuser ) %>
65     <% pkg_status_row_if( $cust_pkg, 'Contract ends', 'contract_end', %opt ) %>
66
67     <TR>
68       <TD COLSPAN=<%$colspan%>>
69         <FONT SIZE=-1>
70 %         if ( $curuser->access_right('Unsuspend customer package') ) { 
71             (&nbsp;<% pkg_unsuspend_link($cust_pkg) %>&nbsp;)
72 %         } 
73 %         if ( $curuser->access_right('Cancel customer package immediately') ) {
74             (&nbsp;<% pkg_cancel_link($cust_pkg) %>&nbsp;)
75 %         } 
76         </FONT>
77       </TD>
78     </TR>
79
80 %   } else { #status: active
81 %
82 %     unless ( $cust_pkg->get('setup') ) { #not setup
83 %
84 %       unless ( $part_pkg->freq ) {
85
86           <% pkg_status_row_colspan( $cust_pkg, 'Not&nbsp;yet&nbsp;billed&nbsp;(one-time&nbsp;charge)', '', 'colspan'=>$colspan, %opt ) %>
87
88           <% pkg_status_row_noauto( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
89
90           <% pkg_status_row_discount( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
91
92           <% pkg_status_row_if(
93                $cust_pkg,
94                ( $part_pkg->freq ? 'Start billing' : 'Bill on' ),
95                'start_date',
96                %opt
97              )
98           %>
99
100           <TR>
101             <TD COLSPAN=<%$colspan%>>
102               <FONT SIZE=-1>
103 %               if ( $curuser->access_right('Cancel customer package immediately') ) { 
104                   (&nbsp;<% pkg_cancel_link($cust_pkg) %>&nbsp;)
105 %               } 
106               </FONT>
107             </TD>
108           </TR>
109
110 %       } else { 
111
112           <% pkg_status_row_colspan($cust_pkg, "Not&nbsp;yet&nbsp;billed&nbsp;($billed_or_prepaid&nbsp;". myfreq($part_pkg). ')', '', 'colspan'=>$colspan, %opt ) %>
113
114           <% pkg_status_row_noauto( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
115
116           <% pkg_status_row_discount( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
117
118           <% pkg_status_row_if($cust_pkg, 'Start billing', 'start_date', %opt) %>
119
120 %       } 
121 %
122 %     } else { #setup
123 %
124 %       unless ( $part_pkg->freq ) { 
125
126           <% pkg_status_row_colspan($cust_pkg, 'One-time&nbsp;charge', '', 'colspan'=>$colspan, %opt ) %>
127
128           <% pkg_status_row($cust_pkg, 'Billed', 'setup', %opt) %>
129
130           <% pkg_status_row_noauto( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
131
132           <% pkg_status_row_discount( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
133
134 %       } else { 
135 %
136 %         if (scalar($cust_pkg->overlimit)) {
137
138             <% pkg_status_row_colspan( $cust_pkg,
139                  'Overlimit',
140                  $billed_or_prepaid. '&nbsp;'. myfreq($part_pkg),
141                  'color'=>'FFD000', 'colspan'=>$colspan,
142                  %opt
143                )
144             %>
145
146 %         } else {
147             <% pkg_status_row_colspan( $cust_pkg,
148                  'Active',
149                  $billed_or_prepaid. '&nbsp;'. myfreq($part_pkg),
150                  'color'=>'00CC00', 'colspan'=>$colspan,
151                  %opt
152                )
153             %>
154 %         } 
155
156           <% pkg_status_row_noauto( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
157
158           <% pkg_status_row_discount( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
159
160           <% pkg_status_row($cust_pkg, 'Setup', 'setup', %opt) %>
161
162 %       } 
163 %
164 %     } 
165 %
166 %     if ( $opt{'cust_pkg-show_autosuspend'} ) {
167 %       my $autosuspend = pkg_autosuspend_time( $cust_pkg );
168 %       $cust_pkg->set('autosuspend', $autosuspend) if $autosuspend;
169 %     }
170
171       <% pkg_status_row_changed( $cust_pkg, %opt, 'colspan'=>$colspan ) %>
172       <% pkg_status_row_if( $cust_pkg, $last_bill_or_renewed, 'last_bill', %opt, curuser=>$curuser ) %>
173       <% pkg_status_row_if( $cust_pkg, $next_bill_or_prepaid_until, 'bill', %opt, curuser=>$curuser ) %>
174       <% pkg_status_row_if($cust_pkg, 'Will automatically suspend by', 'autosuspend', %opt) %>
175       <% pkg_status_row_if( $cust_pkg, 'Will suspend on', 'adjourn', %opt, curuser=>$curuser ) %>
176       <% pkg_status_row_if( $cust_pkg, 'Expires', 'expire', %opt, curuser=>$curuser ) %>
177       <% pkg_status_row_if( $cust_pkg, 'Contract ends', 'contract_end', %opt ) %>
178
179 %     if ( $part_pkg->freq ) { 
180
181         <TR>
182           <TD COLSPAN=<%$colspan%>>
183             <FONT SIZE=-1>
184 %             if ( $curuser->access_right('Suspend customer package') ) { 
185                 (&nbsp;<% pkg_suspend_link($cust_pkg) %>&nbsp;)
186 %             } 
187 %             if ( $curuser->access_right('Suspend customer package later') ) { 
188                 (&nbsp;<% pkg_adjourn_link($cust_pkg) %>&nbsp;)
189 %             } 
190 %             if ( $curuser->access_right('Delay suspension events') ) { 
191                 (&nbsp;<% pkg_delay_link($cust_pkg) %>&nbsp;)
192 %             } 
193 %             if ( $curuser->access_right('Cancel customer package immediately') ) { 
194                 (&nbsp;<% pkg_cancel_link($cust_pkg) %>&nbsp;)
195 %             } 
196 %             if ( $curuser->access_right('Cancel customer package later') ) { 
197                 (&nbsp;<% pkg_expire_link($cust_pkg) %>&nbsp;)
198 %             } 
199
200             <FONT>
201           </TD>
202         </TR>
203 %     }
204 %
205 %   } 
206 % } 
207
208   </TABLE>
209 </TD>
210 <%init>
211
212 my %opt = @_;
213
214 my $bgcolor  = $opt{'bgcolor'};
215 my $cust_pkg = $opt{'cust_pkg'};
216 my $part_pkg = $opt{'part_pkg'};
217 my $curuser  = $FS::CurrentUser::CurrentUser;
218 my $colspan  = $opt{'cust_pkg-display_times'} ? 8 : 4;
219 my $width    = $opt{'cust_pkg-display_times'} ? '38%' : '56%';
220
221 #false laziness w/edit/REAL_cust_pkg.cgi
222 my( $billed_or_prepaid, $last_bill_or_renewed, $next_bill_or_prepaid_until );
223 unless ( $part_pkg->is_prepaid ) {
224   $billed_or_prepaid = 'billed';
225   $last_bill_or_renewed = 'Last&nbsp;bill';
226   $next_bill_or_prepaid_until = 'Next&nbsp;bill';
227 } else {
228   $billed_or_prepaid = 'prepaid';
229   $last_bill_or_renewed = 'Renewed';
230   $next_bill_or_prepaid_until = 'Prepaid&nbsp;until';
231 }
232
233 #subroutines
234
235 sub myfreq {
236   my $part_pkg = shift;
237   my $freq = $part_pkg->freq_pretty;
238   $freq =~ s/ /&nbsp;/g;
239   $freq;
240 }
241
242 #false laziness w/package.html
243 sub pkg_link {
244   my($action, $label, $cust_pkg) = @_;
245   return '' unless $cust_pkg;
246   qq!<a href="$p$action.cgi?!. $cust_pkg->pkgnum. qq!">$label</a>!;
247 }
248
249 sub pkg_status_row {
250   my( $cust_pkg, $title, $field, %opt ) = @_;
251
252   my $color = $opt{'color'};
253
254   my $html = qq(<TR><TD WIDTH="<%$width%>" ALIGN="right">);
255   $html   .= qq(<FONT COLOR="#$color"><B>) if length($color);
256   $html   .= qq($title&nbsp;);
257   $html   .= qq(</B></FONT>) if length($color);
258
259   if ( $opt{'pkg_balances'} && ! $cust_pkg->{_printed_balance}++ ) { #kludge
260     $html .= ' (Balance:&nbsp;<B>'. $opt{'money_char'}.
261              $cust_pkg->cust_main->balance_pkgnum($cust_pkg->pkgnum).
262              '</B>)';
263   }
264
265   $html   .= qq(</TD>);
266   $html   .= pkg_datestr($cust_pkg, $field, %opt). '</TR>';
267
268   $html;
269 }
270
271 sub pkg_status_row_if {
272   my( $cust_pkg, $title, $field, %opt ) = @_;
273   
274   $title = '<FONT SIZE=-1>(&nbsp;'. pkg_unadjourn_link($cust_pkg). '&nbsp;)&nbsp;</FONT>'. $title
275     if ( $field eq 'adjourn' &&
276          $opt{curuser}->access_right('Suspend customer package later')
277        );
278
279   $title = '<FONT SIZE=-1>(&nbsp;'. pkg_unexpire_link($cust_pkg). '&nbsp;)&nbsp;</FONT>'. $title
280     if ( $field eq 'expire' &&
281          $opt{curuser}->access_right('Cancel customer package later')
282        );
283
284   $cust_pkg->get($field) ? pkg_status_row($cust_pkg, $title, $field, %opt) : '';
285 }
286
287 sub pkg_status_row_changed {
288   my( $cust_pkg, %opt ) = @_;
289
290   return '' unless $cust_pkg->change_date;
291
292   my $html =
293     pkg_status_row( $cust_pkg, 'Package&nbsp;changed', 'change_date', %opt );
294
295   my $old = $cust_pkg->old_cust_pkg;
296   if ( $old ) {
297     my $part_pkg = $old->part_pkg;
298     my $label = 'Changed from '. $cust_pkg->change_pkgnum. ': '.
299                 $part_pkg->pkg_comment(nopartpkg => 1);
300     $html .= pkg_status_row_colspan( $cust_pkg, $label, '',
301                                      'size'    => '-1',
302                                      'align'   => 'right',
303                                      'colspan' => $opt{'colspan'},
304                                      #%opt,
305                                    );
306   }
307
308   $html;
309 }
310
311 sub pkg_status_row_noauto {
312   my( $cust_pkg, %opt ) = @_;
313   my $part_pkg = $opt{'part_pkg'};
314   return '' unless $cust_pkg->no_auto || $part_pkg->no_auto;
315
316   #inefficient, should be passed in
317   my $cust_main = $cust_pkg->cust_main;
318
319   return '' unless $cust_main->payby =~ /^(CARD|CHEK)$/;
320   my $what = lc(FS::payby->shortname($cust_main->payby));
321
322   pkg_status_row_colspan( $cust_pkg, "No automatic $what charge", '',
323                           'colspan' => $opt{'colspan'},
324                           #%opt,
325                         );
326 }
327
328 sub pkg_status_row_discount {
329   my( $cust_pkg, %opt ) = @_;
330
331   my $html;
332
333   foreach my $cust_pkg_discount ( $cust_pkg->cust_pkg_discount_active ) {
334
335     my $discount = $cust_pkg_discount->discount;
336
337     my $label = '<B>Discount</B>: '. $discount->description;
338     if ( $discount->months ) {
339       my $remaining = $discount->months - $cust_pkg_discount->months_used;
340       $remaining = sprintf('%.2f', $remaining) if $remaining =~ /\./;
341       $label .= " ($remaining months remaining)"
342     }
343
344     $label .= ' <FONT SIZE="-1">('.
345                 '<A HREF="../misc/delete-cust_pkg_discount.html?'.
346                   $cust_pkg_discount->pkgdiscountnum.
347                 '">remove&nbsp;discount</A>)</FONT>';
348
349     $html .= pkg_status_row_colspan( $cust_pkg, $label, '',
350                                      'colspan' => $opt{'colspan'},
351                                      #%opt,
352                                    );
353
354   }
355
356   $html;
357 }
358
359 sub pkg_status_row_colspan {
360   my($cust_pkg, $title, $addl, %opt) = @_;
361
362   my $colspan  = $opt{'colspan'};
363
364   my $align = $opt{'align'} ? 'ALIGN="'. $opt{'align'}.'"' : '';
365   my $color = $opt{'color'} ? 'COLOR="#'.$opt{'color'}.'"' : '';
366   my $size  = $opt{'size'}  ? 'SIZE="'.  $opt{'size'}. '"' : '';
367
368   my $html = qq(<TR><TD COLSPAN=$colspan $align>);
369   $html   .= qq(<FONT $color $size>) if length($color) || $size;
370   $html   .= qq(<B>) if $color && !$size;
371   $html   .= $title;
372   $html   .= qq(</B>) if $color && !$size;
373   $html   .= qq(</FONT>) if length($color) || $size;
374   $html   .= ",&nbsp;$addl" if length($addl);
375
376   if ( $opt{'pkg-balances'} && ! $cust_pkg->{_printed_balance}++ ) { #kludge
377     $html .= ' (Balance:&nbsp;<B>'. $opt{'money_char'}.
378              $cust_pkg->cust_main->balance_pkgnum($cust_pkg->pkgnum).
379              '</B>)';
380   }
381
382   $html   .= qq(</TD></TR>);
383
384   $html;
385
386 }
387
388 sub pkg_datestr {
389   my($cust_pkg, $field, %opt) = @_ or return '';
390   return '&nbsp;' unless $cust_pkg->get($field);
391   my $format = '<TD align="left"><B>%b</B></TD>'.
392                '<TD align="right"><B>&nbsp;%o,</B></TD>'.
393                '<TD align="right"><B>&nbsp;%Y</B></TD>';
394   #$format .= '&nbsp;<FONT SIZE=-3>%l:%M:%S%P&nbsp;%z</FONT>'
395   $format .= '<TD ALIGN="right"><B>&nbsp;%l</TD>'.
396              '<TD ALIGN="center"><B>:</B></TD>'.
397              '<TD ALIGN="left"><B>%M</B></TD>'.
398              '<TD ALIGN="left"><B>&nbsp;%P</B></TD>'
399     if $opt{'cust_pkg-display_times'};
400   my $strip = time2str($format, $cust_pkg->get($field) );
401   $strip =~ s/ (\d)/$1/g;
402   $strip;
403 }
404
405 sub pkg_suspend_link {
406   include( '/elements/popup_link-cust_pkg.html',
407              'action'      => $p. 'misc/cancel_pkg.html?method=suspend',
408              'label'       => 'Suspend&nbsp;now',
409              'actionlabel' => 'Suspend',
410              'color'       => '#FF9900',
411              'cust_pkg'    => shift,
412          )
413 }
414
415 sub pkg_adjourn_link {
416   include( '/elements/popup_link-cust_pkg.html',
417              'action'      => $p. 'misc/cancel_pkg.html?method=adjourn',
418              'label'       => 'Suspend&nbsp;later',
419              'actionlabel' => 'Adjourn',
420              'color'       => '#CC6600',
421              'cust_pkg'    => shift,
422          )
423 }
424
425 sub pkg_delay_link  {
426   include( '/elements/popup_link-cust_pkg.html',
427              'action'      => $p. 'misc/delay_susp_pkg.html',
428              'label'       => 'Delay&nbsp;suspend',
429              'actionlabel' => 'Delay suspend for',
430              'cust_pkg'    => shift,
431          )
432 }
433
434 sub pkg_unsuspend_link { pkg_link('misc/unsusp_pkg',    'Unsuspend', @_ ); }
435 sub pkg_unadjourn_link { pkg_link('misc/unadjourn_pkg', 'Abort',     @_ ); }
436 sub pkg_unexpire_link  { pkg_link('misc/unexpire_pkg',  'Abort',     @_ ); }
437
438 sub pkg_cancel_link {
439   include( '/elements/popup_link-cust_pkg.html',
440              'action'      => $p. 'misc/cancel_pkg.html?method=cancel',
441              'label'       => 'Cancel&nbsp;now',
442              'actionlabel' => 'Cancel',
443              'color'       => '#ff0000',
444              'cust_pkg'    => shift,
445          )
446 }
447
448 sub pkg_expire_link {
449   include( '/elements/popup_link-cust_pkg.html',
450              'action'      => $p. 'misc/cancel_pkg.html?method=expire',
451              'label'       => 'Cancel&nbsp;later',
452              'actionlabel' => 'Expire', #"Cancel package $num later"
453              'color'       => '#CC0000',
454              'cust_pkg'    => shift,
455          )
456 }
457
458 sub svc_recharge_link {
459   include( '/elements/popup_link-cust_svc.html',
460              'action'      => $p. 'misc/recharge_svc.html',
461              'label'       => 'Recharge',
462              'actionlabel' => 'Recharge',
463              'color'       => '#333399',
464              'cust_svc'    => shift,
465          )
466 }
467
468 sub pkg_autosuspend_time {
469   my $cust_pkg = shift or return '';
470   my $days = 7;
471   my $time = time;
472   my $pending_suspend = 0;
473   #this seems to be extremely inefficient...  and is slowing down all customer
474   #views
475   while ( $days > 0 &&
476           scalar(
477             grep { $_->part_event->action eq 'suspend' }
478             @{$cust_pkg->cust_main->due_cust_event( time => $time + 86400*$days,
479                                                     testonly => 1,
480                                                   ) }
481           )
482         )
483   {
484     $pending_suspend = 1;
485     $days--;
486   }
487
488   $pending_suspend ? time + ($days + 1) * 86400 : '';
489
490 }
491
492 </%init>