RT# 83450 - fixed rateplan export
[freeside.git] / FS / FS / cust_pay_pending.pm
index 8c6ef69..8f313f4 100644 (file)
@@ -1,17 +1,13 @@
 package FS::cust_pay_pending;
+use base qw( FS::payinfo_transaction_Mixin FS::cust_main_Mixin FS::Record );
 
 use strict;
-use vars qw( @ISA  @encrypted_fields );
-use FS::Record qw( qsearch qsearchs dbh ); #dbh for _upgrade_data
-use FS::payinfo_transaction_Mixin;
-use FS::cust_main_Mixin;
-use FS::cust_main;
-use FS::cust_pkg;
+use vars qw( @encrypted_fields );
+use FS::Record qw( qsearchs dbh ); #dbh for _upgrade_data
 use FS::cust_pay;
 
-@ISA = qw( FS::payinfo_transaction_Mixin FS::cust_main_Mixin FS::Record );
-
 @encrypted_fields = ('payinfo');
+sub nohistory_fields { ('payinfo'); }
 
 =head1 NAME
 
@@ -139,6 +135,10 @@ L<FS::payment_gateway> id.
 
 Payment number (L<FS::cust_pay>) of the completed payment.
 
+=item void_paynum
+
+Payment number of the payment if it's been voided.
+
 =item invnum
 
 Invoice number (L<FS::cust_bill>) to try to apply this payment to.
@@ -215,7 +215,7 @@ sub check {
 
   my $error = 
     $self->ut_numbern('paypendingnum')
-    || $self->ut_foreign_key('custnum', 'cust_main', 'custnum')
+    || $self->ut_foreign_keyn('custnum', 'cust_main', 'custnum')
     || $self->ut_money('paid')
     || $self->ut_numbern('_date')
     || $self->ut_textn('payunique')
@@ -228,12 +228,17 @@ sub check {
     || $self->ut_foreign_keyn('paynum', 'cust_pay', 'paynum' )
     || $self->ut_foreign_keyn('pkgnum', 'cust_pkg', 'pkgnum')
     || $self->ut_foreign_keyn('invnum', 'cust_bill', 'invnum')
+    || $self->ut_foreign_keyn('void_paynum', 'cust_pay_void', 'paynum' )
     || $self->ut_flag('manual')
     || $self->ut_numbern('discount_term')
     || $self->payinfo_check() #payby/payinfo/paymask/paydate
   ;
   return $error if $error;
 
+  if (!$self->custnum and !$self->get('custnum_pending')) {
+    return 'custnum required';
+  }
+
   $self->_date(time) unless $self->_date;
 
   # UNIQUE index should catch this too, without race conditions, but this
@@ -259,12 +264,6 @@ Returns the associated L<FS::cust_main> record if any.  Otherwise returns false.
 
 =cut
 
-sub cust_main {
-  my $self = shift;
-  qsearchs('cust_main', { custnum => $self->custnum } );
-}
-
-
 #these two are kind-of false laziness w/cust_main::realtime_bop
 #(currently only used when resolving pending payments manually)
 
@@ -398,6 +397,8 @@ sub approve {
       warn $e;
       return $e;
     }
+    
+    $self->set('jobnum','');
   }
 
   if ( $opt{'paynum_ref'} ) {
@@ -458,6 +459,26 @@ sub decline {
   $self->replace;
 }
 
+=item reverse [ STATUSTEXT ]
+
+Sets the status of this pending payment to "done" (with statustext
+"reversed (manual)" unless otherwise specified).
+
+Currently only used when resolving pending payments manually.
+
+=cut
+
+# almost complete false laziness with decline,
+# but want to avoid confusion, in case any additional steps/defaults are ever added to either
+sub reverse {
+  my $self = shift;
+  my $statustext = shift || "reversed (manual)";
+
+  $self->status('done');
+  $self->statustext($statustext);
+  $self->replace;
+}
+
 # _upgrade_data
 #
 # Used by FS::Upgrade to migrate to a new database.
@@ -473,6 +494,29 @@ sub _upgrade_data {  #class method
 
 }
 
+sub _upgrade_schema {
+  my ($class, %opts) = @_;
+
+  # fix records where jobnum points to a nonexistent queue job
+  my $sql = 'UPDATE cust_pay_pending SET jobnum = NULL
+    WHERE NOT EXISTS (
+      SELECT 1 FROM queue WHERE queue.jobnum = cust_pay_pending.jobnum
+    )';
+  my $sth = dbh->prepare($sql) or die dbh->errstr;
+  $sth->execute or die $sth->errstr;
+
+  # fix records where custnum points to a nonexistent customer
+  $sql = 'UPDATE cust_pay_pending SET custnum = NULL
+    WHERE NOT EXISTS (
+      SELECT 1 FROM cust_main WHERE cust_main.custnum = cust_pay_pending.custnum
+    )';
+  $sth = dbh->prepare($sql) or die dbh->errstr;
+  $sth->execute or die $sth->errstr;
+
+
+  '';
+}
+
 =back
 
 =head1 BUGS