use SL::IC;
use SL::Helper::Flash qw(flash);
use SL::HTML::Util;
+use SL::Presenter::Part;
use SL::ReportGenerator;
#use SL::PE;
$form->{lastsort} = ""; # memory for which table was sort at last time
$form->{ndxs_counter} = 0; # counter for added entries to top100
- my %is_xyz = map { +"is_$_" => ($form->{searchitems} eq $_) } qw(part service assembly);
-
$form->{title} = (ucfirst $form->{searchitems}) . "s";
+ $form->{title} =~ s/ys$/ies/;
$form->{title} = $locale->text($form->{title});
- $form->{title} = $locale->text('Assemblies') if ($is_xyz{is_assembly});
$form->{CUSTOM_VARIABLES} = CVar->get_configs('module' => 'IC');
($form->{CUSTOM_VARIABLES_FILTER_CODE},
'include_prefix' => 'l_',
'include_value' => 'Y');
+ setup_ic_search_action_bar();
$form->header;
$form->get_lists('partsgroup' => 'ALL_PARTSGROUPS');
- print $form->parse_html_template('ic/search', { %is_xyz, });
-
- $lxdebug->leave_sub();
-} #end search()
-
-sub search_update_prices {
- $lxdebug->enter_sub();
-
- $auth->assert('part_service_assembly_edit');
-
- my $pricegroups = IC->get_pricegroups(\%myconfig, \%$form);
-
- $form->{title} = $locale->text('Update Prices');
-
- $form->header;
-
- print $form->parse_html_template('ic/search_update_prices', { PRICE_ROWS => $pricegroups });
+ print $form->parse_html_template('ic/search');
$lxdebug->leave_sub();
} #end search()
-sub confirm_price_update {
- $lxdebug->enter_sub();
-
- $auth->assert('part_service_assembly_edit');
-
- my @errors = ();
- my $value_found = undef;
-
- foreach my $idx (qw(sellprice listprice), (1..$form->{price_rows})) {
- my $name = $idx =~ m/\d/ ? $form->{"pricegroup_${idx}"} : $idx eq 'sellprice' ? $locale->text('Sell Price') : $locale->text('List Price');
- my $type = $idx =~ m/\d/ ? $form->{"pricegroup_type_${idx}"} : $form->{"${idx}_type"};
- my $value_idx = $idx =~ m/\d/ ? "price_${idx}" : $idx;
- my $value = $form->parse_amount(\%myconfig, $form->{$value_idx});
-
- if ((0 > $value) && ($type eq 'percent')) {
- push @errors, $locale->text('You cannot adjust the price for pricegroup "#1" by a negative percentage.', $name);
-
- } elsif (!$value && ($form->{$value_idx} ne '')) {
- push @errors, $locale->text('No valid number entered for pricegroup "#1".', $name);
-
- } elsif (0 < $value) {
- $value_found = 1;
- }
- }
-
- push @errors, $locale->text('No prices will be updated because no prices have been entered.') if (!$value_found);
-
- my $num_matches = IC->get_num_matches_for_priceupdate();
-
- $form->header();
-
- if (@errors) {
- $form->show_generic_error(join('<br>', @errors), 'back_button' => 1);
- }
-
- $form->{nextsub} = "update_prices";
-
- map { delete $form->{$_} } qw(action header);
-
- print $form->parse_html_template('ic/confirm_price_update', { HIDDENS => [ map { name => $_, value => $form->{$_} }, keys %$form ],
- num_matches => $num_matches });
-
- $lxdebug->leave_sub();
-}
-
-sub update_prices {
- $lxdebug->enter_sub();
-
- $auth->assert('part_service_assembly_edit');
-
- my $num_updated = IC->update_prices(\%myconfig, \%$form);
-
- if (-1 != $num_updated) {
- $form->redirect($locale->text('#1 prices were updated.', $num_updated));
- } else {
- $form->error($locale->text('Could not update prices!'));
- }
-
- $lxdebug->leave_sub();
-}
-
sub top100 {
$::lxdebug->enter_sub();
# searchitems=part revers=0 lastsort=''
#
# filter:
-# partnumber ean description partsgroup serialnumber make model drawing microfiche
+# partnumber ean description partsgroup classification serialnumber make model drawing microfiche
# transdatefrom transdateto
#
# radio:
my $cvar_configs = CVar->get_configs('module' => 'IC');
- my %titles = (
- '' => $locale->text('Articles'),
- part => $locale->text('Parts'),
- service => $locale->text('Services'),
- assembly => $locale->text('Assemblies'),
- assortment => $locale->text('Assortments'),
- );
-
- $form->{title} = $titles{$form->{searchitems}};
+ $form->{title} = $locale->text('Articles');
my %column_defs = (
- 'bin' => { 'text' => $locale->text('Bin'), },
'deliverydate' => { 'text' => $locale->text('deliverydate'), },
'description' => { 'text' => $locale->text('Part Description'), },
'notes' => { 'text' => $locale->text('Notes'), },
'insertdate' => { 'text' => $locale->text('Insert Date'), },
'invnumber' => { 'text' => $locale->text('Invoice Number'), },
'lastcost' => { 'text' => $locale->text('Last Cost'), },
+ 'assembly_lastcost' => { 'text' => $locale->text('Assembly Last Cost'), },
'linetotallastcost' => { 'text' => $locale->text('Extended'), },
'linetotallistprice' => { 'text' => $locale->text('Extended'), },
'linetotalsellprice' => { 'text' => $locale->text('Extended'), },
'microfiche' => { 'text' => $locale->text('Microfiche'), },
'name' => { 'text' => $locale->text('Name'), },
'onhand' => { 'text' => $locale->text('Stocked Qty'), },
+ 'assembly_qty' => { 'text' => $locale->text('Assembly Item Qty'), },
'ordnumber' => { 'text' => $locale->text('Order Number'), },
'partnumber' => { 'text' => $locale->text('Part Number'), },
'partsgroup' => { 'text' => $locale->text('Partsgroup'), },
- 'priceupdate' => { 'text' => $locale->text('Updated'), },
+ 'priceupdate' => { 'text' => $locale->text('Price updated'), },
'quonumber' => { 'text' => $locale->text('Quotation'), },
'rop' => { 'text' => $locale->text('ROP'), },
'sellprice' => { 'text' => $locale->text('Sell Price'), },
'serialnumber' => { 'text' => $locale->text('Serial Number'), },
'soldtotal' => { 'text' => $locale->text('Qty in Selected Records'), },
'name' => { 'text' => $locale->text('Name in Selected Records'), },
- 'transdate' => { 'text' => $locale->text('Transdate'), },
+ 'transdate' => { 'text' => $locale->text('Transdate Record'), },
'unit' => { 'text' => $locale->text('Unit'), },
'weight' => { 'text' => $locale->text('Weight'), },
'shop' => { 'text' => $locale->text('Shop article'), },
+ 'type_and_classific' => { 'text' => $locale->text('Type'), },
'projectnumber' => { 'text' => $locale->text('Project Number'), },
'projectdescription' => { 'text' => $locale->text('Project Description'), },
+ 'warehouse' => { 'text' => $locale->text('Default Warehouse'), },
+ 'bin' => { 'text' => $locale->text('Default Bin'), },
+ 'make' => { 'text' => $locale->text('Make'), },
+ 'model' => { 'text' => $locale->text('Model'), },
);
$revers = $form->{revers};
obsolete => $locale->text('Obsolete'),
orphaned => $locale->text('Orphaned'),
onhand => $locale->text('On Hand'),
+ assembly_qty => $locale->text('Assembly Item Qty'),
short => $locale->text('Short'),
onorder => $locale->text('On Order'),
ordered => $locale->text('Ordered'),
description => $locale->text('Part Description') . ": '$form->{description}'",
make => $locale->text('Make') . ": '$form->{make}'",
model => $locale->text('Model') . ": '$form->{model}'",
+ customername => $locale->text('Customer') . ": '$form->{customername}'",
+ customernumber=> $locale->text('Customer Part Number').": '$form->{customernumber}'",
drawing => $locale->text('Drawing') . ": '$form->{drawing}'",
microfiche => $locale->text('Microfiche') . ": '$form->{microfiche}'",
l_soldtotal => $locale->text('Qty in Selected Records'),
ean => $locale->text('EAN') . ": '$form->{ean}'",
insertdatefrom => $locale->text('Insert Date') . ": " . $locale->text('From') . " " . $locale->date(\%myconfig, $form->{insertdatefrom}, 1),
insertdateto => $locale->text('Insert Date') . ": " . $locale->text('To (time)') . " " . $locale->date(\%myconfig, $form->{insertdateto}, 1),
+ l_service => $locale->text('Services'),
+ l_assembly => $locale->text('Assemblies'),
+ l_part => $locale->text('Parts'),
);
my @itemstatus_keys = qw(active obsolete orphaned onhand short);
my @callback_keys = qw(onorder ordered rfq quoted bought sold partnumber partsgroup partsgroup_id serialnumber description make model
- drawing microfiche l_soldtotal l_deliverydate transdatefrom transdateto insertdatefrom insertdateto ean shop all);
+ drawing microfiche l_soldtotal l_deliverydate transdatefrom transdateto insertdatefrom insertdateto ean shop all
+ l_service l_assembly l_part);
# calculate dependencies
for (@itemstatus_keys, @callback_keys) {
$column_defs{sellprice}{text} = $locale->text('Price');
$form->{l_lastcost} = ""
}
+ $form->{l_assembly_lastcost} = "Y" if $form->{l_assembly} && $form->{l_lastcost};
if ($form->{description}) {
$description = $form->{description};
$form->{l_linetotallastcost} = $form->{searchitems} eq 'assembly' && !$form->{bom} ? "" : 'Y' if $form->{l_lastcost};
$form->{l_linetotallistprice} = "Y" if $form->{l_listprice};
}
+ $form->{"l_type_and_classific"} = "Y";
- if ($form->{searchitems} eq 'service') {
+ if ($form->{l_service} && !$form->{l_assembly} && !$form->{l_part}) {
- # remove bin, weight and rop from list
- map { $form->{"l_$_"} = "" } qw(bin weight rop);
+ # remove warehouse, bin, weight and rop from list
+ map { $form->{"l_$_"} = "" } qw(bin weight rop warehouse);
$form->{l_onhand} = "";
flash('warning', $::locale->text('Soldtotal does not make sense without any bsooqr options'));
}
+ if ($form->{l_soldtotal} && ($form->{l_warehouse} || $form->{l_bin})) {
+ delete $form->{"l_$_"} for qw(bin warehouse);
+ flash('warning', $::locale->text('Sorry, I am too stupid to figure out the default warehouse/bin and the sold qty. I drop the default warehouse/bin option.'));
+ }
if ($form->{l_name} && !$bsooqr_mode) {
delete $form->{l_name};
IC->all_parts(\%myconfig, \%$form);
my @columns = qw(
- partnumber description notes partsgroup bin onhand rop soldtotal unit listprice
- linetotallistprice sellprice linetotalsellprice lastcost linetotallastcost
+ partnumber type_and_classific description notes partsgroup warehouse bin
+ make model assembly_qty onhand rop soldtotal unit listprice
+ linetotallistprice sellprice linetotalsellprice lastcost assembly_lastcost linetotallastcost
priceupdate weight image drawing microfiche invnumber ordnumber quonumber
transdate name serialnumber deliverydate ean projectnumber projectdescription
insertdate shop
%column_defs = (%column_defs, %column_defs_cvars, %column_defs_pricegroups);
map { $column_defs{$_}->{visible} ||= $form->{"l_$_"} ? 1 : 0 } @columns;
- map { $column_defs{$_}->{align} = 'right' } qw(onhand sellprice listprice lastcost linetotalsellprice linetotallastcost linetotallistprice rop weight soldtotal shop), @pricegroup_columns;
+ map { $column_defs{$_}->{align} = 'right' } qw(assembly_qty onhand sellprice listprice lastcost assembly_lastcost linetotalsellprice linetotallastcost linetotallistprice rop weight soldtotal shop), @pricegroup_columns;
my @hidden_variables = (
qw(l_subtotal l_linetotal searchitems itemstatus bom l_pricegroups insertdatefrom insertdateto),
+ qw(l_type_and_classific classification_id l_part l_service l_assembly l_assortment),
@itemstatus_keys,
@callback_keys,
map({ "cvar_$_->{name}" } @searchable_custom_variables),
+ map({'cvar_'. $_->{name} .'_from'} grep({$_->{type} eq 'date'} @searchable_custom_variables)),
+ map({'cvar_'. $_->{name} .'_to'} grep({$_->{type} eq 'date'} @searchable_custom_variables)),
map({'cvar_'. $_->{name} .'_qtyop'} grep({$_->{type} eq 'number'} @searchable_custom_variables)),
map({ "l_$_" } @columns),
);
my $callback = build_std_url('action=generate_report', grep { $form->{$_} } @hidden_variables);
my @sort_full = qw(partnumber description onhand soldtotal deliverydate insertdate shop);
- my @sort_no_revers = qw(partsgroup bin priceupdate invnumber ordnumber quonumber name image drawing serialnumber);
+ my @sort_no_revers = qw(partsgroup invnumber ordnumber quonumber name image drawing serialnumber);
foreach my $col (@sort_full) {
$column_defs{$col}->{link} = join '&', $callback, "sort=$col", map { "$_=" . E($form->{$_}) } qw(revers lastsort);
'part' => $locale->text('part_list'),
'service' => $locale->text('service_list'),
'assembly' => $locale->text('assembly_list'),
+ 'article' => $locale->text('article_list'),
);
$report->set_options('raw_top_info_text' => $form->parse_html_template('ic/generate_report_top', { options => \@options }),
- 'raw_bottom_info_text' => $form->parse_html_template('ic/generate_report_bottom'),
+ 'raw_bottom_info_text' => $form->parse_html_template('ic/generate_report_bottom' ,
+ { PART_CLASSIFICATIONS => SL::DB::Manager::PartClassification->get_all_sorted }),
'output_format' => 'HTML',
'title' => $form->{title},
- 'attachment_basename' => $attachment_basenames{$form->{searchitems}} . strftime('_%Y%m%d', localtime time),
+ 'attachment_basename' => 'article_list' . strftime('_%Y%m%d', localtime time),
);
$report->set_options_from_form();
$locale->set_numberformat_wo_thousands_separator(\%myconfig) if lc($report->{options}->{output_format}) eq 'csv';
$ref->{sellprice} *= $ref->{exchangerate} / $ref->{price_factor};
$ref->{listprice} *= $ref->{exchangerate} / $ref->{price_factor};
$ref->{lastcost} *= $ref->{exchangerate} / $ref->{price_factor};
+ $ref->{assembly_lastcost} *= $ref->{exchangerate} / $ref->{price_factor};
# use this for assemblies
my $soldtotal = $bsooqr_mode ? $ref->{soldtotal} : $ref->{onhand};
$soldtotal = 0 if ($form->{sold});
}
- my $edit_link = build_std_url('script=controller.pl', 'action=Part/edit', 'part.id=' . E($ref->{id}), 'callback');
+ my $edit_link = build_std_url('script=controller.pl', 'action=Part/edit', 'part.id=' . E($ref->{id}));
$row->{partnumber}->{link} = $edit_link;
$row->{description}->{link} = $edit_link;
- foreach (qw(sellprice listprice lastcost)) {
+ foreach (qw(sellprice listprice lastcost assembly_lastcost)) {
$row->{$_}{data} = $form->format_amount(\%myconfig, $ref->{$_}, 2);
$row->{"linetotal$_"}{data} = $form->format_amount(\%myconfig, $ref->{onhand} * $ref->{$_}, 2);
}
# | ist bestellt | Von Kunden bestellt | -> edit_oe_ord_link
# | Anfrage | Angebot | -> edit_oe_quo_link
- my $edit_oe_ord_link = build_std_url("script=oe.pl", 'action=edit', 'type=' . E($ref->{cv} eq 'vendor' ? 'purchase_order' : 'sales_order'), 'id=' . E($ref->{trans_id}), 'callback');
- my $edit_oe_quo_link = build_std_url("script=oe.pl", 'action=edit', 'type=' . E($ref->{cv} eq 'vendor' ? 'request_quotation' : 'sales_quotation'), 'id=' . E($ref->{trans_id}), 'callback');
+ my $edit_oe_ord_link = ($::instance_conf->get_feature_experimental_order)
+ ? build_std_url("script=controller.pl", 'action=Order/edit',
+ 'type=' . E($ref->{cv} eq 'vendor' ? 'purchase_order' : 'sales_order'), 'id=' . E($ref->{trans_id}), 'callback')
+ : build_std_url("script=oe.pl", 'action=edit',
+ 'type=' . E($ref->{cv} eq 'vendor' ? 'purchase_order' : 'sales_order'), 'id=' . E($ref->{trans_id}), 'callback');
+
+ my $edit_oe_quo_link = ($::instance_conf->get_feature_experimental_order)
+ ? build_std_url("script=controller.pl", 'action=Order/edit',
+ 'type=' . E($ref->{cv} eq 'vendor' ? 'request_quotation' : 'sales_quotation'), 'id=' . E($ref->{trans_id}), 'callback')
+ : build_std_url("script=oe.pl", 'action=edit',
+ 'type=' . E($ref->{cv} eq 'vendor' ? 'request_quotation' : 'sales_quotation'), 'id=' . E($ref->{trans_id}), 'callback');
$row->{ordnumber}{link} = $edit_oe_ord_link;
$row->{quonumber}{link} = $edit_oe_quo_link if (!$ref->{ordnumber});
map { $row->{$_}{link} = $ref->{$_} } qw(drawing microfiche);
$row->{notes}{data} = SL::HTML::Util->strip($ref->{notes});
+ $row->{type_and_classific}{data} = SL::Presenter::Part::type_abbreviation($ref->{part_type}).
+ SL::Presenter::Part::classification_abbreviation($ref->{classification_id});
+
+ # last price update
+ $row->{priceupdate}{data} = SL::DB::Part->new(id => $ref->{id})->load->last_price_update->valid_from->to_kivitendo;
$report->add_data($row);
(!$next_ref->{assemblyitem} && ($same_item ne $next_ref->{ $form->{sort} })))) {
my $row = { map { $_ => { 'class' => 'listsubtotal', } } @columns };
- if (($form->{searchitems} ne 'assembly') || !$form->{bom}) {
+ if ( !$form->{l_assembly} || !$form->{bom}) {
$row->{soldtotal}->{data} = $form->format_amount(\%myconfig, $subtotals{soldtotal});
}
$report->add_data($row);
}
+ setup_ic_generate_report_action_bar();
$report->generate_with_headers();
$lxdebug->leave_sub();
} #end generate_report
-sub ajax_autocomplete {
- $main::lxdebug->enter_sub();
-
- my $form = $main::form;
- my %myconfig = %main::myconfig;
-
- $form->{column} = 'description' unless $form->{column} =~ /^partnumber|description$/;
- $form->{$form->{column}} = $form->{q} || '';
- $form->{limit} = ($form->{limit} * 1) || 10;
- $form->{searchitems} ||= '';
-
- my @results = IC->all_parts(\%myconfig, $form);
-
- print $form->ajax_response_header(),
- $form->parse_html_template('ic/ajax_autocomplete');
-
- $main::lxdebug->leave_sub();
-}
-
-sub back_to_record {
- _check_io_auth();
-
-
- delete @{$::form}{qw(action action_add action_back_to_record back_sub description item notes partnumber sellprice taxaccount2 unit vc)};
-
- $::auth->restore_form_from_session($::form->{previousform}, clobber => 1);
- $::form->{rowcount}--;
- $::form->{action} = 'display_form';
- $::form->{callback} = $::form->{script} . '?' . join('&', map { $::form->escape($_) . '=' . $::form->escape($::form->{$_}) } sort keys %{ $::form });
- $::form->redirect;
+sub setup_ic_search_action_bar {
+ my %params = @_;
+
+ for my $bar ($::request->layout->get('actionbar')) {
+ $bar->add(
+ action => [
+ t8('Search'),
+ submit => [ '#form', { action => 'generate_report' } ],
+ accesskey => 'enter',
+ ],
+
+ action => [
+ t8('TOP100'),
+ submit => [ '#form', { action => 'top100' } ],
+ ],
+ );
+ }
}
-sub continue { call_sub($form->{"nextsub"}); }
-
-sub dispatcher {
- my $action = first { $::form->{"action_${_}"} } qw(add back_to_record);
- $::form->error($::locale->text('No action defined.')) unless $action;
-
- $::form->{dispatched_action} = $action;
- call_sub($action);
+sub setup_ic_generate_report_action_bar {
+ my %params = @_;
+
+ for my $bar ($::request->layout->get('actionbar')) {
+ $bar->add(
+ combobox => [
+ action => [
+ t8('Add'),
+ ],
+ action => [
+ t8('Add Part'),
+ submit => [ '#new_form', { action => 'Part/add_part' } ],
+ accesskey => 'enter',
+ ],
+ action => [
+ t8('Add Service'),
+ submit => [ '#new_form', { action => 'Part/add_service' } ],
+ ],
+ action => [
+ t8('Add Assembly'),
+ submit => [ '#new_form', { action => 'Part/add_assembly' } ],
+ ],
+ action => [
+ t8('Add Assortment'),
+ submit => [ '#new_form', { action => 'Part/add_assortment' } ],
+ ],
+ ], # end of combobox "Add part"
+ );
+ }
}