when canceling services across multiple packages, transaction-protect each one separa...
authorMark Wells <mark@freeside.biz>
Wed, 20 Jul 2016 16:43:38 +0000 (09:43 -0700)
committerChristopher Burger <burgerc@freeside.biz>
Wed, 21 Nov 2018 17:45:53 +0000 (12:45 -0500)
Conflicts:
FS/FS/cust_main.pm

FS/FS/cust_main.pm

index 88dd0e5..d0d85b9 100644 (file)
@@ -34,6 +34,7 @@ use Date::Format;
 use File::Temp; #qw( tempfile );
 use Email::Address;
 use Business::CreditCard 0.28;
 use File::Temp; #qw( tempfile );
 use Email::Address;
 use Business::CreditCard 0.28;
+use Try::Tiny;
 use FS::UID qw( getotaker dbh driver_name );
 use FS::Record qw( qsearchs qsearch dbdef regexp_sql );
 use FS::Misc qw( generate_email send_email generate_ps do_print money_pretty card_types );
 use FS::UID qw( getotaker dbh driver_name );
 use FS::Record qw( qsearchs qsearch dbdef regexp_sql );
 use FS::Misc qw( generate_email send_email generate_ps do_print money_pretty card_types );
@@ -2495,10 +2496,9 @@ sub cancel_pkgs {
   }
   dbh->commit;
 
   }
   dbh->commit;
 
-  $FS::UID::AutoCommit = 1;
   my @errors;
   my @errors;
-  # now cancel all services, the same way we would for individual packages.
-  # if any of them fail, cancel the rest anyway.
+  # try to cancel each service, the same way we would for individual packages,
+  # but in cancel weight order.
   my @cust_svc = map { $_->cust_svc } @pkgs;
   my @sorted_cust_svc =
     map  { $_->[0] }
   my @cust_svc = map { $_->cust_svc } @pkgs;
   my @sorted_cust_svc =
     map  { $_->[0] }
@@ -2511,8 +2511,15 @@ sub cancel_pkgs {
   foreach my $cust_svc (@sorted_cust_svc) {
     my $part_svc = $cust_svc->part_svc;
     next if ( defined($part_svc) and $part_svc->preserve );
   foreach my $cust_svc (@sorted_cust_svc) {
     my $part_svc = $cust_svc->part_svc;
     next if ( defined($part_svc) and $part_svc->preserve );
-    my $error = $cust_svc->cancel; # immediate cancel, no date option
-    push @errors, $error if $error;
+    # immediate cancel, no date option
+    # transactionize individually
+    my $error = try { $cust_svc->cancel } catch { $_ };
+    if ( $error ) {
+      dbh->rollback;
+      push @errors, $error;
+    } else {
+      dbh->commit;
+    }
   }
   if (@errors) {
     return @errors;
   }
   if (@errors) {
     return @errors;
@@ -2540,7 +2547,12 @@ sub cancel_pkgs {
       }
     }
     my $error = $_->cancel(%lopt);
       }
     }
     my $error = $_->cancel(%lopt);
-    push @errors, 'pkgnum '.$_->pkgnum.': '.$error if $error;
+    if ( $error ) {
+      dbh->rollback;
+      push @errors, 'pkgnum '.$_->pkgnum.': '.$error;
+    } else {
+      dbh->commit;
+    }
   }
 
   return @errors;
   }
 
   return @errors;