X-Git-Url: http://git.freeside.biz/gitweb/?a=blobdiff_plain;f=FS%2FFS%2FClientAPI%2FMyAccount.pm;h=2671afb706ae3899266e13e71f2bbefa36146923;hb=a1ce9d2d64481946c6e4ba317a8c4631448dc842;hp=61082bd9eb5da16ff8c6581f4e4f49173847e8db;hpb=bb22f46481173b008fc9cb98b108ef1da9c1dc4d;p=freeside.git diff --git a/FS/FS/ClientAPI/MyAccount.pm b/FS/FS/ClientAPI/MyAccount.pm index 61082bd9e..2671afb70 100644 --- a/FS/FS/ClientAPI/MyAccount.pm +++ b/FS/FS/ClientAPI/MyAccount.pm @@ -46,8 +46,10 @@ use FS::payby; use FS::acct_rt_transaction; use FS::msg_template; use FS::contact; +use FS::cust_contact; +use FS::cust_location; -$DEBUG = 1; +$DEBUG = 0; $me = '[FS::ClientAPI::MyAccount]'; use vars qw( @cust_main_editable_fields @location_editable_fields ); @@ -82,7 +84,7 @@ sub skin_info { #return { 'error' => $session } if $context eq 'error'; my $agentnum = ''; - if ( $context eq 'customer' ) { + if ( $context eq 'customer' && $custnum ) { my $sth = dbh->prepare('SELECT agentnum FROM cust_main WHERE custnum = ?') or die dbh->errstr; @@ -237,7 +239,16 @@ sub login { return { error => 'Incorrect contact password.' } unless $contact->authenticate_password($p->{'password'}); - $session->{'custnum'} = $contact->custnum; + my @cust_contact = grep $_->selfservice_access, $contact->cust_contact; + if ( scalar(@cust_contact) == 1 ) { + $session->{'custnum'} = $cust_contact[0]->custnum; + } elsif ( scalar(@cust_contact) ) { + $session->{'customers'} = { map { $_->custnum => $_->cust_main->name } + @cust_contact + }; + } else { + return { error => 'No customer self-service access for contact' }; #?? + } } else { @@ -303,16 +314,18 @@ sub login { return { 'error' => '', 'session_id' => $session_id, + %$session, }; } sub logout { my $p = shift; + my $skin_info = skin_info($p); if ( $p->{'session_id'} ) { _cache->remove($p->{'session_id'}); - return { %{ skin_info($p) }, 'error' => '' }; + return { %$skin_info, 'error' => '' }; } else { - return { %{ skin_info($p) }, 'error' => "Can't resume session" }; #better error message + return { %$skin_info, 'error' => "Can't resume session" }; #better error message } } @@ -335,6 +348,23 @@ sub switch_acct { } +sub switch_cust { + my $p = shift; + my($context, $session, $custnum) = _custoragent_session_custnum($p); + return { 'error' => $session } if $context eq 'error'; + + $session->{'custnum'} = $p->{'custnum'} + if exists $session->{'customers'}{ $p->{'custnum'} }; + + my $conf = new FS::Conf; + my $timeout = $conf->config('selfservice-session_timeout') || '1 hour'; + _cache->set( $p->{'session_id'}, $session, $timeout ); + + return { 'error' => '', + %{ customer_info( { session_id=>$p->{'session_id'} } ) }, + }; +} + sub payment_gateway { # internal use only # takes a cust_main and a cust_payby entry, returns the payment_gateway @@ -379,22 +409,23 @@ sub access_info { my($context, $session, $custnum) = _custoragent_session_custnum($p); return { 'error' => $session } if $context eq 'error'; - my $cust_main = qsearchs('cust_main', { 'custnum' => $custnum } ) - or return { 'error' => "unknown custnum $custnum" }; + my $cust_main = qsearchs('cust_main', { 'custnum' => $custnum } ); $info->{'hide_payment_fields'} = [ map { - my $pg = payment_gateway($cust_main, $_); + my $pg = $cust_main && payment_gateway($cust_main, $_); $pg && $pg->gateway_namespace eq 'Business::OnlineThirdPartyPayment'; } @{ $info->{cust_paybys} } ]; $info->{'self_suspend_reason'} = - $conf->config('selfservice-self_suspend_reason', $cust_main->agentnum); + $conf->config('selfservice-self_suspend_reason', + $cust_main ? $cust_main->agentnum : '' + ); $info->{'edit_ticket_subject'} = $conf->exists('ticket_system-selfservice_edit_subject') && - $cust_main->edit_subject; + $cust_main && $cust_main->edit_subject; $info->{'timeout'} = $conf->config('selfservice-timeout') || 3600; @@ -431,7 +462,7 @@ sub customer_info { my $search = { 'custnum' => $custnum }; $search->{'agentnum'} = $session->{'agentnum'} if $context eq 'agent'; my $cust_main = qsearchs('cust_main', $search ) - or return { 'error' => "unknown custnum $custnum" }; + or return { 'error' => "customer_info: unknown custnum $custnum" }; my $list_tickets = list_tickets($p); $return{'tickets'} = $list_tickets->{'tickets'}; @@ -535,7 +566,7 @@ sub customer_info_short { my $search = { 'custnum' => $custnum }; $search->{'agentnum'} = $session->{'agentnum'} if $context eq 'agent'; my $cust_main = qsearchs('cust_main', $search ) - or return { 'error' => "unknown custnum $custnum" }; + or return { 'error' => "customer_info_short: unknown custnum $custnum" }; $return{display_custnum} = $cust_main->display_custnum; @@ -1135,6 +1166,7 @@ sub do_process_payment { my $error = $cust_main->realtime_bop( $FS::payby::payby2bop{$payby}, $amount, 'quiet' => 1, + 'manual' => 1, 'selfservice' => 1, 'paynum_ref' => \$paynum, %$validate, @@ -2271,11 +2303,23 @@ sub order_pkg { or return { 'error' => "unknown custnum $custnum" }; my $status = $cust_main->status; + + my %order_pkg_options = (); + if ( $p->{locationnum} > 0 ) { + $order_pkg_options{locationnum} = delete($p->{locationnum}); + } elsif ( $p->{address1} ) { + $order_pkg_options{'cust_location'} = new FS::cust_location { + map { $_ => $p->{$_} } + qw( address1 address2 city county state zip country ) + }; + } + #false laziness w/ClientAPI/Signup.pm my $cust_pkg = new FS::cust_pkg ( { - 'custnum' => $custnum, - 'pkgpart' => $p->{'pkgpart'}, + 'custnum' => $custnum, + 'pkgpart' => $p->{'pkgpart'}, + 'quantity' => $p->{'quantity'} || 1, } ); my $error = $cust_pkg->check; return { 'error' => $error } if $error; @@ -2334,11 +2378,12 @@ sub order_pkg { } - use Tie::RefHash; - tie my %hash, 'Tie::RefHash'; - %hash = ( $cust_pkg => \@svc ); - #msgcat - $error = $cust_main->order_pkgs( \%hash, 'noexport' => 1 ); + $error = $cust_main->order_pkg( + 'cust_pkg' => $cust_pkg, + 'svcs' => \@svc, + 'noexport' => 1, + %order_pkg_options, + ); return { 'error' => $error } if $error; my $conf = new FS::Conf; @@ -2914,7 +2959,12 @@ sub myaccount_passwd { #need to support the "ISP provides email that's used as a contact email" case #as well as we can. my $contact = FS::contact->by_selfservice_email($svc_acct->email); - if ( $contact && $contact->custnum == $custnum ) { + if ( $contact && qsearchs('cust_contact', { contactnum=> $contact->contactnum, + custnum => $custnum, + selfservice_access => 'Y', + } + ) + ) { #svc_acct was successful but this one returns an error? "shouldn't happen" $error ||= $contact->change_password($p->{'new_password'}); } @@ -2991,7 +3041,10 @@ sub reset_passwd { $contact = FS::contact->by_selfservice_email($p->{'email'}); - $cust_main = $contact->cust_main if $contact; + if ( $contact ) { + my @cust_contact = grep $_->selfservice_access, $contact->cust_contact; + $cust_main = $cust_contact[0]->cust_main if scalar(@cust_contact) == 1; + } #also look for an svc_acct, otherwise it would be super confusing @@ -3033,6 +3086,9 @@ sub reset_passwd { } + return { %$info, 'error' => 'Multi-customer contacts incompatible with customer-based verification' } + if ! $cust_main && $verification ne 'email'; + my %verify = ( 'email' => sub { 1; }, 'paymask' => sub { @@ -3155,7 +3211,9 @@ sub check_reset_passwd { my @contact_email = $contact->contact_email; return { 'error' => 'No contact email' } unless @contact_email; - $p->{'agentnum'} = $contact->cust_main->agentnum; + my @cust_contact = grep $_->selfservice_access, $contact->cust_contact; + $p->{'agentnum'} = $cust_contact[0]->cust_main->agentnum + if scalar(@cust_contact) == 1; my $info = skin_info($p); return { %$info, @@ -3205,7 +3263,9 @@ sub process_reset_passwd { $contact = qsearchs('contact', { 'contactnum' => $contactnum } ) or return { 'error' => "Contact not found" }; - $p->{'agentnum'} ||= $contact->cust_main->agentnum; + my @cust_contact = grep $_->selfservice_access, $contact->cust_contact; + $p->{'agentnum'} = $cust_contact[0]->cust_main->agentnum + if scalar(@cust_contact) == 1; $info ||= skin_info($p); }