X-Git-Url: http://wagnertech.de/git?a=blobdiff_plain;f=SL%2FIC.pm;h=e646fe05cf91c7f9deb4caaf4289121e5e96a264;hb=c19f41e1e0b92c7721963e0b40797b257bc88b3e;hp=44b21ec626148e70a6ba3224c1fb33cd78f07b77;hpb=e851ae005e79c4d8046d59be4191e241439e312a;p=kivitendo-erp.git diff --git a/SL/IC.pm b/SL/IC.pm index 44b21ec62..e646fe05c 100644 --- a/SL/IC.pm +++ b/SL/IC.pm @@ -38,6 +38,7 @@ use Data::Dumper; use List::MoreUtils qw(all); use YAML; +use SL::CVar; use SL::DBUtils; sub get_part { @@ -138,7 +139,7 @@ sub get_part { $form->{PRICEGROUPS} = selectall_hashref_query($form, $dbh, $query); #find not used pricegroups - while ($tmp = pop(@{ $form->{PRICEGROUPS} })) { + while (my $tmp = pop(@{ $form->{PRICEGROUPS} })) { my $in_use = 0; foreach my $item (@pricegroups) { if ($item eq $tmp->{id}) { @@ -152,7 +153,7 @@ sub get_part { # if not used pricegroups are avaible if (@pricegroups_not_used) { - foreach $name (@pricegroups_not_used) { + foreach my $name (@pricegroups_not_used) { $form->{"klass_$i"} = "$name->{id}"; $form->{"pricegroup_id_$i"} = "$name->{id}"; $form->{"pricegroup_$i"} = "$name->{pricegroup}"; @@ -169,7 +170,7 @@ sub get_part { if ($form->{makemodel}) { $query = qq|SELECT m.make, m.model FROM makemodel m | . qq|WHERE m.parts_id = ?|; - @values = ($form->{id}); + my @values = ($form->{id}); $sth = $dbh->prepare($query); $sth->execute(@values) || $form->dberror("$query (" . join(', ', @values) . ")"); @@ -201,7 +202,7 @@ sub get_part { FROM chart c, partstax pt WHERE (pt.chart_id = c.id) AND (pt.parts_id = ?)|; $sth = prepare_execute_query($form, $dbh, $query, conv_i($form->{id})); - while (($key) = $sth->fetchrow_array) { + while (my ($key) = $sth->fetchrow_array) { $form->{amount}{$key} = $key; } @@ -244,7 +245,7 @@ sub get_pricegroups { my $pricegroups = selectall_hashref_query($form, $dbh, $query); my $i = 1; - foreach $pg (@{ $pricegroups }) { + foreach my $pg (@{ $pricegroups }) { $form->{"klass_$i"} = "$pg->{id}"; $form->{"price_$i"} = $form->format_amount($myconfig, $form->{"price_$i"}, -2); $form->{"pricegroup_id_$i"} = "$pg->{id}"; @@ -364,7 +365,7 @@ sub save { my $partsgroup_id = 0; if ($form->{partsgroup}) { - ($partsgroup, $partsgroup_id) = split(/--/, $form->{partsgroup}); + (my $partsgroup, $partsgroup_id) = split(/--/, $form->{partsgroup}); } my ($subq_inventory, $subq_expense, $subq_income); @@ -455,7 +456,7 @@ sub save { do_query($form, $dbh, qq|DELETE FROM translation WHERE parts_id = ?|, conv_i($form->{id})); if ($form->{language_values} ne "") { - foreach $item (split(/---\+\+\+---/, $form->{language_values})) { + foreach my $item (split(/---\+\+\+---/, $form->{language_values})) { my ($language_id, $translation, $longdescription) = split(/--\+\+--/, $item); if ($translation ne "") { $query = qq|INSERT into translation (parts_id, language_id, translation, longdescription) @@ -471,22 +472,20 @@ sub save { # insert price records only if different to sellprice for my $i (1 .. $form->{price_rows}) { - if ($form->{"price_$i"} eq "0") { + my $price = $form->parse_amount($myconfig, $form->{"price_$i"}); + if ($price == 0) { $form->{"price_$i"} = $form->{sellprice}; } if ( - ( $form->{"price_$i"} + ( $price || $form->{"klass_$i"} || $form->{"pricegroup_id_$i"}) - and $form->{"price_$i"} != $form->{sellprice} + and $price != $form->{sellprice} ) { #$klass = $form->parse_amount($myconfig, $form->{"klass_$i"}); - $price = $form->parse_amount($myconfig, $form->{"price_$i"}); - $pricegroup_id = - $form->parse_amount($myconfig, $form->{"pricegroup_id_$i"}); $query = qq|INSERT INTO prices (parts_id, pricegroup_id, price) | . qq|VALUES(?, ?, ?)|; - @values = (conv_i($form->{id}), conv_i($pricegroup_id), $price); + @values = (conv_i($form->{id}), conv_i($form->{"pricegroup_id_$i"}), $price); do_query($form, $dbh, $query, @values); } } @@ -506,7 +505,7 @@ sub save { } # insert taxes - foreach $item (split(/ /, $form->{taxaccounts})) { + foreach my $item (split(/ /, $form->{taxaccounts})) { if ($form->{"IC_tax_$item"}) { $query = qq|INSERT INTO partstax (parts_id, chart_id) @@ -531,7 +530,7 @@ sub save { } } - @a = localtime; + my @a = localtime; $a[5] += 1900; $a[4]++; my $shippingdate = "$a[5]-$a[4]-$a[3]"; @@ -554,10 +553,10 @@ sub save { FROM chart c, tax t WHERE (c.id = t.chart_id) AND (t.taxkey IN (SELECT taxkey_id FROM chart where accno = ?)) ORDER BY c.accno|; - $stw = prepare_execute_query($form, $dbh, $query, $accno_id); + my $stw = prepare_execute_query($form, $dbh, $query, $accno_id); $form->{taxaccount} = ""; - while ($ptr = $stw->fetchrow_hashref(NAME_lc)) { + while (my $ptr = $stw->fetchrow_hashref(NAME_lc)) { $form->{taxaccount} .= "$ptr->{accno} "; if (!($form->{taxaccount2} =~ /\Q$ptr->{accno}\E/)) { $form->{"$ptr->{accno}_rate"} = $ptr->{rate}; @@ -567,6 +566,11 @@ sub save { } } + CVar->save_custom_variables('dbh' => $dbh, + 'module' => 'IC', + 'trans_id' => $form->{id}, + 'variables' => $form); + # commit my $rc = $dbh->commit; $dbh->disconnect; @@ -744,6 +748,7 @@ sub assembly_item { # not working: # onhand - as above, but masking the simple itemstatus results (doh!) # masking of onhand in bsooqr mode - ToDO: fixme +# warehouse onhand # # disabled sanity checks and changes: # - searchitems = assembly will no longer disable bought @@ -771,7 +776,7 @@ sub all_parts { my @all_columns = (@simple_filters, @makemodel_filters, @apoe_filters, qw(serialnumber)); my @simple_l_switches = (@all_columns, qw(listprice sellprice lastcost priceupdate weight unit bin rop image)); my @oe_flags = qw(bought sold onorder ordered rfq quoted); - my @qsooqr_flags = qw(invnumber ordnumber quonumber trans_id name module); + my @qsooqr_flags = qw(invnumber ordnumber quonumber trans_id name module qty); my @deliverydate_flags = qw(deliverydate); # my @other_flags = qw(onhand); # ToDO: implement these # my @inactive_flags = qw(l_subtotal short l_linetotal); @@ -799,6 +804,8 @@ sub all_parts { ); my @join_order = qw(partsgroup makemodel invoice_oi apoe cv pfac); my %joins_needed; + my %table_prefix; + my %renamed_columns; if (($form->{searchitems} eq 'assembly') && $form->{l_lastcost}) { @simple_l_switches = grep { $_ ne 'lastcost' } @simple_l_switches; @@ -809,6 +816,7 @@ sub all_parts { my @select_tokens = qw(id factor); my @where_tokens = qw(1=1); my @group_tokens = (); + my @bind_vars = (); # special case transdate if (grep { $form->{$_} } qw(transdatefrom transdateto)) { @@ -868,14 +876,18 @@ sub all_parts { my $sort_order = ($form->{revers} ? ' DESC' : ' ASC'); + my $order_clause = " ORDER BY $form->{sort} " . ($form->{revers} ? 'DESC' : 'ASC'); + # special case: sorting by partnumber # since partnumbers are expected to be prefixed integers, a special sorting is implemented sorting first lexically by prefix and then by suffix. # and yes, that expression is designed to hold that array of regexes only once, so the map is kinda messy, sorry about that. # ToDO: implement proper functional sorting - $form->{sort} = join ', ', map { push @select_tokens, $_; ($table_prefix{$_} = "substring(partnumber,'[") . $_ } qw|^[:digit:]]+') [:digit:]]+')::INTEGER| - if $form->{sort} eq 'partnumber'; + # Nette Idee von Sven, gibt aber Probleme wenn die Artikelnummern groesser als 32bit sind. Korrekt waere es, dass Sort-Natural-Modul zu nehmen + # Ich lass das mal hier drin, damit die Idee erhalten bleibt jb 28.5.2009 bug 1018 + #$form->{sort} = join ', ', map { push @select_tokens, $_; ($table_prefix{$_} = "substring(partnumber,'[") . $_ } qw|^[:digit:]]+') [:digit:]]+')::INTEGER| + # if $form->{sort} eq 'partnumber'; - my $order_clause = " ORDER BY $form->{sort} $sort_order"; + #my $order_clause = " ORDER BY $form->{sort} $sort_order"; my $limit_clause = " LIMIT 100" if $form->{top100}; @@ -886,6 +898,7 @@ sub all_parts { || $form->{quoted} || $form->{rfq}; my @bsooqr; + my @bsooqr_tokens = (); push @select_tokens, @qsooqr_flags if $bsooqr; push @select_tokens, @deliverydate_flags if $bsooqr && $form->{l_deliverydate}; push @select_tokens, $q_assembly_lastcost if ($form->{searchitems} eq 'assembly') && $form->{l_lastcost}; @@ -897,6 +910,9 @@ sub all_parts { push @bsooqr_tokens, q|module = 'oe' AND quotation AND cv = 'vendor'| if $form->{rfq}; push @where_tokens, join ' OR ', map { "($_)" } @bsooqr_tokens if $bsooqr; + $renamed_columns{onhand} = 'onhand_before_bsooqr'; + $renamed_columns{qty} = 'onhand'; + $joins_needed{partsgroup} = 1; $joins_needed{pfac} = 1; $joins_needed{makemodel} = 1 if grep { $form->{$_} || $form->{"l_$_"} } @makemodel_filters; @@ -942,7 +958,8 @@ sub all_parts { $table_prefix{$q_assembly_lastcost} = ' '; - my %renamed_columns = ( + %renamed_columns = ( + %renamed_columns, 'factor' => 'price_factor', 'SUM(ioi.qty)' => 'soldtotal', ); @@ -955,6 +972,15 @@ sub all_parts { my $where_clause = join ' AND ', map { "($_)" } @where_tokens; my $group_clause = ' GROUP BY ' . join ', ', map { ($table_prefix{$_} || "p.") . $_ } @group_tokens if scalar @group_tokens; + my ($cvar_where, @cvar_values) = CVar->build_filter_query('module' => 'IC', + 'trans_id_field' => 'p.id', + 'filter' => $form); + + if ($cvar_where) { + $where_clause .= qq| AND ($cvar_where)|; + push @bind_vars, @cvar_values; + } + my $query = qq|SELECT DISTINCT $select_clause FROM parts p $join_clause WHERE $where_clause $group_clause $order_clause $limit_clause|; $form->{parts} = selectall_hashref_query($form, $dbh, $query, @bind_vars); @@ -976,13 +1002,13 @@ sub all_parts { INNER JOIN assembly a ON (p.id = a.parts_id) $joins{pfac} WHERE a.id = ?|; - $sth = prepare_query($form, $dbh, $query); + my $sth = prepare_query($form, $dbh, $query); - foreach $item (@{ $form->{parts} }) { + foreach my $item (@{ $form->{parts} }) { push(@assemblies, $item); do_statement($form, $sth, $query, conv_i($item->{id})); - while ($ref = $sth->fetchrow_hashref(NAME_lc)) { + while (my $ref = $sth->fetchrow_hashref(NAME_lc)) { $ref->{assemblyitem} = 1; map { $ref->{$_} /= $ref->{factor} || 1 } qw(sellprice listprice lastcost); push(@assemblies, $ref); @@ -997,51 +1023,35 @@ sub all_parts { $main::lxdebug->leave_sub(); } -sub update_prices { +sub _create_filter_for_priceupdate { $main::lxdebug->enter_sub(); - my ($self, $myconfig, $form) = @_; + my $self = shift; + my $myconfig = \%main::myconfig; + my $form = $main::form; + my @where_values; my $where = '1 = 1'; - my $var; - my $group; - my $limit; + foreach my $item (qw(partnumber drawing microfiche make model pg.partsgroup)) { + my $column = $item; + $column =~ s/.*\.//; + next unless ($form->{$column}); - if ($item ne 'make') { - foreach my $item (qw(partnumber drawing microfiche make model pg.partsgroup)) { - my $column = $item; - $column =~ s/.*\.//; - next unless ($form->{$column}); - $where .= qq| AND $item ILIKE ?|; - push(@where_values, '%' . $form->{$column} . '%'); - } + $where .= qq| AND $item ILIKE ?|; + push(@where_values, '%' . $form->{$column} . '%'); } - # special case for description - if ($form->{description} - && !( $form->{bought} || $form->{sold} || $form->{onorder} - || $form->{ordered} || $form->{rfq} || $form->{quoted})) { - $where .= qq| AND (p.description ILIKE ?)|; - push(@where_values, '%' . $form->{description} . '%'); - } + foreach my $item (qw(description serialnumber)) { + next unless ($form->{$item}); - # special case for serialnumber - if ($form->{l_serialnumber} && $form->{serialnumber}) { - $where .= qq| AND serialnumber ILIKE ?|; - push(@where_values, '%' . $form->{serialnumber} . '%'); + $where .= qq| AND (${item} ILIKE ?)|; + push(@where_values, '%' . $form->{$item} . '%'); } # items which were never bought, sold or on an order if ($form->{itemstatus} eq 'orphaned') { - $form->{onhand} = $form->{short} = 0; - $form->{bought} = $form->{sold} = 0; - $form->{onorder} = $form->{ordered} = 0; - $form->{rfq} = $form->{quoted} = 0; - - $form->{transdatefrom} = $form->{transdateto} = ""; - $where .= qq| AND (p.onhand = 0) AND p.id NOT IN @@ -1052,31 +1062,93 @@ sub update_prices { UNION SELECT DISTINCT parts_id FROM orderitems )|; - } - if ($form->{itemstatus} eq 'active') { + } elsif ($form->{itemstatus} eq 'active') { $where .= qq| AND p.obsolete = '0'|; - } - if ($form->{itemstatus} eq 'obsolete') { + } elsif ($form->{itemstatus} eq 'obsolete') { $where .= qq| AND p.obsolete = '1'|; - $form->{onhand} = $form->{short} = 0; - } - if ($form->{itemstatus} eq 'onhand') { + } elsif ($form->{itemstatus} eq 'onhand') { $where .= qq| AND p.onhand > 0|; - } - if ($form->{itemstatus} eq 'short') { + } elsif ($form->{itemstatus} eq 'short') { $where .= qq| AND p.onhand < p.rop|; + } foreach my $column (qw(make model)) { - next unless ($form->{$colum}); + next unless ($form->{$column}); $where .= qq| AND p.id IN (SELECT DISTINCT parts_id FROM makemodel WHERE $column ILIKE ?|; push(@where_values, '%' . $form->{$column} . '%'); } + $main::lxdebug->leave_sub(); + + return ($where, @where_values); +} + +sub get_num_matches_for_priceupdate { + $main::lxdebug->enter_sub(); + + my $self = shift; + + my $myconfig = \%main::myconfig; + my $form = $main::form; + + my $dbh = $form->get_standard_dbh($myconfig); + + my ($where, @where_values) = $self->_create_filter_for_priceupdate(); + + my $num_updated = 0; + my $query; + + for my $column (qw(sellprice listprice)) { + next if ($form->{$column} eq ""); + + $query = + qq|SELECT COUNT(*) + FROM parts + WHERE id IN + (SELECT p.id + FROM parts p + LEFT JOIN partsgroup pg ON (p.partsgroup_id = pg.id) + WHERE $where)|; + my ($result) = selectfirst_array_query($form, $dbh, $query, @where_values); + $num_updated += $result if (0 <= $result); + } + + $query = + qq|SELECT COUNT(*) + FROM prices + WHERE parts_id IN + (SELECT p.id + FROM parts p + LEFT JOIN partsgroup pg ON (p.partsgroup_id = pg.id) + WHERE $where) AND (pricegroup_id = ?)|; + my $sth = prepare_query($form, $dbh, $query); + + for my $i (1 .. $form->{price_rows}) { + next if ($form->{"price_$i"} eq ""); + + my ($result) = do_statement($form, $sth, $query, @where_values, conv_i($form->{"pricegroup_id_$i"})); + $num_updated += $result if (0 <= $result); + } + $sth->finish(); + + $main::lxdebug->leave_sub(); + + return $num_updated; +} + +sub update_prices { + $main::lxdebug->enter_sub(); + + my ($self, $myconfig, $form) = @_; + + my ($where, @where_values) = $self->_create_filter_for_priceupdate(); + my $num_updated = 0; + # connect to database my $dbh = $form->dbconnect_noauto($myconfig); @@ -1091,14 +1163,15 @@ sub update_prices { $operator = '*'; } - $query = + my $query = qq|UPDATE parts SET $column = $column $operator ? WHERE id IN (SELECT p.id FROM parts p LEFT JOIN partsgroup pg ON (p.partsgroup_id = pg.id) WHERE $where)|; - do_query($from, $dbh, $query, $value, @where_values); + my $result = do_query($form, $dbh, $query, $value, @where_values); + $num_updated += $result if (0 <= $result); } my $q_add = @@ -1123,12 +1196,15 @@ sub update_prices { next if ($form->{"price_$i"} eq ""); my $value = $form->parse_amount($myconfig, $form->{"price_$i"}); + my $result; if ($form->{"pricegroup_type_$i"} eq "percent") { - do_statement($form, $sth_multiply, $q_multiply, ($value / 100) + 1, @where_values, conv_i($form->{"pricegroup_id_$i"})); + $result = do_statement($form, $sth_multiply, $q_multiply, ($value / 100) + 1, @where_values, conv_i($form->{"pricegroup_id_$i"})); } else { - do_statement($form, $sth_add, $q_add, $value, @where_values, conv_i($form->{"pricegroup_id_$i"})); + $result = do_statement($form, $sth_add, $q_add, $value, @where_values, conv_i($form->{"pricegroup_id_$i"})); } + + $num_updated += $result if (0 <= $result); } $sth_add->finish(); @@ -1139,7 +1215,7 @@ sub update_prices { $main::lxdebug->leave_sub(); - return $rc; + return $num_updated; } sub create_links { @@ -1151,6 +1227,7 @@ sub create_links { my $dbh = $form->dbconnect($myconfig); my @values = ('%' . $module . '%'); + my $query; if ($form->{id}) { $query = @@ -1287,6 +1364,7 @@ sub retrieve_languages { my @values; my $where; + my $query; if ($form->{language_values} ne "") { $query = @@ -1330,7 +1408,7 @@ sub follow_account_chain { while (1) { do_statement($form, $sth, $query, $accno_id); - $ref = $sth->fetchrow_hashref(); + my $ref = $sth->fetchrow_hashref(); last unless ($ref && $ref->{"is_valid"} && !grep({ $_ == $ref->{"new_chart_id"} } @visited_accno_ids)); $accno_id = $ref->{"new_chart_id"};