RT 82999 - fixed issue where payment receipt only sent when one email present.
[freeside.git] / FS / FS / cust_pay.pm
index 04aac4e..3e368f6 100644 (file)
@@ -227,6 +227,8 @@ sub insert {
   local $FS::UID::AutoCommit = 0;
   my $dbh = dbh;
 
+  my $conf = new FS::Conf;
+
   my $cust_bill;
   if ( $self->invnum ) {
     $cust_bill = qsearchs('cust_bill', { 'invnum' => $self->invnum } )
@@ -548,7 +550,8 @@ otherwise returns false.
 
 sub replace {
   my $self = shift;
-  return "Can't modify closed payment" if $self->closed =~ /^Y/i;
+  return "Can't modify closed payment"
+    if $self->closed =~ /^Y/i && !$FS::payinfo_Mixin::allow_closed_replace;
   $self->SUPER::replace(@_);
 }
 
@@ -651,6 +654,8 @@ sub send_receipt {
 
   return '' unless $conf->config_bool('payment_receipt', $cust_main->agentnum);
 
+  return '' if ($conf->config_bool('allow_payment_receipt_noemail', $cust_main->agentnum) && $cust_main->paymentreceipt_noemail);
+
   my @invoicing_list = $cust_main->invoicing_list_emailonly;
   return '' unless @invoicing_list;
 
@@ -663,11 +668,84 @@ sub send_receipt {
        || ! $cust_bill
      )
   {
-    my $msgnum = $conf->config('payment_receipt_msgnum', $cust_main->agentnum);
+
+    $error = $self->send_message_receipt(
+        'cust_main'      => $cust_main,
+        'cust_bill'      => $opt->{cust_bill},
+        'cust_pkg'       => $opt->{cust_pkg},
+        'invoicing_list' => \@invoicing_list,
+        'msgnum'         => $conf->config('payment_receipt_msgnum', $cust_main->agentnum)
+    );
+
+  } elsif ( ! $cust_main->invoice_noemail ) { #not manual
+
+    # check to see if they want to send specific message template as receipt for auto payments
+    if ( $conf->config('payment_receipt_msgnum_auto', $cust_main->agentnum) ) {
+      $error = $self->send_message_receipt(
+        'cust_main' => $cust_main,
+        'cust_bill' => $opt->{cust_bill},
+        'msgnum'    => $conf->config('payment_receipt_msgnum_auto', $cust_main->agentnum),
+      );
+    }
+    else {
+      my $queue = new FS::queue {
+        'job'     => 'FS::cust_bill::queueable_email',
+        'paynum'  => $self->paynum,
+        'custnum' => $cust_main->custnum,
+      };
+
+      my %opt = (
+        'invnum'      => $cust_bill->invnum,
+        'no_coupon'   => 1,
+      );
+
+      if ( my $mode = $conf->config('payment_receipt_statement_mode') ) {
+        $opt{'mode'} = $mode;
+      } else {
+        # backward compatibility, no good fix for this yet as some people may
+        # still have "invoice_latex_statement" and such options
+        $opt{'template'} = 'statement';
+        $opt{'notice_name'} = 'Statement';
+      }
+
+      $error = $queue->insert(%opt);
+    }
+  }
+
+  warn "send_receipt: $error\n" if $error;
+}
+
+=item send_message_receipt
+
+sends out a message receipt.
+$error = $self->send_message_receipt(
+        'cust_main'      => $cust_main,
+        'cust_bill'      => $opt->{cust_bill},
+        'cust_pkg'       => $opt->{cust_pkg},
+        'invoicing_list' => \@invoicing_list,
+        'msgnum'         => $conf->config('payment_receipt_msgnum', $cust_main->agentnum)
+      );
+
+=cut
+
+sub send_message_receipt {
+  my ($self, %opt) = @_;
+  my $cust_main      = $opt{'cust_main'};
+  my $cust_bill      = $opt{'cust_bill'};
+  my $cust_pkg       = $opt{'cust_pkg'};
+  my @invoicing_list = ref($opt{'invoicing_list'}) ? @{ $opt{'invoicing_list'} } : ( $opt{'invoicing_list'} );
+  my $msgnum         = $opt{'msgnum'};
+  my $error = '';
+
     if ( $msgnum ) {
 
       my %substitutions = ();
-      $substitutions{invnum} = $opt->{cust_bill}->invnum if $opt->{cust_bill};
+      $substitutions{invnum} = $cust_bill->invnum if $cust_bill;
+
+      my $msg_template = qsearchs('msg_template',{ msgnum => $msgnum});
+      unless ($msg_template) {
+        return "send_receipt could not load msg_template";
+      }
 
       my $queue = new FS::queue {
         'job'     => 'FS::Misc::process_send_email',
@@ -683,15 +761,13 @@ sub send_receipt {
         ),
         'msgtype' => 'receipt', # override msg_template's default
       );
-
     } elsif ( $conf->exists('payment_receipt_email') ) {
 
       my $receipt_template = new Text::Template (
         TYPE   => 'ARRAY',
         SOURCE => [ map "$_\n", $conf->config('payment_receipt_email') ],
       ) or do {
-        warn "can't create payment receipt template: $Text::Template::ERROR";
-        return '';
+        return "can't create payment receipt template: $Text::Template::ERROR";
       };
 
       my $payby = $self->payby;
@@ -715,13 +791,13 @@ sub send_receipt {
         'company_name' => $conf->config('company_name', $cust_main->agentnum),
       );
 
-      $fill_in{'invnum'} = $opt->{cust_bill}->invnum if $opt->{cust_bill};
+      $fill_in{'invnum'} = $cust_bill->invnum if $cust_bill;
 
-      if ( $opt->{'cust_pkg'} ) {
-        $fill_in{'pkg'} = $opt->{'cust_pkg'}->part_pkg->pkg;
+      if ( $cust_pkg ) {
+        $fill_in{'pkg'} = $cust_pkg->part_pkg->pkg;
         #setup date, other things?
       }
-
+      
       my $queue = new FS::queue {
         'job'     => 'FS::Misc::process_send_generated_email',
         'paynum'  => $self->paynum,
@@ -734,41 +810,12 @@ sub send_receipt {
         'to'      => \@invoicing_list,
         'subject' => 'Payment receipt',
         'body'    => [ $receipt_template->fill_in( HASH => \%fill_in ) ],
-      );
-
-    } else {
-
-      warn "payment_receipt is on, but no payment_receipt_msgnum\n";
-
-    }
-
-  } elsif ( ! $cust_main->invoice_noemail ) { #not manual
-
-    my $queue = new FS::queue {
-       'job'     => 'FS::cust_bill::queueable_email',
-       'paynum'  => $self->paynum,
-       'custnum' => $cust_main->custnum,
-    };
-
-    my %opt = (
-      'invnum'      => $cust_bill->invnum,
-      'no_coupon'   => 1,
-    );
-
-    if ( my $mode = $conf->config('payment_receipt_statement_mode') ) {
-      $opt{'mode'} = $mode;
+      );  
     } else {
-      # backward compatibility, no good fix for this yet as some people may
-      # still have "invoice_latex_statement" and such options
-      $opt{'template'} = 'statement';
-      $opt{'notice_name'} = 'Statement';
+      $error = "payment_receipt is on, but no payment_receipt_msgnum\n";
     }
 
-    $error = $queue->insert(%opt);
-
-  }
-  
-  warn "send_receipt: $error\n" if $error;
+  return $error;
 }
 
 =item cust_bill_pay
@@ -1105,6 +1152,30 @@ sub unapplied_sql {
 
 }
 
+=item SSAPI_getinfo
+
+=cut
+
+sub SSAPI_getinfo {
+  #my( $self, %opt ) = @_;
+  my $self = shift;
+
+  +{ 'paynum'       => $self->paynum,
+     '_date'        => $self->_date,
+     'date'         => time2str("%b %o, %Y", $self->_date),
+     'date_short'   => time2str("%m-%d-%Y",  $self->_date),
+     'paid'         => sprintf('%.2f', $self->paid),
+     'payby'        => $self->payby,
+     'paycardtype'  => $self->paycardtype,
+     'paymask'      => $self->paymask,
+     'processor'    => $self->processor,
+     'auth'         => $self->auth,
+     'order_number' => $self->order_number,
+  };
+
+}
+
+
 # _upgrade_data
 #
 # Used by FS::Upgrade to migrate to a new database.
@@ -1248,10 +1319,34 @@ sub _upgrade_data {  #class method
   }
 
   ###
-  # set paycardtype
+  # don't set paycardtype until 4.x
   ###
-  $class->upgrade_set_cardtype;
-
+  #$class->upgrade_set_cardtype;
+
+  # for batch payments, make sure paymask is set
+  do {
+    local $FS::payinfo_Mixin::allow_closed_replace = 1;
+    local $FS::payinfo_Mixin::ignore_masked_payinfo = 1;
+
+    my $cursor = FS::Cursor->new({
+      table => 'cust_pay',
+      extra_sql => ' WHERE paymask IS NULL AND payinfo IS NOT NULL
+                    AND payby IN(\'CARD\', \'CHEK\')
+                    AND batchnum IS NOT NULL',
+    });
+
+    # records from cursors for some reason don't decrypt payinfo, so
+    # call replace_old to fetch the record "normally"
+    while (my $cust_pay = $cursor->fetch) {
+      $cust_pay = $cust_pay->replace_old;
+      $cust_pay->set('paymask', $cust_pay->mask_payinfo);
+      my $error = $cust_pay->replace;
+      if ($error) {
+        die "$error (setting masked payinfo on payment#". $cust_pay->paynum.
+          ")\n"
+      }
+    }
+  };
 }
 
 sub process_upgrade_paybatch {