[freeside-commits] branch master updated. 94b60bb13c044e436800239be3e3c5a029bdff8e

Christopher Burger burgerc at freeside.biz
Mon Nov 5 14:45:32 PST 2018


The branch, master has been updated
       via  94b60bb13c044e436800239be3e3c5a029bdff8e (commit)
      from  1144312a89d0a9d9598f7279bb7c7b8f65e5b0b9 (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 94b60bb13c044e436800239be3e3c5a029bdff8e
Author: Christopher Burger <burgerc at freeside.biz>
Date:   Mon Nov 5 17:44:50 2018 -0500

    RT# 76093 - Added ability to charge a processing fee when taking a payment on the back end

diff --git a/FS/FS/Conf.pm b/FS/FS/Conf.pm
index aed054a33..d5b72fa4b 100644
--- a/FS/FS/Conf.pm
+++ b/FS/FS/Conf.pm
@@ -2654,6 +2654,14 @@ and customer address. Include units.',
   },
 
   {
+    'key'         => 'processing-fee',
+    'section'     => 'payments',
+    'description' => 'Fee for back end payment processing.',
+    'type'        => 'text',
+    'per_agent'   => 1,
+  },
+
+  {
     'key'         => 'banned_pay-pad',
     'section'     => 'credit_cards',
     'description' => 'Padding for encrypted storage of banned credit card hashes.  If you already have new-style SHA512 entries in the banned_pay table, do not change as this will invalidate the old entries.',
diff --git a/FS/FS/cust_main/Billing_Batch.pm b/FS/FS/cust_main/Billing_Batch.pm
index 70dc28892..1ea069de4 100644
--- a/FS/FS/cust_main/Billing_Batch.pm
+++ b/FS/FS/cust_main/Billing_Batch.pm
@@ -167,6 +167,41 @@ sub batch_card {
     return $error; # e.g. "Illegal zip" ala RT#75998
   }
 
+  if ($options{'processing-fee'} > 0) {
+    my $pf_cust_pkg;
+    my $processing_fee_text = 'Payment Processing Fee';
+    my $pf_change_error = $self->charge({
+            'amount'  => $options{'processing-fee'},
+            'pkg'   => $processing_fee_text,
+            'setuptax'  => 'Y',
+            'cust_pkg_ref' => \$pf_cust_pkg,
+    });
+
+    if($pf_change_error) {
+      warn 'Unable to add payment processing fee';
+      return '';
+    }
+
+    $pf_cust_pkg->setup(time);
+    my $pf_error = $pf_cust_pkg->replace;
+    if($pf_error) {
+      warn 'Unable to set setup time on cust_pkg for processing fee';
+      # but keep going...
+    }
+
+    my $cust_bill = qsearchs('cust_bill', { 'invnum' => $invnum });
+    unless ( $cust_bill ) {
+      warn "race condition + invoice deletion just happened";
+      return '';
+    }
+
+    my $grand_pf_error =
+      $cust_bill->add_cc_surcharge($pf_cust_pkg->pkgnum,$options{'processing-fee'});
+
+    warn "cannot add Processing fee to invoice #$invnum: $grand_pf_error"
+      if $grand_pf_error;
+  }
+
   my $unapplied =   $self->total_unapplied_credits
                   + $self->total_unapplied_payments
                   + $self->in_transit_payments;
diff --git a/FS/FS/cust_main/Billing_Realtime.pm b/FS/FS/cust_main/Billing_Realtime.pm
index 714a2e687..b29408b0e 100644
--- a/FS/FS/cust_main/Billing_Realtime.pm
+++ b/FS/FS/cust_main/Billing_Realtime.pm
@@ -474,8 +474,8 @@ sub realtime_bop {
   elsif($cc_surcharge_pct > 0 || $cc_surcharge_flat > 0) {
     # we're called not from event (i.e. from a
     # payment screen), so consider the given
-		# amount as post-surcharge
-    $cc_surcharge = $options{'amount'} - (($options{'amount'} - $cc_surcharge_flat) / ( 1 + $cc_surcharge_pct/100 )) if $options{'amount'} > 0;
+		# amount as post-surcharge-processing_fee
+    $cc_surcharge = $options{'amount'} - $options{'processing-fee'} - (($options{'amount'} - ($cc_surcharge_flat + $options{'processing-fee'})) / ( 1 + $cc_surcharge_pct/100 )) if $options{'amount'} > 0;
   }
   
   $cc_surcharge = sprintf("%.2f",$cc_surcharge) if $cc_surcharge > 0;
@@ -1061,7 +1061,7 @@ sub _realtime_bop_result {
       }
 
       # have a CC surcharge portion --> one-time charge
-      if ( $options{'cc_surcharge'} > 0 ) { 
+      if ( $options{'cc_surcharge'} > 0 || $options{'processing-fee'} > 0) {
 	    # XXX: this whole block needs to be in a transaction?
 
 	  my $invnum;
@@ -1082,44 +1082,83 @@ sub _realtime_bop_result {
 	  unless ( $invnum ) {
 	    # XXX: unlikely case - pre-paying before any invoices generated
 	    # what it should do is create a new invoice and pick it
-		warn 'CC SURCHARGE AND NO INVOICES PICKED TO APPLY IT!';
+		warn 'CC SURCHARGE OR PROCESS FEE AND NO INVOICES PICKED TO APPLY IT!';
 		return '';
 	  }
 
-	  my $cust_pkg;
-    my $cc_surcharge_text = 'Credit Card Surcharge';
-    $cc_surcharge_text = $conf->config('credit-card-surcharge-text', $self->agentnum) if $conf->exists('credit-card-surcharge-text', $self->agentnum);
-	  my $charge_error = $self->charge({
+    if ($options{'cc_surcharge'} > 0) {
+	    my $cust_pkg;
+      my $cc_surcharge_text = 'Credit Card Surcharge';
+      $cc_surcharge_text = $conf->config('credit-card-surcharge-text', $self->agentnum) if $conf->exists('credit-card-surcharge-text', $self->agentnum);
+	    my $charge_error = $self->charge({
 				    'amount' 	=> $options{'cc_surcharge'},
 				    'pkg' 	=> $cc_surcharge_text,
 				    'setuptax'  => 'Y',
 				    'cust_pkg_ref' => \$cust_pkg,
-				});
-	  if($charge_error) {
-		warn 'Unable to add CC surcharge cust_pkg';
-		return '';
-	  }
+			});
+
+	    if($charge_error) {
+		    warn 'Unable to add CC surcharge cust_pkg';
+		    return '';
+	    }
+
+      $cust_pkg->setup(time);
+      my $cp_error = $cust_pkg->replace;
+      if($cp_error) {
+        warn 'Unable to set setup time on cust_pkg for cc surcharge';
+        # but keep going...
+      }
 
-	  $cust_pkg->setup(time);
-	  my $cp_error = $cust_pkg->replace;
-	  if($cp_error) {
-	      warn 'Unable to set setup time on cust_pkg for cc surcharge';
-	    # but keep going...
-	  }
-				    
-	  my $cust_bill = qsearchs('cust_bill', { 'invnum' => $invnum });
-	  unless ( $cust_bill ) {
-	      warn "race condition + invoice deletion just happened";
-	      return '';
-	  }
+      my $cust_bill = qsearchs('cust_bill', { 'invnum' => $invnum });
+      unless ( $cust_bill ) {
+        warn "race condition + invoice deletion just happened";
+        return '';
+      }
+
+      my $grand_error =
+        $cust_bill->add_cc_surcharge($cust_pkg->pkgnum,$options{'cc_surcharge'});
+
+      warn "cannot add CC surcharge to invoice #$invnum: $grand_error"
+        if $grand_error;
+    } # end if $options{'cc_surcharge'}
+
+    if ($options{'processing-fee'} > 0) {
+      my $pf_cust_pkg;
+      my $processing_fee_text = 'Payment Processing Fee';
+      my $pf_change_error = $self->charge({
+            'amount'  => $options{'processing-fee'},
+            'pkg'   => $processing_fee_text,
+            'setuptax'  => 'Y',
+            'cust_pkg_ref' => \$pf_cust_pkg,
+      });
+
+      if($pf_change_error) {
+        warn 'Unable to add payment processing fee';
+        return '';
+      }
 
-	  my $grand_error = 
-	    $cust_bill->add_cc_surcharge($cust_pkg->pkgnum,$options{'cc_surcharge'});
+      $pf_cust_pkg->setup(time);
+      my $pf_error = $pf_cust_pkg->replace;
+      if($pf_error) {
+        warn 'Unable to set setup time on cust_pkg for processing fee';
+        # but keep going...
+      }
 
-	  warn "cannot add CC surcharge to invoice #$invnum: $grand_error"
-	    if $grand_error;
+      my $cust_bill = qsearchs('cust_bill', { 'invnum' => $invnum });
+      unless ( $cust_bill ) {
+        warn "race condition + invoice deletion just happened";
+        return '';
       }
 
+      my $grand_pf_error =
+        $cust_bill->add_cc_surcharge($pf_cust_pkg->pkgnum,$options{'processing-fee'});
+
+      warn "cannot add Processing fee to invoice #$invnum: $grand_pf_error"
+        if $grand_pf_error;
+    } #end if $options{'processing-fee'}
+
+      } #end if ( $options{'cc_surcharge'} > 0 || $options{'processing-fee'} > 0)
+
       return ''; #no error
 
     }
diff --git a/httemplate/elements/tr-amount_fee.html b/httemplate/elements/tr-amount_fee.html
index a84fef6ec..94795de37 100644
--- a/httemplate/elements/tr-amount_fee.html
+++ b/httemplate/elements/tr-amount_fee.html
@@ -8,7 +8,7 @@
                                 VALUE    = "<% $amount %>"
                                 SIZE     = 8
                                 STYLE    = "text-align:right;"
-%                               if ( $fee || $surcharge_percentage || $surcharge_flatfee ) {
+%                               if ( $fee || $surcharge_percentage || $surcharge_flatfee || $processing_fee) {
                                   onChange   = "amount_changed(this)"
                                   onKeyDown  = "amount_changed(this)"
                                   onKeyUp    = "amount_changed(this)"
@@ -38,7 +38,23 @@
     </TD>
   </TR>
 
-% if ($fee || $surcharge_percentage || $surcharge_flatfee ) {
+%        if ( $processing_fee ) {
+      <TR>
+        <TH ALIGN="right"><% mt('Apply processing fee') |h %></TH>
+        <TD>
+          <TABLE><TR>
+            <TD BGCOLOR="#ffffff">
+             <INPUT TYPE="checkbox" NAME="processing_fee" ID="processing_fee" VALUE="<% $processing_fee %>" onclick="<% $opt{prefix} %>process_fee_changed()">
+            </TD>
+            <TD ID="ajax_processingfee_cell" BGCOLOR="#dddddd" STYLE="border:1px solid blue">
+             <FONT SIZE="+1">A processing fee of <% $processing_fee %> is being applied to this transaction.</FONT>
+            </TD>
+          </TR></TABLE>
+        </TD>
+      </TR>
+%        }
+
+% if ($fee || $surcharge_percentage || $surcharge_flatfee || $processing_fee) {
 
     <SCRIPT TYPE="text/javascript">
 
@@ -58,6 +74,10 @@
 
 % if ( $surcharge_percentage || $surcharge_flatfee ) {
         var surcharge_cell = document.getElementById('ajax_surcharge_cell');
+        var amount = what.value;
+        if (document.getElementById('processing_fee').checked == true) {
+          amount = (what.value - <% $processing_fee %>);
+        }
         var surcharge = ((what.value - <% $surcharge_flatfee %>) * <% $surcharge_percentage %>) + <% $surcharge_flatfee %>;
         surcharge_cell.innerHTML = '<FONT SIZE="+1">A credit card surcharge of ' + surcharge.toFixed(2) + ' is included in this payment</FONT>';
 % }
@@ -82,6 +102,7 @@ my $fee_op = '';
 my $surcharge = '';
 my $surcharge_percentage = 0;
 my $surcharge_flatfee = 0;
+my $processing_fee = 0;
 
 if ( $opt{'process-pkgpart'}
      and ! $opt{'process-skip_first'} || $opt{'num_payments'}
@@ -115,6 +136,7 @@ if ( $amount ) {
   $surcharge_flatfee = $opt{'surcharge_flatfee'} if $opt{'surcharge_flatfee'} > 0;
   $surcharge = $amount * $surcharge_percentage if $surcharge_percentage > 0;
   $surcharge += $surcharge_flatfee if ( $surcharge_flatfee > 0 && $amount > 0 );
+  $processing_fee = $opt{'processing_fee'} if $opt{'processing_fee'} > 0;
 
   $amount += $surcharge;
 
diff --git a/httemplate/elements/tr-select-payment_options.html b/httemplate/elements/tr-select-payment_options.html
index f86f3edfd..c5b84e756 100644
--- a/httemplate/elements/tr-select-payment_options.html
+++ b/httemplate/elements/tr-select-payment_options.html
@@ -22,6 +22,7 @@ Example:
           ? scalar($conf->config('credit-card-surcharge-flatfee', $cust_main->agentnum))
           : 0
       ),
+    'processing_fee' => scalar($conf->config('processing-fee', $cust_main->agentnum)),
   )
 
 </%doc>
@@ -59,6 +60,7 @@ Example:
 
       $('#payment_option_row').<% $payment_option_row %>();
       $('#payment_amount_row').<% $payment_amount_row %>();
+      $('#ajax_processingfee_cell').hide();
 
       if($('#payment_amount_row').is(':visible')) {
         var surcharge;
@@ -76,11 +78,21 @@ Example:
       function <% $opt{prefix} %>payment_option_changed(what) {
 
         var surcharge;
+        var processingFee = 0;
+        var pfElement = document.getElementById('processing_fee');
+
         if (document.getElementById('surcharge_percentage') || document.getElementById('surcharge_flatfee')) {
           surcharge = (+what.value * +document.getElementById('surcharge_percentage').value) + +document.getElementById('surcharge_flatfee').value;
         }
         else { surcharge = 0; }
-        var amount = +what.value + +surcharge;
+
+        if (pfElement != null) {
+          if (pfElement.checked == true) {
+           processingFee = +pfElement.value;
+          }
+        }
+
+        var amount = +what.value + +surcharge + +processingFee;
         document.getElementById('amount').disabled = true;
 
         if ( what.value == 'select' ) {
@@ -131,12 +143,21 @@ Example:
       function <% $opt{prefix} %>invoice_select_changed(what) {
 
         var surcharge;
+        var processingFee = 0;
+        var pfElement = document.getElementById('processing_fee');
         var invdue = document.getElementById("<% $opt{prefix} %>inv" + what.value);
         if (document.getElementById('surcharge_percentage') || document.getElementById('surcharge_flatfee')) {
           surcharge = (+invdue.value * +document.getElementById('surcharge_percentage').value) + +document.getElementById('surcharge_flatfee').value;
         }
         else { surcharge = 0; }
-        var amount = +invdue.value + +surcharge;
+
+        if (pfElement != null) {
+          if (pfElement.checked == true) {
+           processingFee = +pfElement.value;
+          }
+        }
+
+        var amount = +invdue.value + +surcharge + +processingFee;
 
         if ( what.value == 'select' ) {
           $('#payment_amount_row').hide();
@@ -154,6 +175,21 @@ Example:
 
       }
 
+      function <% $opt{prefix} %>process_fee_changed(what) {
+
+        if (document.getElementById('processing_fee').checked == true) {
+          var amount = +document.getElementById('amount').value + +document.getElementById('processing_fee').value;
+          $('#amount').val(amount.toFixed(2));
+          $('#ajax_processingfee_cell').show();
+        }
+        else {
+          var amount = +document.getElementById('amount').value - +document.getElementById('processing_fee').value;
+          $('#amount').val(amount.toFixed(2));
+          $('#ajax_processingfee_cell').hide();
+        }
+
+      }
+
 </SCRIPT>
 
 <%init>
diff --git a/httemplate/misc/payment.cgi b/httemplate/misc/payment.cgi
index 77f5acd6a..7911a5dd9 100644
--- a/httemplate/misc/payment.cgi
+++ b/httemplate/misc/payment.cgi
@@ -29,6 +29,7 @@
              ? scalar($conf->config('credit-card-surcharge-flatfee', $cust_main->agentnum))
              : 0
          ),
+         'processing_fee' => scalar($conf->config('processing-fee', $cust_main->agentnum)),
   &>
 
 % if ( $conf->exists('part_pkg-term_discounts') ) {
diff --git a/httemplate/misc/process/payment.cgi b/httemplate/misc/process/payment.cgi
index 7747bcbea..56bcfd872 100644
--- a/httemplate/misc/process/payment.cgi
+++ b/httemplate/misc/process/payment.cgi
@@ -41,6 +41,8 @@ my $cust_main = qsearchs({
 
 my $invoice = ($cgi->param('invoice') =~ /^(\d+)$/) ? $cgi->param('invoice') : '';
 
+my $processing_fee = $cgi->param('processing_fee') ? $cgi->param('processing_fee') : '';
+
 $cgi->param('amount') =~ /^\s*(\d*(\.\d\d)?)\s*$/
   or errorpage("illegal amount ". $cgi->param('amount'));
 my $amount = $1;
@@ -233,6 +235,7 @@ if ( $cgi->param('batch') ) {
                                      'paydate'  => $paydate,
                                      'payname'  => $payname,
                                      'invnum'   => $invoice,
+                                     'processing-fee' => $processing_fee,
                                      map { $_ => scalar($cgi->param($_)) } 
                                        @{$payby2fields{$payby}}
                                    );
@@ -256,6 +259,7 @@ if ( $cgi->param('batch') ) {
     'no_auto_apply' => ($cgi->param('apply') eq 'never') ? 'Y' : '',
     'no_invnum'     => 1,
     'invnum'        => $invoice,
+    'processing-fee' => $processing_fee,
     map { $_ => scalar($cgi->param($_)) } @{$payby2fields{$payby}}
   );
   errorpage($error) if $error;

-----------------------------------------------------------------------

Summary of changes:
 FS/FS/Conf.pm                                      |  8 ++
 FS/FS/cust_main/Billing_Batch.pm                   | 35 ++++++++
 FS/FS/cust_main/Billing_Realtime.pm                | 97 +++++++++++++++-------
 httemplate/elements/tr-amount_fee.html             | 26 +++++-
 httemplate/elements/tr-select-payment_options.html | 40 ++++++++-
 httemplate/misc/payment.cgi                        |  1 +
 httemplate/misc/process/payment.cgi                |  4 +
 7 files changed, 178 insertions(+), 33 deletions(-)




More information about the freeside-commits mailing list