+ my $recur_charge = $br * $months / $self->freq;
+ # round this, because the real recur charge is rounded
+ $recur_charge = sprintf('%.2f', $recur_charge);
+
+ # if it's a percentage discount, calculate it based on that estimate.
+ # otherwise use the flat amount.
+
+ if ( $discount->percent > 0 ) {
+ $amount = $recur_charge * $discount->percent / 100;
+ } elsif ( $discount->amount > 0
+ and $cust_pkg->pkgpart == $param->{'real_pkgpart'} ) {
+ $amount = $discount->amount * $months;
+ }
+
+ if ( exists $param->{'discount_left_recur'}{$discount->discountnum} ) {
+ # there is a discount_left_recur entry for this discountnum, so this
+ # is the second (recur) pass on the discount. use up transferred
+ # remainder of discount from setup.
+ #
+ # note that discount_left_recur can now be zero.
+ $amount = $param->{'discount_left_recur'}{$discount->discountnum};
+ $param->{'discount_left_recur'}{$discount->discountnum} = 0;
+ $months = 1; # XXX really? not $chg_months?
+ }
+ #elsif ( $discount->setup
+ # && ($discount->months || 0) == 1
+ # && $discount->amount > 0
+ # ) {
+ # next;
+ #
+ # RT #11512: bugfix to prevent applying flat discount to both setup
+ # and recur. The original implementation ignored discount_left_recur
+ # if it was zero, so if the setup fee used up the entire flat
+ # discount, the recurring charge would get to use the entire flat
+ # discount also. This bugfix was a kludge. Instead, we now allow
+ # discount_left_recur to be zero in that case, and then the available
+ # recur discount is zero.
+ #}
+
+ # Transfer remainder of discount, if any, to setup
+ # This is used when the recur phase wants to add a setup fee
+ # (prorate_defer_bill): the "discount_left_setup" amount will
+ # be subtracted in _make_lines.
+ if ( $discount->amount > 0 && ($discount->months || 0) != 1 )
+ {
+ # make sure there is a setup discount with this discountnum
+ # on the same package.
+ if ( qsearchs('cust_pkg_discount', {
+ pkgnum => $cust_pkg->pkgnum,
+ discountnum => $discount->discountnum,
+ setuprecur => 'setup'
+ }) )
+ {
+ # $amount is no longer permonth at this point! correct. very good.
+ $discount_left = $amount - $recur_charge; # backward, as above
+ if ( $discount_left > 0 ) {
+ $amount = $recur_charge;
+ $param->{'discount_left_setup'}{$discount->discountnum} =
+ 0 - $discount_left;
+ }
+ }
+ }
+
+ # cap the discount amount at the recur charge
+ $amount = min($amount, $recur_charge);
+
+ # if this is the base pkgpart, schedule increment_months_used to run at
+ # the end of billing. (addon packages haven't been calculated yet, so
+ # don't let the discount expire during the billing process. RT#17045.)
+ if ( $cust_pkg->pkgpart == $param->{'real_pkgpart'} ) {
+ push @{ $param->{precommit_hooks} }, sub {
+ my $error = $cust_pkg_discount->increment_months_used($months);
+ die "error discounting: $error" if $error;
+ };
+ }
+
+ } # else not 'setup_charge'
+
+ $amount = sprintf('%.2f', $amount + 0.00000001 ); #so 1.005 rounds to 1.01