X-Git-Url: http://git.freeside.biz/gitweb/?a=blobdiff_plain;f=FS%2FFS%2Fcust_main.pm;h=78739bbb4c78169ee9e7c7a7d3b62a2c3d990bd3;hb=f8f4c51eaa6f5aa3d49672fe7a17f19fa22494c0;hp=8387af4a462e7bc6a6c1bab0fa92b6bce8c5e8e4;hpb=dde22b43f5f2efbdc8e8fc411ddac1357e70cbc4;p=freeside.git diff --git a/FS/FS/cust_main.pm b/FS/FS/cust_main.pm index 8387af4a4..78739bbb4 100644 --- a/FS/FS/cust_main.pm +++ b/FS/FS/cust_main.pm @@ -86,7 +86,7 @@ $skip_fuzzyfiles = 0; @fuzzyfields = ( 'first', 'last', 'company', 'address1' ); @encrypted_fields = ('payinfo', 'paycvv'); -sub nohistory_fields { ('paycvv'); } +sub nohistory_fields { ('payinfo', 'paycvv'); } @paytypes = ('', 'Personal checking', 'Personal savings', 'Business checking', 'Business savings'); @@ -1453,8 +1453,15 @@ sub replace { } - if ( $self->payby =~ /^(CARD|CHEK|LECB)$/ && - grep { $self->get($_) ne $old->get($_) } qw(payinfo paydate payname) ) { + if ( $self->payby =~ /^(CARD|CHEK|LECB)$/ + && ( ( $self->get('payinfo') ne $old->get('payinfo') + && $self->get('payinfo') !~ /^99\d{14}$/ + ) + || grep { $self->get($_) ne $old->get($_) } qw(paydate payname) + ) + ) + { + # card/check/lec info has changed, want to retry realtime_ invoice events my $error = $self->retry_realtime; if ( $error ) { @@ -1708,12 +1715,7 @@ sub check { # If it is encrypted and the private key is not availaible then we can't # check the credit card. - - my $check_payinfo = 1; - - if ($self->is_encrypted($self->payinfo)) { - $check_payinfo = 0; - } + my $check_payinfo = ! $self->is_encrypted($self->payinfo); if ( $check_payinfo && $self->payby =~ /^(CARD|DCRD)$/ ) { @@ -1727,7 +1729,8 @@ sub check { or return gettext('invalid_card'); # . ": ". $self->payinfo; return gettext('unknown_card_type') - if cardtype($self->payinfo) eq "Unknown"; + if $self->payinfo !~ /^99\d{14}$/ #token + && cardtype($self->payinfo) eq "Unknown"; my $ban = qsearchs('banned_pay', $self->_banned_pay_hashref); if ( $ban ) { @@ -4239,6 +4242,7 @@ sub _bop_options { $options->{payment_gateway}->gatewaynum ? $options->{payment_gateway}->options : @{ $options->{payment_gateway}->get('options') }; + } sub _bop_defaults { @@ -4561,6 +4565,8 @@ sub realtime_bop { my $BOP_TESTING_SUCCESS = 1; unless ( $BOP_TESTING ) { + $transaction->test_transaction(1) + if $conf->exists('business-onlinepayment-test_transaction'); $transaction->submit(); } else { if ( $BOP_TESTING_SUCCESS ) { @@ -4613,6 +4619,8 @@ sub realtime_bop { $capture->content( %capture ); + $capture->test_transaction(1) + if $conf->exists('business-onlinepayment-test_transaction'); $capture->submit(); unless ( $capture->is_success ) { @@ -4642,6 +4650,25 @@ sub realtime_bop { } ### + # Tokenize + ### + + + if ( $transaction->can('card_token') && $transaction->card_token ) { + + $self->card_token($transaction->card_token); + + if ( $options{'payinfo'} eq $self->payinfo ) { + $self->payinfo($transaction->card_token); + my $error = $self->replace; + if ( $error ) { + warn "WARNING: error storing token: $error, but proceeding anyway\n"; + } + } + + } + + ### # result handling ### @@ -4764,7 +4791,7 @@ sub _realtime_bop_result { 'paid' => $cust_pay_pending->paid, '_date' => '', 'payby' => $cust_pay_pending->payby, - #'payinfo' => $payinfo, + 'payinfo' => $options{'payinfo'}, 'paybatch' => $paybatch, 'paydate' => $cust_pay_pending->paydate, 'pkgnum' => $cust_pay_pending->pkgnum, @@ -5168,7 +5195,7 @@ sub realtime_refund_bop { my $self = shift; my %options = (); - if (ref($_[0]) ne 'HASH') { + if (ref($_[0]) eq 'HASH') { %options = %{$_[0]}; } else { my $method = shift; @@ -5300,6 +5327,8 @@ sub realtime_refund_bop { } } $void->content( 'action' => 'void', %content ); + $void->test_transaction(1) + if $conf->exists('business-onlinepayment-test_transaction'); $void->submit(); if ( $void->is_success ) { my $error = $cust_pay->void($options{'reason'}); @@ -5402,6 +5431,8 @@ sub realtime_refund_bop { ); warn join('', map { " $_ => $sub_content{$_}\n" } keys %sub_content ) if $DEBUG > 1; + $refund->test_transaction(1) + if $conf->exists('business-onlinepayment-test_transaction'); $refund->submit(); return "$processor error: ". $refund->error_message @@ -5840,29 +5871,17 @@ sub total_owed_date { my $self = shift; my $time = shift; -# my $custnum = $self->custnum; -# -# my $owed_sql = FS::cust_bill->owed_sql; -# -# my $sql = " -# SELECT SUM($owed_sql) FROM cust_bill -# WHERE custnum = $custnum -# AND _date <= $time -# "; -# -# my $sth = dbh->prepare($sql) or die dbh->errstr; -# $sth->execute() or die $sth->errstr; -# -# return sprintf( '%.2f', $sth->fetchrow_arrayref->[0] ); + my $custnum = $self->custnum; - my $total_bill = 0; - foreach my $cust_bill ( - grep { $_->_date <= $time } - qsearch('cust_bill', { 'custnum' => $self->custnum, } ) - ) { - $total_bill += $cust_bill->owed; - } - sprintf( "%.2f", $total_bill ); + my $owed_sql = FS::cust_bill->owed_sql; + + my $sql = " + SELECT SUM($owed_sql) FROM cust_bill + WHERE custnum = $custnum + AND _date <= $time + "; + + sprintf( "%.2f", $self->scalar_sql($sql) ); } @@ -5932,9 +5951,18 @@ sub total_credited { sub total_unapplied_credits { my $self = shift; - my $total_credit = 0; - $total_credit += $_->credited foreach $self->cust_credit; - sprintf( "%.2f", $total_credit ); + + my $custnum = $self->custnum; + + my $unapplied_sql = FS::cust_credit->unapplied_sql; + + my $sql = " + SELECT SUM($unapplied_sql) FROM cust_credit + WHERE custnum = $custnum + "; + + sprintf( "%.2f", $self->scalar_sql($sql) ); + } =item total_unapplied_credits_pkgnum PKGNUM @@ -5961,9 +5989,18 @@ See L. sub total_unapplied_payments { my $self = shift; - my $total_unapplied = 0; - $total_unapplied += $_->unapplied foreach $self->cust_pay; - sprintf( "%.2f", $total_unapplied ); + + my $custnum = $self->custnum; + + my $unapplied_sql = FS::cust_pay->unapplied_sql; + + my $sql = " + SELECT SUM($unapplied_sql) FROM cust_pay + WHERE custnum = $custnum + "; + + sprintf( "%.2f", $self->scalar_sql($sql) ); + } =item total_unapplied_payments_pkgnum PKGNUM @@ -5991,9 +6028,17 @@ customer. See L. sub total_unapplied_refunds { my $self = shift; - my $total_unapplied = 0; - $total_unapplied += $_->unapplied foreach $self->cust_refund; - sprintf( "%.2f", $total_unapplied ); + my $custnum = $self->custnum; + + my $unapplied_sql = FS::cust_refund->unapplied_sql; + + my $sql = " + SELECT SUM($unapplied_sql) FROM cust_refund + WHERE custnum = $custnum + "; + + sprintf( "%.2f", $self->scalar_sql($sql) ); + } =item balance @@ -6005,12 +6050,7 @@ total_unapplied_credits minus total_unapplied_payments). sub balance { my $self = shift; - sprintf( "%.2f", - $self->total_owed - + $self->total_unapplied_refunds - - $self->total_unapplied_credits - - $self->total_unapplied_payments - ); + $self->balance_date_range; } =item balance_date TIME @@ -6025,19 +6065,13 @@ functions. sub balance_date { my $self = shift; - my $time = shift; - sprintf( "%.2f", - $self->total_owed_date($time) - + $self->total_unapplied_refunds - - $self->total_unapplied_credits - - $self->total_unapplied_payments - ); + $self->balance_date_range(shift); } -=item balance_date_range START_TIME [ END_TIME [ OPTION => VALUE ... ] ] +=item balance_date_range [ START_TIME [ END_TIME [ OPTION => VALUE ... ] ] ] -Returns the balance for this customer, only considering invoices with date -earlier than START_TIME, and optionally not later than END_TIME +Returns the balance for this customer, optionally considering invoices with +date earlier than START_TIME, and not later than END_TIME (total_owed_date minus total_unapplied_credits minus total_unapplied_payments). Times are specified as SQL fragments or numeric @@ -7364,10 +7398,10 @@ sub balance_sql { " WHERE cust_refund.custnum = cust_main.custnum ) "; } -=item balance_date_sql START_TIME [ END_TIME [ OPTION => VALUE ... ] ] +=item balance_date_sql [ START_TIME [ END_TIME [ OPTION => VALUE ... ] ] ] -Returns an SQL fragment to retreive the balance for this customer, only -considering invoices with date earlier than START_TIME, and optionally not +Returns an SQL fragment to retreive the balance for this customer, optionally +considering invoices with date earlier than START_TIME, and not later than END_TIME (total_owed_date minus total_unapplied_credits minus total_unapplied_payments). @@ -7450,9 +7484,11 @@ Available options are: =cut sub unapplied_payments_date_sql { - my( $class, $start, $end, ) = @_; + my( $class, $start, $end, %opt ) = @_; + + my $cutoff = $opt{'cutoff'}; - my $unapp_pay = FS::cust_pay->unapplied_sql; + my $unapp_pay = FS::cust_pay->unapplied_sql($cutoff); my $pay_where = $class->_money_table_where( 'cust_pay', $start, $end, 'unapplied_date'=>1 ); @@ -8805,14 +8841,23 @@ sub _agent_plandata { } +=item queued_bill 'custnum' => CUSTNUM [ , OPTION => VALUE ... ] + +Subroutine (not a method), designed to be called from the queue. + +Takes a list of options and values. + +Pulls up the customer record via the custnum option and calls bill_and_collect. + +=cut + sub queued_bill { - ## actual sub, not a method, designed to be called from the queue. - ## sets up the customer, and calls the bill_and_collect my (%args) = @_; #, ($time, $invoice_time, $check_freq, $resetup) = @_; + my $cust_main = qsearchs( 'cust_main', { custnum => $args{'custnum'} } ); - $cust_main->bill_and_collect( - %args, - ); + warn 'bill_and_collect custnum#'. $cust_main->custnum. "\n";#log custnum w/pid + + $cust_main->bill_and_collect( %args ); } sub _upgrade_data { #class method