[freeside-commits] branch FREESIDE_3_BRANCH updated. ae732741cb031ddb6c99156a8804cac3e7500f76

Ivan ivan at 420.am
Tue Sep 16 06:41:10 PDT 2014


The branch, FREESIDE_3_BRANCH has been updated
       via  ae732741cb031ddb6c99156a8804cac3e7500f76 (commit)
       via  aa59cc83ffa65da2fce9b5be42f483d9b17d91c0 (commit)
      from  2eb4ef92fbea43f55fd705d604fda5c815f9eb9c (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 ae732741cb031ddb6c99156a8804cac3e7500f76
Author: Ivan Kohler <ivan at freeside.biz>
Date:   Tue Sep 16 06:41:05 2014 -0700

    convert prospects to customers via quotations, RT#20688

diff --git a/FS/FS/prospect_main.pm b/FS/FS/prospect_main.pm
index a18c8ff..2e3c0b9 100644
--- a/FS/FS/prospect_main.pm
+++ b/FS/FS/prospect_main.pm
@@ -7,6 +7,7 @@ use Scalar::Util qw( blessed );
 use FS::Record qw( dbh qsearch qsearchs );
 use FS::agent;
 use FS::cust_location;
+use FS::cust_main;
 use FS::contact;
 use FS::qual;
 
@@ -81,7 +82,11 @@ primary key
 
 =item agentnum
 
-Agent
+Agent (see L<FS::agent>)
+
+=item refnum
+
+Referral (see L<FS::part_referral>)
 
 =item company
 
@@ -240,7 +245,8 @@ sub check {
 
   my $error = 
     $self->ut_numbern('prospectnum')
-    || $self->ut_foreign_key('agentnum', 'agent', 'agentnum' )
+    || $self->ut_foreign_key( 'agentnum', 'agent',         'agentnum' )
+    || $self->ut_foreign_key( 'refnum',   'part_referral', 'refnum' )
     || $self->ut_textn('company')
   ;
   return $error if $error;
@@ -316,6 +322,49 @@ sub agent {
   qsearchs( 'agent', { 'agentnum' => $self->agentnum } );
 }
 
+=item convert_cust_main
+
+Converts this prospect to a customer.
+
+If there is an error, returns an error message, otherwise, returns the
+newly-created FS::cust_main object.
+
+=cut
+
+sub convert_cust_main {
+  my $self = shift;
+
+  my @cust_location = $self->cust_location;
+  #the interface only allows one, so we're just gonna go with that for now
+
+  my @contact = $self->contact;
+
+  #XXX define one contact type as "billing", then we could pick just that one
+  my @invoicing_list = map $_->emailaddress, map $_->contact_email, @contact;
+
+  #XXX i'm not compatible with cust_main-require_phone (which is kind of a
+  # pre-contact thing anyway)
+
+  my $cust_main = new FS::cust_main {
+    'bill_location' => $cust_location[0],
+    'ship_location' => $cust_location[0],
+    ( map { $_ => $self->$_ } qw( agentnum refnum company ) ),
+  };
+
+  #XXX again, arbitrary, if one contact was "billing", that would be better
+  if ( $contact[0] ) {
+    $cust_main->set($_, $contact[0]->get($_)) foreach qw( first last );
+  } else {
+    $cust_main->set('first', 'Unknown');
+    $cust_main->set('last',  'Unknown');
+  }
+
+  $cust_main->insert( {}, \@invoicing_list,
+    'prospectnum' => $self->prospectnum,
+  )
+    or $cust_main;
+}
+
 =item search HASHREF
 
 (Class method)
diff --git a/FS/FS/quotation.pm b/FS/FS/quotation.pm
index 47f13e6..7f53e31 100644
--- a/FS/FS/quotation.pm
+++ b/FS/FS/quotation.pm
@@ -2,9 +2,12 @@ package FS::quotation;
 use base qw( FS::Template_Mixin FS::cust_main_Mixin FS::otaker_Mixin FS::Record );
 
 use strict;
+use Tie::RefHash;
+use FS::UID qw( dbh );
 use FS::Record qw( qsearch qsearchs );
 use FS::CurrentUser;
 use FS::cust_main;
+use FS::cust_pkg;
 use FS::prospect_main;
 use FS::quotation_pkg;
 
@@ -212,6 +215,75 @@ sub _items_total {
 
 sub enable_previous { 0 }
 
+=item convert_cust_main
+
+If this quotation already belongs to a customer, then returns that customer, as
+an FS::cust_main object.
+
+Otherwise, creates a new customer (FS::cust_main object and record, and
+associated) based on this quotation's prospect, then orders this quotation's
+packages as real packages for the customer.
+
+If there is an error, returns an error message, otherwise, returns the
+newly-created FS::cust_main object.
+
+=cut
+
+sub convert_cust_main {
+  my $self = shift;
+
+  my $cust_main = $self->cust_main;
+  return $cust_main if $cust_main; #already converted, don't again
+
+  my $oldAutoCommit = $FS::UID::AutoCommit;
+  local $FS::UID::AutoCommit = 0;
+  my $dbh = dbh;
+
+  $cust_main = $self->prospect_main->convert_cust_main;
+  unless ( ref($cust_main) ) { # eq 'FS::cust_main' ) {
+    $dbh->rollback if $oldAutoCommit;
+    return $cust_main;
+  }
+
+  $self->prospectnum('');
+  $self->custnum( $cust_main->custnum );
+  my $error = $self->replace || $self->order;
+  if ( $error ) {
+    $dbh->rollback if $oldAutoCommit;
+    return $error;
+  }
+
+  $dbh->commit or die $dbh->errstr if $oldAutoCommit;
+
+  $cust_main;
+
+}
+
+=item order
+
+This method is for use with quotations which are already associated with a customer.
+
+Orders this quotation's packages as real packages for the customer.
+
+If there is an error, returns an error message, otherwise returns false.
+
+=cut
+
+sub order {
+  my $self = shift;
+
+  tie my %cust_pkg, 'Tie::RefHash',
+    map { FS::cust_pkg->new({ pkgpart  => $_->pkgpart,
+                              quantity => $_->quantity,
+                           })
+            => [] #services
+        }
+      $self->quotation_pkg ;
+
+  $self->cust_main->order_pkgs( \%cust_pkg );
+
+}
+
 =back
 
 =head1 CLASS METHODS
diff --git a/httemplate/edit/prospect_main.html b/httemplate/edit/prospect_main.html
index d398541..da5c6ce 100644
--- a/httemplate/edit/prospect_main.html
+++ b/httemplate/edit/prospect_main.html
@@ -3,6 +3,7 @@
      'table'           => 'prospect_main',
      'labels'          => { 'prospectnum' => 'Prospect',
                             'agentnum'    => 'Agent',
+                            'refnum'      => 'Advertising source',
                             'company'     => 'Company',
                             'contactnum'  => 'Contact',
                             'locationnum' => ' ',
@@ -13,6 +14,11 @@
          'empty_label' => 'Select agent',
          'colspan'     => 6,
        },
+       { 'field'       => 'refnum',
+         'type'        => 'select-part_referral',
+         'empty_label' => 'Select advertising source',
+         'colspan'     => 6,
+       },
        { 'field'    => 'residential_commercial',
          'type'     => 'radio',
          'options'  => [ 'Residential', 'Commercial', ],
diff --git a/httemplate/search/prospect_main.html b/httemplate/search/prospect_main.html
index ab37b90..4798f58 100644
--- a/httemplate/search/prospect_main.html
+++ b/httemplate/search/prospect_main.html
@@ -23,6 +23,8 @@
                                   '', #link to contact edit???
                                 ],
              'agent_virt'    => 1,
+             'disableable'   => 1,
+             'disabled_statuspos' => 2,
 &>
 <%init>
 
diff --git a/httemplate/view/prospect_main.html b/httemplate/view/prospect_main.html
index 6c4595d..689b422 100644
--- a/httemplate/view/prospect_main.html
+++ b/httemplate/view/prospect_main.html
@@ -11,7 +11,11 @@
 
 <TR>
   <TD ALIGN="right">Prospect #</TD>
-  <TD BGCOLOR="#FFFFFF"><B><% $prospectnum %></B></TD>
+  <TD BGCOLOR="#FFFFFF"><B><% $prospectnum %></B>
+%   if ( $prospect_main->disabled ) {
+      <B>(DISABLED)</B>
+%   }
+  </TD>
 </TR>
 
 %unless ( scalar(@agentnums) == 1
@@ -19,7 +23,15 @@
 %  my $agent = qsearchs('agent',{ 'agentnum' => $prospect_main->agentnum } );
    <TR>
      <TD ALIGN="right">Agent</TD>
-     <TD BGCOLOR="#ffffff"><% $agent->agentnum %>: <% $agent->agent %></TD>
+     <TD BGCOLOR="#ffffff"><% $agent->agentnum %>: <% $agent->agent |h %></TD>
+   </TR>
+%}
+
+%unless ( ! $prospect_main->refnum ) { # || scalar(@part_referral) == 1 ) {
+%  my $part_referral = qsearchs('part_referral',{ 'refnum' => $prospect_main->refnum } );
+   <TR>
+     <TD ALIGN="right">Advertising source</TD>
+     <TD BGCOLOR="#ffffff"><% $part_referral->referral |h %></TD>
    </TR>
 %}
 
@@ -76,6 +88,9 @@
       <TR>
         <TH CLASS="grid" BGCOLOR="#cccccc">#</TH>
         <TH CLASS="grid" BGCOLOR="#cccccc"><% mt('Date') |h %></TH>
+        <TH CLASS="grid" BGCOLOR="#cccccc"><% mt('Setup') |h %></TH>
+        <TH CLASS="grid" BGCOLOR="#cccccc"><% mt('Recurring') |h %></TH>
+        <TH CLASS="grid" BGCOLOR="#cccccc"></TH>
       </TR>
 %     foreach my $quotation (@quotations) {
 %       if ( $bgcolor eq $bgcolor1 ) {
@@ -88,6 +103,9 @@
         <TR>
           <TD CLASS="grid" BGCOLOR="<% $bgcolor %>"><% $a %><% $quotation->quotationnum %></A></TD>
           <TD CLASS="grid" BGCOLOR="<% $bgcolor %>"><% $a %><% time2str($date_format, $quotation->_date) |h %></A></TD>
+          <TD CLASS="grid" BGCOLOR="<% $bgcolor %>"><% $a %><% $quotation->total_setup |h %></A></TD>
+          <TD CLASS="grid" BGCOLOR="<% $bgcolor %>"><% $a %><% $quotation->total_recur |h %></A></TD>
+          <TD CLASS="grid" BGCOLOR="<% $bgcolor %>"><A HREF="<%$p%>edit/process/quotation_convert.html?quotationnum=<% $quotation->quotationnum %>">Convert to customer</A></TD>
         </TR>
 %     }
     </TABLE>

commit aa59cc83ffa65da2fce9b5be42f483d9b17d91c0
Author: Ivan Kohler <ivan at freeside.biz>
Date:   Tue Sep 16 06:38:11 2014 -0700

    convert prospects to customers via quotations, RT#20688

diff --git a/FS/FS/Schema.pm b/FS/FS/Schema.pm
index 1828cba..3eedc5c 100644
--- a/FS/FS/Schema.pm
+++ b/FS/FS/Schema.pm
@@ -1300,10 +1300,11 @@ sub tables_hashref {
         'add_date',   @date_type,                  '', '', 
         'disabled',       'char', 'NULL',       1, '', '', 
         'custnum',         'int', 'NULL',      '', '', '',
+        'refnum',          'int', 'NULL',      '', '', '', 
       ],
       'primary_key' => 'prospectnum',
       'unique'      => [],
-      'index'       => [ [ 'company' ], [ 'agentnum' ], [ 'disabled' ] ],
+      'index'        => [ ['company'], ['agentnum'], ['disabled'], ['refnum'] ],
     },
 
     'quotation' => {
diff --git a/FS/FS/cust_main.pm b/FS/FS/cust_main.pm
index 43d8f0c..e1d3caa 100644
--- a/FS/FS/cust_main.pm
+++ b/FS/FS/cust_main.pm
@@ -402,11 +402,8 @@ sub insert {
 
   # insert locations
   foreach my $l (qw(bill_location ship_location)) {
-    my $loc = delete $self->hashref->{$l};
-    # XXX if we're moving a prospect's locations, do that here
-    if ( !$loc ) {
-      return "$l not set";
-    }
+
+    my $loc = delete $self->hashref->{$l} or return "$l not set";
     
     if ( !$loc->locationnum ) {
       # warn the location that we're going to insert it with no custnum
@@ -419,8 +416,19 @@ sub insert {
         my $label = $l eq 'ship_location' ? 'service' : 'billing';
         return "$error (in $label location)";
       }
-    }
-    elsif ( ($loc->custnum || 0) > 0 or $loc->prospectnum ) {
+
+    } elsif ( $loc->prospectnum ) {
+
+      $loc->prospectnum('');
+      $loc->set(custnum_pending => 1);
+      my $error = $loc->replace;
+      if ( $error ) {
+        $dbh->rollback if $oldAutoCommit;
+        my $label = $l eq 'ship_location' ? 'service' : 'billing';
+        return "$error (moving $label location)";
+      }
+
+    } elsif ( ($loc->custnum || 0) > 0 ) {
       # then it somehow belongs to another customer--shouldn't happen
       $dbh->rollback if $oldAutoCommit;
       return "$l belongs to customer ".$loc->custnum;

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

Summary of changes:
 FS/FS/Schema.pm                      |    3 +-
 FS/FS/cust_main.pm                   |   22 +++++++----
 FS/FS/prospect_main.pm               |   53 ++++++++++++++++++++++++-
 FS/FS/quotation.pm                   |   72 ++++++++++++++++++++++++++++++++++
 httemplate/edit/prospect_main.html   |    6 +++
 httemplate/search/prospect_main.html |    2 +
 httemplate/view/prospect_main.html   |   22 ++++++++++-
 7 files changed, 168 insertions(+), 12 deletions(-)




More information about the freeside-commits mailing list