use SL::CVar;
use SL::DB::Order;
use SL::DB::PeriodicInvoicesConfig;
+use SL::DB::Project;
+use SL::DB::ProjectType;
use SL::DB::Status;
use SL::DB::Tax;
use SL::DBUtils;
use SL::HTML::Restrict;
use SL::IC;
use SL::TransNumber;
+use SL::Util qw(trim);
+use Text::ParseWords;
use strict;
WHERE proi.projectnumber ILIKE ? AND oi.trans_id = o.id
))
SQL
- push @values, "%" . $form->{"projectnumber"} . "%", "%" . $form->{"projectnumber"} . "%" ;
+ push @values, like($form->{"projectnumber"}), like($form->{"projectnumber"});
}
if ($form->{"business_id"}) {
} elsif ($form->{$vc}) {
$query .= " AND ct.name ILIKE ?";
- push(@values, '%' . $form->{$vc} . '%');
+ push(@values, like($form->{$vc}));
}
if ($form->{"cp_name"}) {
$query .= " AND (cp.cp_name ILIKE ? OR cp.cp_givenname ILIKE ?)";
- push(@values, ('%' . $form->{"cp_name"} . '%')x2);
+ push(@values, (like($form->{"cp_name"}))x2);
}
if (!$main::auth->assert('sales_all_edit', 1)) {
if ($form->{$ordnumber}) {
$query .= qq| AND o.$ordnumber ILIKE ?|;
- push(@values, '%' . $form->{$ordnumber} . '%');
+ push(@values, like($form->{$ordnumber}));
}
if ($form->{cusordnumber}) {
$query .= qq| AND o.cusordnumber ILIKE ?|;
- push(@values, '%' . $form->{cusordnumber} . '%');
+ push(@values, like($form->{cusordnumber}));
}
if($form->{transdatefrom}) {
if ($form->{shippingpoint}) {
$query .= qq| AND o.shippingpoint ILIKE ?|;
- push(@values, '%' . $form->{shippingpoint} . '%');
+ push(@values, like($form->{shippingpoint}));
}
if ($form->{taxzone_id} ne '') { # taxzone_id could be 0
if ($form->{transaction_description}) {
$query .= qq| AND o.transaction_description ILIKE ?|;
- push(@values, '%' . $form->{transaction_description} . '%');
+ push(@values, like($form->{transaction_description}));
}
if ($form->{periodic_invoices_active} ne $form->{periodic_invoices_inactive}) {
if (($form->{order_probability_value} || '') ne '') {
my $op = $form->{order_probability_value} eq 'le' ? '<=' : '>=';
$query .= qq| AND (o.order_probability ${op} ?)|;
- push @values, $form->{order_probability_value};
+ push @values, trim($form->{order_probability_value});
}
if ($form->{expected_billing_date_from}) {
push @values, conv_date($form->{expected_billing_date_to});
}
+ if ($form->{parts_partnumber}) {
+ $query .= <<SQL;
+ AND EXISTS (
+ SELECT orderitems.trans_id
+ FROM orderitems
+ LEFT JOIN parts ON (orderitems.parts_id = parts.id)
+ WHERE (orderitems.trans_id = o.id)
+ AND (parts.partnumber ILIKE ?)
+ LIMIT 1
+ )
+SQL
+ push @values, like($form->{parts_partnumber});
+ }
+
+ if ($form->{parts_description}) {
+ $query .= <<SQL;
+ AND EXISTS (
+ SELECT orderitems.trans_id
+ FROM orderitems
+ WHERE (orderitems.trans_id = o.id)
+ AND (orderitems.description ILIKE ?)
+ LIMIT 1
+ )
+SQL
+ push @values, like($form->{parts_description});
+ }
+
+ if ($form->{all}) {
+ my @tokens = parse_line('\s+', 0, $form->{all});
+ # ordnumber quonumber customer.name vendor.name transaction_description
+ $query .= qq| AND (
+ o.ordnumber ILIKE ? OR
+ o.quonumber ILIKE ? OR
+ ct.name ILIKE ? OR
+ o.transaction_description ILIKE ?
+ )| for @tokens;
+ push @values, (like($_))x4 for @tokens;
+ }
+
my ($cvar_where, @cvar_values) = CVar->build_filter_query('module' => 'CT',
'trans_id_field' => 'ct.id',
'filter' => $form,
my $number_field = $form->{type} =~ m{order} ? 'ordnumber' : 'quonumber';
my $trans_number = SL::TransNumber->new(type => $form->{type}, dbh => $dbh, number => $form->{$number_field}, id => $form->{id});
- $form->{$number_field} ||= $trans_number->create_unique;
+ $form->{$number_field} ||= $trans_number->create_unique; # set $form->{ordnumber} or $form->{quonumber}
if ($form->{id}) {
+ $query = qq|DELETE FROM custom_variables
+ WHERE (config_id IN (SELECT id FROM custom_variable_configs WHERE (module = 'ShipTo')))
+ AND (trans_id IN (SELECT shipto_id FROM shipto WHERE (module = 'OE') AND (trans_id = ?)))|;
+ do_query($form, $dbh, $query, $form->{id});
+
$query = qq|DELETE FROM shipto | .
qq|WHERE trans_id = ? AND module = 'OE'|;
do_query($form, $dbh, $query, $form->{id});
$pricegroup_id *= 1;
$pricegroup_id = undef if !$pricegroup_id;
+ # force new project, if not set yet
+ if ($::instance_conf->get_order_always_project && !$form->{"globalproject_id"} && ($form->{type} eq 'sales_order')) {
+ require SL::DB::Customer;
+ my $customer = SL::DB::Manager::Customer->find_by(id => $form->{customer_id});
+ die "Can't find customer" unless $customer;
+ my $new_project = SL::DB::Project->new(
+ projectnumber => $form->{ordnumber},
+ description => $customer->name,
+ customer_id => $customer->id,
+ active => 1,
+ project_type_id => $::instance_conf->get_project_type_id,
+ project_status_id => $::instance_conf->get_project_status_id,
+ );
+ $new_project->save;
+ $form->{"globalproject_id"} = $new_project->id;
+ };
+
CVar->get_non_editable_ic_cvars(form => $form,
dbh => $dbh,
row => $i,
UPDATE orderitems SET
trans_id = ?, position = ?, parts_id = ?, description = ?, longdescription = ?, qty = ?, base_qty = ?,
sellprice = ?, discount = ?, unit = ?, reqdate = ?, project_id = ?, serialnumber = ?, ship = ?,
- pricegroup_id = ?, ordnumber = ?, transdate = ?, cusordnumber = ?, subtotal = ?,
+ pricegroup_id = ?, subtotal = ?,
marge_percent = ?, marge_total = ?, lastcost = ?, price_factor_id = ?,
active_price_source = ?, active_discount_source = ?,
price_factor = (SELECT factor FROM price_factors WHERE id = ?), marge_price_factor = ?
$form->{"qty_$i"}, $baseqty,
$fxsellprice, $form->{"discount_$i"},
$form->{"unit_$i"}, conv_date($reqdate), conv_i($form->{"project_id_$i"}),
- $form->{"serialnumber_$i"}, $form->{"ship_$i"}, $pricegroup_id,
- $form->{"ordnumber_$i"}, conv_date($form->{"transdate_$i"}),
- $form->{"cusordnumber_$i"}, $form->{"subtotal_$i"} ? 't' : 'f',
+ $form->{"serialnumber_$i"}, $form->{"ship_$i"},
+ $pricegroup_id, $form->{"subtotal_$i"} ? 't' : 'f',
$form->{"marge_percent_$i"}, $form->{"marge_absolut_$i"},
$form->{"lastcost_$i"}, conv_i($form->{"price_factor_id_$i"}),
$form->{"active_price_source_$i"}, $form->{"active_discount_source_$i"},
my $tax = 0;
map { $tax += $form->round_amount($taxaccounts{$_}, 2) } keys %taxaccounts;
- $amount = $form->round_amount($netamount + $tax, 2);
+ $amount = $form->round_amount($netamount + $tax, 2, 1);
$netamount = $form->round_amount($netamount, 2);
if ($form->{currency} eq $form->{defaultcurrency}) {
$exchangerate = $form->check_exchangerate($myconfig, $form->{currency}, $form->{transdate}, ($form->{vc} eq 'customer') ? 'buy' : 'sell');
}
- $form->{exchangerate} = $exchangerate || $form->parse_amount($myconfig, $form->{exchangerate});
+ # from inputfield (exchangerate) or hidden (forex)
+ my $exchangerate_from_form = $form->{forex} || $form->parse_amount($myconfig, $form->{exchangerate});
+
+ $form->{exchangerate} = $exchangerate || $exchangerate_from_form;
my $quotation = $form->{type} =~ /_order$/ ? 'f' : 't';
conv_i($form->{id}));
do_query($form, $dbh, $query, @values);
+ $form->new_lastmtime('oe');
+
$form->{ordtotal} = $amount;
$form->{name} = $form->{ $form->{vc} };
if ($config_obj) {
my $config = { map { $_ => $config_obj->$_ } qw(active terminated periodicity order_value_periodicity start_date_as_date end_date_as_date first_billing_date_as_date extend_automatically_by ar_chart_id
- print printer_id copies) };
+ print printer_id copies direct_debit send_email email_recipient_contact_id email_recipient_address email_sender email_subject email_body) };
$form->{periodic_invoices_config} = YAML::Dump($config);
}
}
# and remember for the rest of the function
my $is_collective_order = scalar @ids;
- $form->{useasnew} = !!$is_collective_order;
- if (!$form->{id}) {
- my $extra_days = $form->{type} eq 'sales_quotation' ? $::instance_conf->get_reqdate_interval : 1;
- my $next_workday = DateTime->today_local->add(days => $extra_days);
- my $day_of_week = $next_workday->day_of_week;
-
- $next_workday->add(days => (8 - $day_of_week)) if $day_of_week >= 6;
+ # If collective order was created from exactly 1 order, we assume the same
+ # behaviour as a "save as new" from within an order is actually desired, i.e.
+ # the original order isn't part of a workflow where we want to remember
+ # record_links, but simply a quick way of generating a new order from an old
+ # one without having to enter everything again.
+ # Setting useasnew will prevent the creation of record_links for the items
+ # when saving the new order.
+ # This form variable is probably not necessary, could just set saveasnew instead
+ $form->{useasnew} = 1 if $is_collective_order == 1;
+ if (!$form->{id}) {
+ my $extra_days = $form->{type} eq 'sales_quotation' ? $::instance_conf->get_reqdate_interval : 1;
+ $form->{reqdate} = DateTime->today_local->next_workday(extra_days => $extra_days)->to_kivitendo;
$form->{transdate} = DateTime->today_local->to_kivitendo;
- $form->{reqdate} = $next_workday->to_kivitendo;
}
# get default accounts
(SELECT c.accno FROM chart c WHERE d.income_accno_id = c.id) AS income_accno,
(SELECT c.accno FROM chart c WHERE d.expense_accno_id = c.id) AS expense_accno,
(SELECT c.accno FROM chart c WHERE d.fxgain_accno_id = c.id) AS fxgain_accno,
- (SELECT c.accno FROM chart c WHERE d.fxloss_accno_id = c.id) AS fxloss_accno
+ (SELECT c.accno FROM chart c WHERE d.fxloss_accno_id = c.id) AS fxloss_accno,
+ (SELECT c.accno FROM chart c WHERE d.rndgain_accno_id = c.id) AS rndgain_accno,
+ (SELECT c.accno FROM chart c WHERE d.rndloss_accno_id = c.id) AS rndloss_accno
$query_add
FROM defaults d|;
my $ref = selectfirst_hashref_query($form, $dbh, $query);
(SELECT cu.name FROM currencies cu WHERE cu.id=o.currency_id) AS currency, e.name AS employee, o.employee_id, o.salesman_id,
o.${vc}_id, cv.name AS ${vc}, o.amount AS invtotal,
o.closed, o.reqdate, o.quonumber, o.department_id, o.cusordnumber,
+ o.mtime, o.itime,
d.description AS department, o.payment_id, o.language_id, o.taxzone_id,
o.delivery_customer_id, o.delivery_vendor_id, o.proforma, o.shipto_id,
o.globalproject_id, o.delivered, o.transaction_description, o.delivery_term_id,
map { $form->{$_} = '' if ($ref->{$_} ne $form->{$_}) } keys %$ref;
}
}
+ $form->{mtime} ||= $form->{itime};
+ $form->{lastmtime} = $form->{mtime};
# if not given, fill transdate with current_date
$form->{transdate} = $form->current_date($myconfig)
map { $form->{$_} = $ref->{$_} } keys %$ref;
$sth->finish;
+ if ($form->{shipto_id}) {
+ my $cvars = CVar->get_custom_variables(
+ dbh => $dbh,
+ module => 'ShipTo',
+ trans_id => $form->{shipto_id},
+ );
+ $form->{"shiptocvar_$_->{name}"} = $_->{value} for @{ $cvars };
+ }
+
# get printed, emailed and queued
$query = qq|SELECT s.printed, s.emailed, s.spoolfile, s.formname FROM status s WHERE s.trans_id = ?|;
$sth = prepare_execute_query($form, $dbh, $query, $form->{id});
}
# delete orderitems_id in collective orders, so that they get cloned no matter what
+ # is this correct? or is the following meant?
+ # remember orderitems_ids in converted_from_orderitems_ids, so that they may be linked
$ref->{converted_from_orderitems_id} = delete $ref->{orderitems_id} if $is_collective_order;
# get tax rates and description
# format amounts
$form->{quototal} = $form->{ordtotal} = $form->format_amount($myconfig, $form->{ordtotal}, 2);
- if ($form->{type} =~ /_quotation/) {
- $form->set_payment_options($myconfig, $form->{quodate});
- } else {
- $form->set_payment_options($myconfig, $form->{orddate});
- }
+ $form->set_payment_options($myconfig, $form->{$form->{type} =~ /_quotation/ ? 'quodate' : 'orddate'}, $form->{type});
$form->{username} = $myconfig->{name};
$dbh->disconnect;
$form->{delivery_term} = SL::DB::Manager::DeliveryTerm->find_by(id => $form->{delivery_term_id} || undef);
- $form->{delivery_term}->description_long($form->{delivery_term}->translated_attribute('description_long', $form->{language_id})) if $form->{delivery_term} && $form->{language_id};
+ if ($form->{delivery_term} && $form->{language_id}) {
+ $form->{delivery_term}->description_long( $form->{delivery_term}->translated_attribute('description_long', $form->{language_id}));
+ $form->{delivery_term}->description_long_invoice($form->{delivery_term}->translated_attribute('description_long_invoice', $form->{language_id}));
+ }
- $::form->{order} = SL::DB::Manager::Order->find_by(id => $::form->{id});
+ $form->{order} = SL::DB::Manager::Order->find_by(id => $form->{id}) if $form->{id};
$main::lxdebug->leave_sub();
}