X-Git-Url: http://git.freeside.biz/gitweb/?p=freeside.git;a=blobdiff_plain;f=FS%2FFS%2Fpart_pkg_taxproduct.pm;h=51bc37f9c437d4eed03c9d52a2ba3ff8671aef29;hp=56e63b668716a31ed3ad6e66930f0906a49b17da;hb=7a33cb6e4c3e33b7399d6574cbd3ee38ddcba5e0;hpb=bc521ca75f4189ebd6d927aa263bdcce500150a5 diff --git a/FS/FS/part_pkg_taxproduct.pm b/FS/FS/part_pkg_taxproduct.pm index 56e63b668..51bc37f9c 100644 --- a/FS/FS/part_pkg_taxproduct.pm +++ b/FS/FS/part_pkg_taxproduct.pm @@ -2,7 +2,8 @@ package FS::part_pkg_taxproduct; use strict; use vars qw( @ISA $delete_kludge ); -use FS::Record qw( qsearch ); +use FS::Record qw( qsearch dbh ); +use Text::CSV_XS; @ISA = qw(FS::Record); $delete_kludge = 0; @@ -28,7 +29,7 @@ FS::part_pkg_taxproduct - Object methods for part_pkg_taxproduct records =head1 DESCRIPTION -An FS::part_pkg_taxproduct object represents a tax product. +An FS::part_pkg_taxproduct object represents a tax product. FS::part_pkg_taxproduct inherits from FS::Record. The following fields are currently supported: @@ -123,12 +124,157 @@ sub check { $self->SUPER::check; } +=item part_pkg_taxrate GEOCODE + +Returns the L records (tax definitions) that can apply +to this tax product category in the location identified by GEOCODE. + +=cut + +# actually only returns one arbitrary record for each taxclassnum, making +# it useful only for retrieving the taxclassnums + +sub part_pkg_taxrate { + my $self = shift; + my $data_vendor = $self->data_vendor; # because duh + my $geocode = shift; + + my $dbh = dbh; + + # CCH oddness in m2m + my $extra_sql .= "AND part_pkg_taxrate.data_vendor = '$data_vendor' ". + "AND (". + join(' OR ', map{ 'geocode = '. $dbh->quote(substr($geocode, 0, $_)) } + qw(10 5 2) + ). + ')'; + # much more CCH oddness in m2m -- this is kludgy + my $tpnums = join(',', + map { $_->taxproductnum } + $self->expand_cch_taxproduct + ); + + # if there are no taxproductnums, there are no matching tax classes + return if length($tpnums) == 0; + + $extra_sql .= " AND taxproductnum IN($tpnums)"; + + my $addl_from = 'LEFT JOIN part_pkg_taxproduct USING ( taxproductnum )'; + my $order_by = 'ORDER BY taxclassnum, length(geocode) desc, length(taxproduct) desc'; + my $select = 'DISTINCT ON(taxclassnum) *, taxproduct'; + + # should qsearch preface columns with the table to facilitate joins? + qsearch( { 'table' => 'part_pkg_taxrate', + 'select' => $select, + 'hashref' => { 'taxable' => 'Y' }, + 'addl_from' => $addl_from, + 'extra_sql' => $extra_sql, + 'order_by' => $order_by, + } ); +} + +=item expand_cch_taxproduct + +Returns the full set of part_pkg_taxproduct records that are "implied" by +this one. + +=cut + +sub expand_cch_taxproduct { + my $self = shift; + my $class = shift; + + my ($a,$b,$c,$d) = split ':', $self->taxproduct; + $a = '' unless $a; $b = '' unless $b; $c = '' unless $c; $d = '' unless $d; + my $taxproducts = join(',', + "'${a}:${b}:${c}:${d}'", + "'${a}:${b}:${c}:'", + "'${a}:${b}::${d}'", + "'${a}:${b}::'" + ); + qsearch( { + 'table' => 'part_pkg_taxproduct', + 'hashref' => { 'data_vendor'=>'cch' }, + 'extra_sql' => "AND taxproduct IN($taxproducts)", + } ); +} + + =back =cut +sub batch_import { + my ($param, $job) = @_; + + my $oldAutoCommit = $FS::UID::AutoCommit; + local $FS::UID::AutoCommit = 0; + my $dbh = dbh; + + my $fh = $param->{filehandle}; + my $format = $param->{format}; + die "unsupported part_pkg_taxproduct format '$format'" + unless $format eq 'billsoft'; + + # this is slightly silly + my @lines = <$fh>; + my $lines = scalar @lines; + seek($fh, 0, 0); + + my $imported = 0; + my $csv = Text::CSV_XS->new; + my $error; + # for importing the "transervdesc.txt" file + while ( my $row = $csv->getline($fh) ) { + if (!defined $row) { + $dbh->rollback if $oldAutoCommit; + return "can't parse: ". $csv->error_input(); + } + + if ( $job ) { + $job->update_statustext( + int( 100 * $imported / $lines ) . ',Inserting tax product records' + ); + } + + # columns 0-2: irrelevant here + my $taxproduct = $row->[3] . ':' . $row->[5]; + my $description = $row->[4]; + $description =~ s/\s+$//; + $description .= ':' . $row->[6]; + $description =~ s/\s+$//; + my $ppt = qsearchs('part_pkg_taxproduct', { + 'data_vendor' => 'billsoft', + 'taxproduct' => $taxproduct + }); + if ( $ppt ) { + $ppt->set('description', $description); + $ppt->set('note', $row->[7]); + $error = $ppt->replace; + } else { + $ppt = FS::part_pkg_taxproduct->new({ + 'data_vendor' => 'billsoft', + 'taxproduct' => $taxproduct, + 'description' => $description, + 'note' => $row->[7], + }); + $error = $ppt->insert; + } + if ( $error ) { + $dbh->rollback if $oldAutoCommit; + return "error inserting part_pkg_taxproduct $taxproduct: $error\n"; + } + $imported++; + } + + $dbh->commit if $oldAutoCommit; + return ''; +} + =head1 BUGS +Confusingly named. It has nothing to do with part_pkg. + =head1 SEE ALSO L, schema.html from the base documentation.