mirror of
https://github.com/opensourcepos/opensourcepos.git
synced 2026-01-02 06:27:50 -05:00
Optimizations and CSV Import Rework - Replaced " with ' where possible to prevent the parser from being called when not needed. - Replaced == and != with === and !== where possible for bug prevention and speed. - Replaced -1 with NEW_ITEM global constant for code clarity. - Added NEW_ITEM global constant to constants.php. - Refactored CSV import function names for clarity. - Added capability to import a CSV file containing updates. - Replaced array() with [] for speed and consistency. - Removed hungarian notation from two private functions. - Refactored QueryBuilder functions to place table name in the get() function call. - Replaced (int) cast with call to intval() for speed. - Replaced == and != with === and !== where possible to prevent bugs and for speed. - Replaced array() with [] for speed and consistency. - Fixed search_custom call Optimizations and bugfixes for attributes used in csv_import - Reordered where statements in queries to match composite index on attribute_links table. - fixed value_exists() to account for different attribute types. - Removed hungarian notation on private function. - Replaced array() with [] for speed and consistency. - Replaced != with <> in SQL for consistency. - Removed from() calls in querybuilder where possible to reduce function calls. - Add get_items_by_value() - Reworked check_data_validity() - Remove unneeded comments - Refactor functions for code clarity. - Use $this->db->dbprefix() where possible instead of hand-writing ospos_... - Removed unneeded column from query. - Replaced (int) cast with intval() call for speed. - Added get_attribute_values() - Fixed issue with date format locale not being used - Refactored save_value to respect different attribute_types - Added delete_orphaned_links() to remove attribute_links that are no longer linked to any items - Added get_attributes_by_definition() - Added attribute_cleanup() Optimizations used in csv_import - replaced array() with [] for consistency and speed. - Removed hungarian notation in private functions. - Replaced " with ' where possible to prevent the parser from being called. - Minor formatting - Refactored if statement to tertiary notation for cleaner implementation. - Replaced " for ' where possible to prevent the parser from being called. - Added the Id column in the generate_import_items_csv() template so that users can submit an update to an existing item. - Removed unused key=>value pairs in foreach loops for speed. - Removed unneeded comments where the function name was self-explanatory. - Rework get_csv_file() for speed. - Rework bom_exists() for speed. - Replaced array() with [] for speed and consistency. - Replaced == with === where possible to prevent bugs and for speed. - Reworked valid_date() and valid_decimal helper functions for speed and accuracy according to the locale_format instead of a fixed format. - Minor Reformatting for clarity. - Replaced " for ' to prevent the parser from being called. - Refactored function call names to reflect new names. - Added missing ; in - Used String interpolation where useful. - Spelling fix in comment Requested Review Changes - Fixed indentation in Items.php - Fixed indentation in Attribute.php - Refactored variable out of long line of code to make it more readable.
1228 lines
38 KiB
PHP
1228 lines
38 KiB
PHP
<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
|
|
|
|
require_once('Secure_Controller.php');
|
|
|
|
class Items extends Secure_Controller
|
|
{
|
|
public function __construct()
|
|
{
|
|
parent::__construct('items');
|
|
|
|
$this->load->library('item_lib');
|
|
}
|
|
|
|
public function index()
|
|
{
|
|
$this->session->set_userdata('allow_temp_items', 0);
|
|
|
|
$data['table_headers'] = $this->xss_clean(get_items_manage_table_headers());
|
|
$data['stock_location'] = $this->xss_clean($this->item_lib->get_item_location());
|
|
$data['stock_locations'] = $this->xss_clean($this->Stock_location->get_allowed_locations());
|
|
|
|
//Filters that will be loaded in the multiselect dropdown
|
|
$data['filters'] = array(
|
|
'empty_upc' => $this->lang->line('items_empty_upc_items'),
|
|
'low_inventory' => $this->lang->line('items_low_inventory_items'),
|
|
'is_serialized' => $this->lang->line('items_serialized_items'),
|
|
'no_description' => $this->lang->line('items_no_description_items'),
|
|
'search_custom' => $this->lang->line('items_search_attributes'),
|
|
'is_deleted' => $this->lang->line('items_is_deleted'),
|
|
'temporary' => $this->lang->line('items_temp'));
|
|
|
|
$this->load->view('items/manage', $data);
|
|
}
|
|
|
|
/*
|
|
* Returns Items table data rows. This will be called with AJAX.
|
|
*/
|
|
public function search()
|
|
{
|
|
$search = $this->input->get('search');
|
|
$limit = $this->input->get('limit');
|
|
$offset = $this->input->get('offset');
|
|
$sort = $this->input->get('sort');
|
|
$order = $this->input->get('order');
|
|
|
|
$this->item_lib->set_item_location($this->input->get('stock_location'));
|
|
|
|
$definition_names = $this->Attribute->get_definitions_by_flags(Attribute::SHOW_IN_ITEMS);
|
|
|
|
$filters = array(
|
|
'start_date' => $this->input->get('start_date'),
|
|
'end_date' => $this->input->get('end_date'),
|
|
'stock_location_id' => $this->item_lib->get_item_location(),
|
|
'empty_upc' => FALSE,
|
|
'low_inventory' => FALSE,
|
|
'is_serialized' => FALSE,
|
|
'no_description' => FALSE,
|
|
'search_custom' => FALSE,
|
|
'is_deleted' => FALSE,
|
|
'temporary' => FALSE,
|
|
'definition_ids' => array_keys($definition_names));
|
|
|
|
//Check if any filter is set in the multiselect dropdown
|
|
$filledup = array_fill_keys($this->input->get('filters'), TRUE);
|
|
$filters = array_merge($filters, $filledup);
|
|
$items = $this->Item->search($search, $filters, $limit, $offset, $sort, $order);
|
|
$total_rows = $this->Item->get_found_rows($search, $filters);
|
|
$data_rows = [];
|
|
|
|
foreach($items->result() as $item)
|
|
{
|
|
$data_rows[] = $this->xss_clean(get_item_data_row($item));
|
|
|
|
if($item->pic_filename !== NULL)
|
|
{
|
|
$this->update_pic_filename($item);
|
|
}
|
|
}
|
|
|
|
echo json_encode(array('total' => $total_rows, 'rows' => $data_rows));
|
|
}
|
|
|
|
public function pic_thumb($pic_filename)
|
|
{
|
|
$this->load->helper('file');
|
|
$this->load->library('image_lib');
|
|
|
|
$file_extension = pathinfo($pic_filename, PATHINFO_EXTENSION);
|
|
$images = glob('./uploads/item_pics/' . $pic_filename);
|
|
|
|
$base_path = './uploads/item_pics/' . pathinfo($pic_filename, PATHINFO_FILENAME);
|
|
|
|
if(sizeof($images) > 0)
|
|
{
|
|
$image_path = $images[0];
|
|
$thumb_path = $base_path . $this->image_lib->thumb_marker . '.' . $file_extension;
|
|
|
|
if(sizeof($images) < 2 && !file_exists($thumb_path))
|
|
{
|
|
$config['image_library'] = 'gd2';
|
|
$config['source_image'] = $image_path;
|
|
$config['maintain_ratio'] = TRUE;
|
|
$config['create_thumb'] = TRUE;
|
|
$config['width'] = 52;
|
|
$config['height'] = 32;
|
|
|
|
$this->image_lib->initialize($config);
|
|
$this->image_lib->resize();
|
|
|
|
$thumb_path = $this->image_lib->full_dst_path;
|
|
}
|
|
$this->output->set_content_type(get_mime_by_extension($thumb_path));
|
|
$this->output->set_output(file_get_contents($thumb_path));
|
|
}
|
|
}
|
|
|
|
/*
|
|
Gives search suggestions based on what is being searched for
|
|
*/
|
|
public function suggest_search()
|
|
{
|
|
$options = array(
|
|
'search_custom' => $this->input->post('search_custom'),
|
|
'is_deleted' => $this->input->post('is_deleted') !== NULL);
|
|
$suggestions = $this->xss_clean($this->Item->get_search_suggestions($this->input->post_get('term'), $options, FALSE));
|
|
|
|
echo json_encode($suggestions);
|
|
}
|
|
|
|
public function suggest()
|
|
{
|
|
$suggestions = $this->xss_clean($this->Item->get_search_suggestions($this->input->post_get('term'),
|
|
array('search_custom' => FALSE, 'is_deleted' => FALSE), TRUE));
|
|
|
|
echo json_encode($suggestions);
|
|
}
|
|
|
|
public function suggest_low_sell()
|
|
{
|
|
$suggestions = $this->xss_clean($this->Item->get_low_sell_suggestions($this->input->post_get('name')));
|
|
|
|
echo json_encode($suggestions);
|
|
}
|
|
|
|
public function suggest_kits()
|
|
{
|
|
$suggestions = $this->xss_clean($this->Item->get_kit_search_suggestions($this->input->post_get('term'),
|
|
array('search_custom' => FALSE, 'is_deleted' => FALSE), TRUE));
|
|
|
|
echo json_encode($suggestions);
|
|
}
|
|
|
|
/*
|
|
Gives search suggestions based on what is being searched for
|
|
*/
|
|
public function suggest_category()
|
|
{
|
|
$suggestions = $this->xss_clean($this->Item->get_category_suggestions($this->input->get('term')));
|
|
|
|
echo json_encode($suggestions);
|
|
}
|
|
|
|
/*
|
|
Gives search suggestions based on what is being searched for
|
|
*/
|
|
public function suggest_location()
|
|
{
|
|
$suggestions = $this->xss_clean($this->Item->get_location_suggestions($this->input->get('term')));
|
|
|
|
echo json_encode($suggestions);
|
|
}
|
|
|
|
public function get_row($item_ids)
|
|
{
|
|
$item_infos = $this->Item->get_multiple_info(explode(':', $item_ids), $this->item_lib->get_item_location());
|
|
|
|
$result = [];
|
|
|
|
foreach($item_infos->result() as $item_info)
|
|
{
|
|
$result[$item_info->item_id] = $this->xss_clean(get_item_data_row($item_info));
|
|
}
|
|
|
|
echo json_encode($result);
|
|
}
|
|
|
|
public function view($item_id = NEW_ITEM)
|
|
{
|
|
if($item_id === NEW_ITEM)
|
|
{
|
|
$data = [];
|
|
}
|
|
|
|
//allow_temp_items is set in the index function of items.php or sales.php
|
|
$data['allow_temp_item'] = $this->session->userdata('allow_temp_items');
|
|
$data['item_tax_info'] = $this->xss_clean($this->Item_taxes->get_info($item_id));
|
|
$data['default_tax_1_rate'] = '';
|
|
$data['default_tax_2_rate'] = '';
|
|
$data['item_kit_disabled'] = !$this->Employee->has_grant('item_kits', $this->Employee->get_logged_in_employee_info()->person_id);
|
|
$data['definition_values'] = $this->Attribute->get_attributes_by_item($item_id);
|
|
$data['definition_names'] = $this->Attribute->get_definition_names();
|
|
|
|
foreach($data['definition_values'] as $definition_id => $definition)
|
|
{
|
|
unset($data['definition_names'][$definition_id]);
|
|
}
|
|
|
|
$item_info = $this->Item->get_info($item_id);
|
|
|
|
foreach(get_object_vars($item_info) as $property => $value)
|
|
{
|
|
$item_info->$property = $this->xss_clean($value);
|
|
}
|
|
|
|
if($data['allow_temp_item'] === 1)
|
|
{
|
|
if($item_id !== NEW_ITEM)
|
|
{
|
|
if($item_info->item_type != ITEM_TEMP)
|
|
{
|
|
$data['allow_temp_item'] = 0;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if($item_info->item_type == ITEM_TEMP)
|
|
{
|
|
$data['allow_temp_item'] = 1;
|
|
}
|
|
}
|
|
|
|
$use_destination_based_tax = (boolean)$this->config->item('use_destination_based_tax');
|
|
$data['include_hsn'] = $this->config->item('include_hsn') === '1';
|
|
$data['category_dropdown'] = $this->config->item('category_dropdown');
|
|
|
|
if($data['category_dropdown'] === '1')
|
|
{
|
|
$categories = array('' => $this->lang->line('items_none'));
|
|
$category_options = $this->Attribute->get_definition_values(CATEGORY_DEFINITION_ID);
|
|
$category_options = array_combine($category_options,$category_options); //Overwrite indexes with values for saving in items table instead of attributes
|
|
$data['categories'] = array_merge($categories,$category_options);
|
|
|
|
$data['selected_category'] = $item_info->category;
|
|
}
|
|
|
|
if($item_id === NEW_ITEM)
|
|
{
|
|
$data['default_tax_1_rate'] = $this->config->item('default_tax_1_rate');
|
|
$data['default_tax_2_rate'] = $this->config->item('default_tax_2_rate');
|
|
|
|
$item_info->receiving_quantity = 1;
|
|
$item_info->reorder_level = 1;
|
|
$item_info->item_type = ITEM; //Standard
|
|
$item_info->item_id = $item_id;
|
|
$item_info->stock_type = HAS_STOCK;
|
|
$item_info->tax_category_id = NULL;
|
|
$item_info->qty_per_pack = 1;
|
|
$item_info->pack_name = $this->lang->line('items_default_pack_name');
|
|
$data['hsn_code'] = '';
|
|
|
|
if($use_destination_based_tax)
|
|
{
|
|
$item_info->tax_category_id = $this->config->item('default_tax_category');
|
|
}
|
|
}
|
|
|
|
$data['standard_item_locked'] = (
|
|
$data['item_kit_disabled']
|
|
&& $item_info->item_type == ITEM_KIT
|
|
&& !$data['allow_temp_item']
|
|
&& !($this->config->item('derive_sale_quantity') === '1'));
|
|
|
|
$data['item_info'] = $item_info;
|
|
|
|
$suppliers = array('' => $this->lang->line('items_none'));
|
|
|
|
foreach($this->Supplier->get_all()->result_array() as $row)
|
|
{
|
|
$suppliers[$this->xss_clean($row['person_id'])] = $this->xss_clean($row['company_name']);
|
|
}
|
|
|
|
$data['suppliers'] = $suppliers;
|
|
$data['selected_supplier'] = $item_info->supplier_id;
|
|
|
|
if($data['include_hsn'])
|
|
{
|
|
$data['hsn_code'] = $item_info->hsn_code;
|
|
}
|
|
else
|
|
{
|
|
$data['hsn_code'] = '';
|
|
}
|
|
|
|
if($use_destination_based_tax)
|
|
{
|
|
$data['use_destination_based_tax'] = TRUE;
|
|
$tax_categories = [];
|
|
|
|
foreach($this->Tax_category->get_all()->result_array() as $row)
|
|
{
|
|
$tax_categories[$this->xss_clean($row['tax_category_id'])] = $this->xss_clean($row['tax_category']);
|
|
}
|
|
|
|
$tax_category = '';
|
|
|
|
if ($item_info->tax_category_id !== NULL)
|
|
{
|
|
$tax_category_info=$this->Tax_category->get_info($item_info->tax_category_id);
|
|
$tax_category= $tax_category_info->tax_category;
|
|
}
|
|
|
|
$data['tax_categories'] = $tax_categories;
|
|
$data['tax_category'] = $tax_category;
|
|
$data['tax_category_id'] = $item_info->tax_category_id;
|
|
}
|
|
else
|
|
{
|
|
$data['use_destination_based_tax'] = FALSE;
|
|
$data['tax_categories'] = [];
|
|
$data['tax_category'] = '';
|
|
}
|
|
|
|
$data['logo_exists'] = $item_info->pic_filename !== '';
|
|
$file_extension = pathinfo($item_info->pic_filename, PATHINFO_EXTENSION);
|
|
|
|
if(empty($file_extension))
|
|
{
|
|
$images = glob("./uploads/item_pics/$item_info->pic_filename.*");
|
|
}
|
|
else
|
|
{
|
|
$images = glob("./uploads/item_pics/$item_info->pic_filename");
|
|
}
|
|
|
|
$data['image_path'] = sizeof($images) > 0 ? base_url($images[0]) : '';
|
|
$stock_locations = $this->Stock_location->get_undeleted_all()->result_array();
|
|
|
|
foreach($stock_locations as $location)
|
|
{
|
|
$location = $this->xss_clean($location);
|
|
|
|
$quantity = $this->xss_clean($this->Item_quantity->get_item_quantity($item_id, $location['location_id'])->quantity);
|
|
$quantity = ($item_id === NEW_ITEM) ? 0 : $quantity;
|
|
$location_array[$location['location_id']] = array('location_name' => $location['location_name'], 'quantity' => $quantity);
|
|
$data['stock_locations'] = $location_array;
|
|
}
|
|
|
|
$data['selected_low_sell_item_id'] = $item_info->low_sell_item_id;
|
|
|
|
if($item_id !== NEW_ITEM && $item_info->item_id !== $item_info->low_sell_item_id)
|
|
{
|
|
$low_sell_item_info = $this->Item->get_info($item_info->low_sell_item_id);
|
|
$data['selected_low_sell_item'] = implode(NAME_SEPARATOR, array($low_sell_item_info->name, $low_sell_item_info->pack_name));
|
|
}
|
|
else
|
|
{
|
|
$data['selected_low_sell_item'] = '';
|
|
}
|
|
|
|
$this->load->view('items/form', $data);
|
|
}
|
|
|
|
public function inventory($item_id = NEW_ITEM)
|
|
{
|
|
$item_info = $this->Item->get_info($item_id);
|
|
|
|
foreach(get_object_vars($item_info) as $property => $value)
|
|
{
|
|
$item_info->$property = $this->xss_clean($value);
|
|
}
|
|
|
|
$data['item_info'] = $item_info;
|
|
$data['stock_locations'] = [];
|
|
$stock_locations = $this->Stock_location->get_undeleted_all()->result_array();
|
|
|
|
foreach($stock_locations as $location)
|
|
{
|
|
$location = $this->xss_clean($location);
|
|
$quantity = $this->xss_clean($this->Item_quantity->get_item_quantity($item_id, $location['location_id'])->quantity);
|
|
|
|
$data['stock_locations'][$location['location_id']] = $location['location_name'];
|
|
$data['item_quantities'][$location['location_id']] = $quantity;
|
|
}
|
|
|
|
$this->load->view('items/form_inventory', $data);
|
|
}
|
|
|
|
public function count_details($item_id = NEW_ITEM)
|
|
{
|
|
$item_info = $this->Item->get_info($item_id);
|
|
|
|
foreach(get_object_vars($item_info) as $property => $value)
|
|
{
|
|
$item_info->$property = $this->xss_clean($value);
|
|
}
|
|
|
|
$data['item_info'] = $item_info;
|
|
$data['stock_locations'] = [];
|
|
$stock_locations = $this->Stock_location->get_undeleted_all()->result_array();
|
|
|
|
foreach($stock_locations as $location)
|
|
{
|
|
$location = $this->xss_clean($location);
|
|
$quantity = $this->xss_clean($this->Item_quantity->get_item_quantity($item_id, $location['location_id'])->quantity);
|
|
|
|
$data['stock_locations'][$location['location_id']] = $location['location_name'];
|
|
$data['item_quantities'][$location['location_id']] = $quantity;
|
|
}
|
|
|
|
$this->load->view('items/form_count_details', $data);
|
|
}
|
|
|
|
public function generate_barcodes($item_ids)
|
|
{
|
|
$this->load->library('barcode_lib');
|
|
|
|
$item_ids = explode(':', $item_ids);
|
|
$result = $this->Item->get_multiple_info($item_ids, $this->item_lib->get_item_location())->result_array();
|
|
$config = $this->barcode_lib->get_barcode_config();
|
|
|
|
$data['barcode_config'] = $config;
|
|
|
|
foreach($result as &$item)
|
|
{
|
|
$item = $this->xss_clean($item);
|
|
|
|
if(empty($item['item_number']) && $this->config->item('barcode_generate_if_empty'))
|
|
{
|
|
$barcode_instance = Barcode_lib::barcode_instance($item, $config);
|
|
$item['item_number'] = $barcode_instance->getData();
|
|
$save_item = array('item_number' => $item['item_number']);
|
|
|
|
$this->Item->save($save_item, $item['item_id']);
|
|
}
|
|
}
|
|
$data['items'] = $result;
|
|
|
|
$this->load->view('barcodes/barcode_sheet', $data);
|
|
}
|
|
|
|
public function attributes($item_id = NEW_ITEM)
|
|
{
|
|
$data['item_id'] = $item_id;
|
|
$definition_ids = json_decode($this->input->post('definition_ids'), TRUE);
|
|
$data['definition_values'] = $this->Attribute->get_attributes_by_item($item_id) + $this->Attribute->get_values_by_definitions($definition_ids);
|
|
$data['definition_names'] = $this->Attribute->get_definition_names();
|
|
|
|
foreach($data['definition_values'] as $definition_id => $definition_value)
|
|
{
|
|
$attribute_value = $this->Attribute->get_attribute_value($item_id, $definition_id);
|
|
$attribute_id = (empty($attribute_value) || empty($attribute_value->attribute_id)) ? NULL : $attribute_value->attribute_id;
|
|
$values = &$data['definition_values'][$definition_id];
|
|
$values['attribute_id'] = $attribute_id;
|
|
$values['attribute_value'] = $attribute_value;
|
|
$values['selected_value'] = '';
|
|
|
|
if ($definition_value['definition_type'] === DROPDOWN)
|
|
{
|
|
$values['values'] = $this->Attribute->get_definition_values($definition_id);
|
|
$link_value = $this->Attribute->get_link_value($item_id, $definition_id);
|
|
$values['selected_value'] = (empty($link_value)) ? '' : $link_value->attribute_id;
|
|
}
|
|
|
|
if (!empty($definition_ids[$definition_id]))
|
|
{
|
|
$values['selected_value'] = $definition_ids[$definition_id];
|
|
}
|
|
|
|
unset($data['definition_names'][$definition_id]);
|
|
}
|
|
|
|
$this->load->view('attributes/item', $data);
|
|
}
|
|
|
|
public function bulk_edit()
|
|
{
|
|
$suppliers = array('' => $this->lang->line('items_none'));
|
|
|
|
foreach($this->Supplier->get_all()->result_array() as $row)
|
|
{
|
|
$row = $this->xss_clean($row);
|
|
$suppliers[$row['person_id']] = $row['company_name'];
|
|
}
|
|
|
|
$data['suppliers'] = $suppliers;
|
|
$data['allow_alt_description_choices'] = array(
|
|
'' => $this->lang->line('items_do_nothing'),
|
|
1 => $this->lang->line('items_change_all_to_allow_alt_desc'),
|
|
0 => $this->lang->line('items_change_all_to_not_allow_allow_desc'));
|
|
|
|
$data['serialization_choices'] = array(
|
|
'' => $this->lang->line('items_do_nothing'),
|
|
1 => $this->lang->line('items_change_all_to_serialized'),
|
|
0 => $this->lang->line('items_change_all_to_unserialized'));
|
|
|
|
$this->load->view('items/form_bulk', $data);
|
|
}
|
|
|
|
public function save($item_id = NEW_ITEM)
|
|
{
|
|
$upload_success = $this->handle_image_upload();
|
|
$upload_data = $this->upload->data();
|
|
$receiving_quantity = parse_quantity($this->input->post('receiving_quantity'));
|
|
$item_type = $this->input->post('item_type') === NULL ? ITEM : $this->input->post('item_type');
|
|
|
|
if($receiving_quantity === 0 && $item_type !== ITEM_TEMP)
|
|
{
|
|
$receiving_quantity = 1;
|
|
}
|
|
|
|
$default_pack_name = $this->lang->line('items_default_pack_name');
|
|
|
|
//Save item data
|
|
$item_data = array(
|
|
'name' => $this->input->post('name'),
|
|
'description' => $this->input->post('description'),
|
|
'category' => $this->input->post('category'),
|
|
'item_type' => $item_type,
|
|
'stock_type' => $this->input->post('stock_type') === NULL ? HAS_STOCK : intval($this->input->post('stock_type')),
|
|
'supplier_id' => empty($this->input->post('supplier_id')) ? NULL : intval($this->input->post('supplier_id')),
|
|
'item_number' => empty($this->input->post('item_number')) ? NULL : $this->input->post('item_number'),
|
|
'cost_price' => parse_decimals($this->input->post('cost_price')),
|
|
'unit_price' => parse_decimals($this->input->post('unit_price')),
|
|
'reorder_level' => parse_quantity($this->input->post('reorder_level')),
|
|
'receiving_quantity' => $receiving_quantity,
|
|
'allow_alt_description' => $this->input->post('allow_alt_description') !== NULL,
|
|
'is_serialized' => $this->input->post('is_serialized') !== NULL,
|
|
'qty_per_pack' => $this->input->post('qty_per_pack') === NULL ? 1 : $this->input->post('qty_per_pack'),
|
|
'pack_name' => $this->input->post('pack_name') === NULL ? $default_pack_name : $this->input->post('pack_name'),
|
|
'low_sell_item_id' => $this->input->post('low_sell_item_id') === NULL ? $item_id : $this->input->post('low_sell_item_id'),
|
|
'deleted' => $this->input->post('is_deleted') !== NULL,
|
|
'hsn_code' => $this->input->post('hsn_code') === NULL ? '' : $this->input->post('hsn_code')
|
|
);
|
|
|
|
if($item_data['item_type'] == ITEM_TEMP)
|
|
{
|
|
$item_data['stock_type'] = HAS_NO_STOCK;
|
|
$item_data['receiving_quantity'] = 0;
|
|
$item_data['reorder_level'] = 0;
|
|
}
|
|
|
|
$tax_category_id = $this->input->post('tax_category_id');
|
|
|
|
if(!isset($tax_category_id))
|
|
{
|
|
$item_data['tax_category_id'] = '';
|
|
}
|
|
else
|
|
{
|
|
$item_data['tax_category_id'] = empty($this->input->post('tax_category_id')) ? NULL : $this->input->post('tax_category_id');
|
|
}
|
|
|
|
if(!empty($upload_data['orig_name']))
|
|
{
|
|
if($this->xss_clean($upload_data['orig_name'], TRUE) === TRUE)
|
|
{
|
|
$item_data['pic_filename'] = $upload_data['orig_name'];
|
|
}
|
|
}
|
|
|
|
$employee_id = $this->Employee->get_logged_in_employee_info()->person_id;
|
|
|
|
if($this->Item->save($item_data, $item_id))
|
|
{
|
|
$success = TRUE;
|
|
$new_item = FALSE;
|
|
|
|
if($item_id === NEW_ITEM)
|
|
{
|
|
$item_id = $item_data['item_id'];
|
|
$new_item = TRUE;
|
|
}
|
|
|
|
$use_destination_based_tax = (boolean)$this->config->item('use_destination_based_tax');
|
|
|
|
if(!$use_destination_based_tax)
|
|
{
|
|
$items_taxes_data = [];
|
|
$tax_names = $this->input->post('tax_names');
|
|
$tax_percents = $this->input->post('tax_percents');
|
|
|
|
$tax_name_index = 0;
|
|
|
|
foreach($tax_percents as $tax_percent)
|
|
{
|
|
$tax_percentage = parse_tax($tax_percent);
|
|
|
|
if(is_numeric($tax_percentage))
|
|
{
|
|
$items_taxes_data[] = array('name' => $tax_names[$tax_name_index], 'percent' => $tax_percentage);
|
|
}
|
|
|
|
$tax_name_index++;
|
|
}
|
|
$success &= $this->Item_taxes->save($items_taxes_data, $item_id);
|
|
}
|
|
|
|
//Save item quantity
|
|
$stock_locations = $this->Stock_location->get_undeleted_all()->result_array();
|
|
foreach($stock_locations as $location)
|
|
{
|
|
$updated_quantity = parse_quantity($this->input->post('quantity_' . $location['location_id']));
|
|
|
|
if($item_data['item_type'] == ITEM_TEMP)
|
|
{
|
|
$updated_quantity = 0;
|
|
}
|
|
|
|
$location_detail = array(
|
|
'item_id' => $item_id,
|
|
'location_id' => $location['location_id'],
|
|
'quantity' => $updated_quantity);
|
|
|
|
$item_quantity = $this->Item_quantity->get_item_quantity($item_id, $location['location_id']);
|
|
|
|
if($item_quantity->quantity != $updated_quantity || $new_item)
|
|
{
|
|
$success &= $this->Item_quantity->save($location_detail, $item_id, $location['location_id']);
|
|
|
|
$inv_data = array(
|
|
'trans_date' => date('Y-m-d H:i:s'),
|
|
'trans_items' => $item_id,
|
|
'trans_user' => $employee_id,
|
|
'trans_location' => $location['location_id'],
|
|
'trans_comment' => $this->lang->line('items_manually_editing_of_quantity'),
|
|
'trans_inventory' => $updated_quantity - $item_quantity->quantity
|
|
);
|
|
|
|
$success &= $this->Inventory->insert($inv_data);
|
|
}
|
|
}
|
|
|
|
// Save item attributes
|
|
$attribute_links = $this->input->post('attribute_links') !== NULL ? $this->input->post('attribute_links') : [];
|
|
$attribute_ids = $this->input->post('attribute_ids');
|
|
|
|
$this->Attribute->delete_link($item_id);
|
|
|
|
foreach($attribute_links as $definition_id => $attribute_id)
|
|
{
|
|
$definition_type = $this->Attribute->get_info($definition_id)->definition_type;
|
|
|
|
if($definition_type !== DROPDOWN)
|
|
{
|
|
$attribute_id = $this->Attribute->save_value($attribute_id, $definition_id, $item_id, $attribute_ids[$definition_id], $definition_type);
|
|
}
|
|
|
|
$this->Attribute->save_link($item_id, $definition_id, $attribute_id);
|
|
}
|
|
|
|
if($success && $upload_success)
|
|
{
|
|
$message = $this->xss_clean($this->lang->line('items_successful_' . ($new_item ? 'adding' : 'updating')) . ' ' . $item_data['name']);
|
|
|
|
echo json_encode(array('success' => TRUE, 'message' => $message, 'id' => $item_id));
|
|
}
|
|
else
|
|
{
|
|
$message = $this->xss_clean($upload_success ? $this->lang->line('items_error_adding_updating') . ' ' . $item_data['name'] : strip_tags($this->upload->display_errors()));
|
|
|
|
echo json_encode(array('success' => FALSE, 'message' => $message, 'id' => $item_id));
|
|
}
|
|
}
|
|
else
|
|
{
|
|
$message = $this->xss_clean($this->lang->line('items_error_adding_updating') . ' ' . $item_data['name']);
|
|
|
|
echo json_encode(array('success' => FALSE, 'message' => $message, 'id' => NEW_ITEM));
|
|
}
|
|
}
|
|
|
|
public function check_item_number()
|
|
{
|
|
$exists = $this->Item->item_number_exists($this->input->post('item_number'), $this->input->post('item_id'));
|
|
echo !$exists ? 'true' : 'false';
|
|
}
|
|
|
|
/*
|
|
If adding a new item check to see if an item kit with the same name as the item already exists.
|
|
*/
|
|
public function check_kit_exists()
|
|
{
|
|
if($this->input->post('item_number') === NEW_ITEM)
|
|
{
|
|
$exists = $this->Item_kit->item_kit_exists_for_name($this->input->post('name'));
|
|
}
|
|
else
|
|
{
|
|
$exists = FALSE;
|
|
}
|
|
echo !$exists ? 'true' : 'false';
|
|
}
|
|
|
|
/*
|
|
* Let files be uploaded with their original name
|
|
*/
|
|
private function handle_image_upload()
|
|
{
|
|
//Load upload library
|
|
$config = array('upload_path' => './uploads/item_pics/',
|
|
'allowed_types' => $this->config->item('image_allowed_types'),
|
|
'max_size' => $this->config->item('image_max_size'),
|
|
'max_width' => $this->config->item('image_max_width'),
|
|
'max_height' => $this->config->item('image_max_height'));
|
|
|
|
$this->load->library('upload', $config);
|
|
$this->upload->do_upload('item_image');
|
|
|
|
return strlen($this->upload->display_errors()) === 0 || !strcmp($this->upload->display_errors(), '<p>' . $this->lang->line('upload_no_file_selected') . '</p>');
|
|
}
|
|
|
|
public function remove_logo($item_id)
|
|
{
|
|
$item_data = array('pic_filename' => NULL);
|
|
$result = $this->Item->save($item_data, $item_id);
|
|
|
|
echo json_encode(array('success' => $result));
|
|
}
|
|
|
|
public function save_inventory($item_id = NEW_ITEM)
|
|
{
|
|
$employee_id = $this->Employee->get_logged_in_employee_info()->person_id;
|
|
$cur_item_info = $this->Item->get_info($item_id);
|
|
$location_id = $this->input->post('stock_location');
|
|
$inv_data = array(
|
|
'trans_date' => date('Y-m-d H:i:s'),
|
|
'trans_items' => $item_id,
|
|
'trans_user' => $employee_id,
|
|
'trans_location' => $location_id,
|
|
'trans_comment' => $this->input->post('trans_comment'),
|
|
'trans_inventory' => parse_quantity($this->input->post('newquantity'))
|
|
);
|
|
|
|
$this->Inventory->insert($inv_data);
|
|
|
|
//Update stock quantity
|
|
$item_quantity = $this->Item_quantity->get_item_quantity($item_id, $location_id);
|
|
$item_quantity_data = array(
|
|
'item_id' => $item_id,
|
|
'location_id' => $location_id,
|
|
'quantity' => $item_quantity->quantity + parse_quantity($this->input->post('newquantity'))
|
|
);
|
|
|
|
if($this->Item_quantity->save($item_quantity_data, $item_id, $location_id))
|
|
{
|
|
$message = $this->xss_clean($this->lang->line('items_successful_updating') . " $cur_item_info->name");
|
|
|
|
echo json_encode(array('success' => TRUE, 'message' => $message, 'id' => $item_id));
|
|
}
|
|
else
|
|
{
|
|
$message = $this->xss_clean($this->lang->line('items_error_adding_updating') . " $cur_item_info->name");
|
|
|
|
echo json_encode(array('success' => FALSE, 'message' => $message, 'id' => NEW_ITEM));
|
|
}
|
|
}
|
|
|
|
public function bulk_update()
|
|
{
|
|
$items_to_update = $this->input->post('item_ids');
|
|
$item_data = [];
|
|
|
|
foreach($_POST as $key => $value)
|
|
{
|
|
//This field is nullable, so treat it differently
|
|
if($key === 'supplier_id' && $value !== '')
|
|
{
|
|
$item_data[$key] = $value;
|
|
}
|
|
elseif($value !== '' && !(in_array($key, array('item_ids', 'tax_names', 'tax_percents'))))
|
|
{
|
|
$item_data[$key] = $value;
|
|
}
|
|
}
|
|
|
|
//Item data could be empty if tax information is being updated
|
|
if(empty($item_data) || $this->Item->update_multiple($item_data, $items_to_update))
|
|
{
|
|
$items_taxes_data = [];
|
|
$tax_names = $this->input->post('tax_names');
|
|
$tax_percents = $this->input->post('tax_percents');
|
|
$tax_updated = FALSE;
|
|
|
|
foreach($tax_percents as $tax_percent)
|
|
{
|
|
if(!empty($tax_names[$tax_percent]) && is_numeric($tax_percents[$tax_percent]))
|
|
{
|
|
$tax_updated = TRUE;
|
|
$items_taxes_data[] = array('name' => $tax_names[$tax_percent], 'percent' => $tax_percents[$tax_percent]);
|
|
}
|
|
}
|
|
|
|
if($tax_updated)
|
|
{
|
|
$this->Item_taxes->save_multiple($items_taxes_data, $items_to_update);
|
|
}
|
|
|
|
echo json_encode(array('success' => TRUE, 'message' => $this->lang->line('items_successful_bulk_edit'), 'id' => $this->xss_clean($items_to_update)));
|
|
}
|
|
else
|
|
{
|
|
echo json_encode(array('success' => FALSE, 'message' => $this->lang->line('items_error_updating_multiple')));
|
|
}
|
|
}
|
|
|
|
public function delete()
|
|
{
|
|
$items_to_delete = $this->input->post('ids');
|
|
|
|
if($this->Item->delete_list($items_to_delete))
|
|
{
|
|
$message = $this->lang->line('items_successful_deleted') . ' ' . count($items_to_delete) . ' ' . $this->lang->line('items_one_or_multiple');
|
|
echo json_encode(array('success' => TRUE, 'message' => $message));
|
|
}
|
|
else
|
|
{
|
|
echo json_encode(array('success' => FALSE, 'message' => $this->lang->line('items_cannot_be_deleted')));
|
|
}
|
|
}
|
|
|
|
public function generate_csv_file()
|
|
{
|
|
$name = 'import_items.csv';
|
|
$allowed_locations = $this->Stock_location->get_allowed_locations();
|
|
$allowed_attributes = $this->Attribute->get_definition_names(FALSE);
|
|
$data = generate_import_items_csv($allowed_locations, $allowed_attributes);
|
|
|
|
force_download($name, $data, TRUE);
|
|
}
|
|
|
|
public function csv_import()
|
|
{
|
|
$this->load->view('items/form_csv_import', NULL);
|
|
}
|
|
|
|
/**
|
|
* Imports items from CSV formatted file.
|
|
*/
|
|
public function import_csv_file()
|
|
{
|
|
if($_FILES['file_path']['error'] !== UPLOAD_ERR_OK)
|
|
{
|
|
echo json_encode(array('success' => FALSE, 'message' => $this->lang->line('items_csv_import_failed')));
|
|
}
|
|
else
|
|
{
|
|
if(file_exists($_FILES['file_path']['tmp_name']))
|
|
{
|
|
set_time_limit(240);
|
|
|
|
$failCodes = [];
|
|
$third_party_data = [];
|
|
$csv_rows = get_csv_file($_FILES['file_path']['tmp_name']);
|
|
$employee_id = $this->Employee->get_logged_in_employee_info()->person_id;
|
|
$allowed_stock_locations = $this->Stock_location->get_allowed_locations();
|
|
$attribute_definition_names = $this->Attribute->get_definition_names();
|
|
|
|
unset($attribute_definition_names[-1]); //Removes the common_none_selected_text from the array
|
|
|
|
foreach($attribute_definition_names as $definition_name)
|
|
{
|
|
$attribute_data[$definition_name] = $this->Attribute->get_definition_by_name($definition_name)[0];
|
|
|
|
if($attribute_data[$definition_name]['definition_type'] === DROPDOWN)
|
|
{
|
|
$attribute_data[$definition_name]['dropdown_values'] = $this->Attribute->get_definition_values($attribute_data[$definition_name]['definition_id']);
|
|
}
|
|
}
|
|
|
|
$this->db->trans_begin();
|
|
|
|
foreach($csv_rows as $key => $row)
|
|
{
|
|
$is_failed_row = FALSE;
|
|
$item_id = $row['Id'];
|
|
$is_update = !empty($item_id);
|
|
$item_data = array(
|
|
'item_id' => $item_id,
|
|
'name' => $row['Item Name'],
|
|
'description' => $row['Description'],
|
|
'category' => $row['Category'],
|
|
'cost_price' => $row['Cost Price'],
|
|
'unit_price' => $row['Unit Price'],
|
|
'reorder_level' => $row['Reorder Level'],
|
|
'deleted' => FALSE,
|
|
'hsn_code' => $row['HSN'],
|
|
'pic_filename' => $row['Image']);
|
|
|
|
if(!empty($row['supplier_id']))
|
|
{
|
|
$item_data['supplier_id'] = $this->Supplier->exists($row['Supplier ID']) ? $row['Supplier ID'] : NULL;
|
|
}
|
|
|
|
if($is_update)
|
|
{
|
|
$item_data['allow_alt_description'] = empty($row['Allow Alt Description']) ? NULL : $row['Allow Alt Description'];
|
|
$item_data['is_serialized'] = empty($row['Item has Serial Number']) ? NULL : $row['Item has Serial Number'];
|
|
}
|
|
else
|
|
{
|
|
$item_data['allow_alt_description'] = empty($row['Allow Alt Description'])? '0' : '1';
|
|
$item_data['is_serialized'] = empty($row['Item has Serial Number'])? '0' : '1';
|
|
}
|
|
|
|
if(!empty($row['Barcode']))
|
|
{
|
|
$item_data['item_number'] = $row['Barcode'];
|
|
$is_failed_row = $this->Item->item_number_exists($item_data['item_number']);
|
|
}
|
|
|
|
if(!$is_failed_row)
|
|
{
|
|
$is_failed_row = $this->data_error_check($row, $item_data, $allowed_stock_locations, $attribute_definition_names, $attribute_data);
|
|
}
|
|
|
|
$item_data = $this->item_lib->custom_array_filter($item_data);
|
|
|
|
if(!$is_failed_row && $this->Item->save($item_data, $item_id))
|
|
{
|
|
$this->save_tax_data($row, $item_data);
|
|
$this->save_inventory_quantities($row, $item_data, $allowed_stock_locations, $employee_id);
|
|
$is_failed_row = $this->save_attribute_data($row, $item_data, $attribute_data);
|
|
|
|
if($is_update)
|
|
{
|
|
$item_data = array_merge($item_data, get_object_vars($this->Item->get_info_by_id_or_number($item_id)));
|
|
}
|
|
}
|
|
else
|
|
{
|
|
$failed_row = $key+2;
|
|
$failCodes[] = $failed_row;
|
|
log_message('ERROR',"CSV Item import failed on line $failed_row. This item was not imported.");
|
|
}
|
|
|
|
unset($csv_rows[$key]);
|
|
}
|
|
|
|
$csv_rows = NULL;
|
|
|
|
if(count($failCodes) > 0)
|
|
{
|
|
$message = $this->lang->line('items_csv_import_partially_failed', count($failCodes), implode(', ', $failCodes));
|
|
$this->db->trans_rollback();
|
|
echo json_encode(array('success' => FALSE, 'message' => $message));
|
|
}
|
|
else
|
|
{
|
|
$this->db->trans_commit();
|
|
|
|
echo json_encode(array('success' => TRUE, 'message' => $this->lang->line('items_csv_import_success')));
|
|
}
|
|
}
|
|
else
|
|
{
|
|
echo json_encode(array('success' => FALSE, 'message' => $this->lang->line('items_csv_import_nodata_wrongformat')));
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Checks the entire line of data in an import file for errors
|
|
*
|
|
* @param array $line
|
|
* @param array $item_data
|
|
*
|
|
* @return bool Returns FALSE if all data checks out and TRUE when there is an error in the data
|
|
*/
|
|
private function data_error_check($row, $item_data, $allowed_locations, $definition_names, $attribute_data)
|
|
{
|
|
$item_id = $row['Id'];
|
|
$is_update = $item_id ? TRUE : FALSE;
|
|
|
|
//Check for empty required fields
|
|
$check_for_empty = array(
|
|
'name' => $item_data['name'],
|
|
'category' => $item_data['category'],
|
|
'unit_price' => $item_data['unit_price']);
|
|
|
|
foreach($check_for_empty as $key => $val)
|
|
{
|
|
if (empty($val) && !$is_update)
|
|
{
|
|
log_message('Error',"Empty required value in $key.");
|
|
return TRUE;
|
|
}
|
|
}
|
|
|
|
if(!$is_update)
|
|
{
|
|
$item_data['cost_price'] = empty($item_data['cost_price']) ? 0 : $item_data['cost_price']; //Allow for zero wholesale price
|
|
}
|
|
else
|
|
{
|
|
if(!$this->Item->exists($item_id))
|
|
{
|
|
log_message('Error',"non-existent item_id: '$item_id' when either existing item_id or no item_id is required.");
|
|
return TRUE;
|
|
}
|
|
}
|
|
|
|
//Build array of fields to check for numerics
|
|
$check_for_numeric_values = array(
|
|
'cost_price' => $item_data['cost_price'],
|
|
'unit_price' => $item_data['unit_price'],
|
|
'reorder_level' => $item_data['reorder_level'],
|
|
'supplier_id' => $item_data['supplier_id'],
|
|
'Tax 1 Percent' => $row['Tax 1 Percent'],
|
|
'Tax 2 Percent' => $row['Tax 2 Percent']);
|
|
|
|
foreach($allowed_locations as $location_name)
|
|
{
|
|
$check_for_numeric_values[] = $row["location_$location_name"];
|
|
}
|
|
|
|
//Check for non-numeric values which require numeric
|
|
foreach($check_for_numeric_values as $key => $value)
|
|
{
|
|
if(!is_numeric($value) && !empty($value))
|
|
{
|
|
log_message('Error',"non-numeric: '$value' for '$key' when numeric is required");
|
|
return TRUE;
|
|
}
|
|
}
|
|
|
|
//Check Attribute Data
|
|
foreach($definition_names as $definition_name)
|
|
{
|
|
if(!empty($row["attribute_$definition_name"]))
|
|
{
|
|
$definition_type = $attribute_data[$definition_name]['definition_type'];
|
|
$attribute_value = $row["attribute_$definition_name"];
|
|
|
|
switch($definition_type)
|
|
{
|
|
case DROPDOWN:
|
|
$dropdown_values = $attribute_data[$definition_name]['dropdown_values'];
|
|
$dropdown_values[] = '';
|
|
|
|
if(!empty($attribute_value) && in_array($attribute_value, $dropdown_values) === FALSE)
|
|
{
|
|
log_message('Error',"Value: '$attribute_value' is not an acceptable DROPDOWN value");
|
|
return TRUE;
|
|
}
|
|
break;
|
|
case DECIMAL:
|
|
if(!is_numeric($attribute_value) && !empty($attribute_value))
|
|
{
|
|
log_message('Error',"'$attribute_value' is not an acceptable DECIMAL value");
|
|
return TRUE;
|
|
}
|
|
break;
|
|
case DATE:
|
|
if(valid_date($attribute_value) === FALSE && !empty($attribute_value))
|
|
{
|
|
log_message('Error',"'$attribute_value' is not an acceptable DATE value. The value must match the set locale.");
|
|
return TRUE;
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
return FALSE;
|
|
}
|
|
|
|
/**
|
|
* Saves attribute data found in the CSV import.
|
|
*
|
|
* @param line
|
|
* @param failCodes
|
|
* @param attribute_data
|
|
*/
|
|
private function save_attribute_data($row, $item_data, $definitions)
|
|
{
|
|
foreach($definitions as $definition)
|
|
{
|
|
$attribute_name = $definition['definition_name'];
|
|
$attribute_value = $row["attribute_$attribute_name"];
|
|
|
|
//Create attribute value
|
|
if(!empty($attribute_value) || $attribute_value === '0')
|
|
{
|
|
if($definition['definition_type'] === CHECKBOX)
|
|
{
|
|
$checkbox_is_unchecked = (strcasecmp($attribute_value,'FALSE') === 0 || $attribute_value === '0');
|
|
$attribute_value = $checkbox_is_unchecked ? '0' : '1';
|
|
|
|
$attribute_id = $this->store_attribute_value($attribute_value, $definition, $item_data['item_id']);
|
|
}
|
|
elseif(!empty($attribute_value))
|
|
{
|
|
$attribute_id = $this->store_attribute_value($attribute_value, $definition, $item_data['item_id']);
|
|
}
|
|
else
|
|
{
|
|
return TRUE;
|
|
}
|
|
|
|
if($attribute_id === FALSE)
|
|
{
|
|
return TRUE;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Saves the attribute_value and attribute_link if necessary
|
|
*/
|
|
private function store_attribute_value($value, $attribute_data, $item_id)
|
|
{
|
|
$attribute_id = $this->Attribute->value_exists($value, $attribute_data['definition_type']);
|
|
|
|
$this->Attribute->delete_link($item_id, $attribute_data['definition_id']);
|
|
|
|
if($attribute_id === FALSE)
|
|
{
|
|
$attribute_id = $this->Attribute->save_value($value, $attribute_data['definition_id'], $item_id, FALSE, $attribute_data['definition_type']);
|
|
}
|
|
else if($this->Attribute->save_link($item_id, $attribute_data['definition_id'], $attribute_id) === FALSE)
|
|
{
|
|
return FALSE;
|
|
}
|
|
return $attribute_id;
|
|
}
|
|
|
|
/**
|
|
* Saves inventory quantities for the row in the appropriate stock locations.
|
|
*
|
|
* @param array line
|
|
* @param item_data
|
|
*/
|
|
private function save_inventory_quantities($row, $item_data, $allowed_locations, $employee_id)
|
|
{
|
|
//Quantities & Inventory Section
|
|
$comment = $this->lang->line('items_inventory_CSV_import_quantity');
|
|
$is_update = $row['Id'] ? TRUE : FALSE;
|
|
|
|
foreach($allowed_locations as $location_id => $location_name)
|
|
{
|
|
$item_quantity_data = array(
|
|
'item_id' => $item_data['item_id'],
|
|
'location_id' => $location_id);
|
|
|
|
$csv_data = array(
|
|
'trans_items' => $item_data['item_id'],
|
|
'trans_user' => $employee_id,
|
|
'trans_comment' => $comment,
|
|
'trans_location' => $location_id);
|
|
|
|
if(!empty($row["location_$location_name"]) || $row["location_$location_name"] === '0')
|
|
{
|
|
$item_quantity_data['quantity'] = $row["location_$location_name"];
|
|
$this->Item_quantity->save($item_quantity_data, $item_data['item_id'], $location_id);
|
|
|
|
$csv_data['trans_inventory'] = $row["location_$location_name"];
|
|
$this->Inventory->insert($csv_data);
|
|
}
|
|
elseif($is_update)
|
|
{
|
|
return;
|
|
}
|
|
else
|
|
{
|
|
$item_quantity_data['quantity'] = 0;
|
|
$this->Item_quantity->save($item_quantity_data, $item_data['item_id'], $location_id);
|
|
|
|
$csv_data['trans_inventory'] = 0;
|
|
$this->Inventory->insert($csv_data);
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Saves the tax data found in the line of the CSV items import file
|
|
*
|
|
* @param array line
|
|
*/
|
|
private function save_tax_data($row, $item_data)
|
|
{
|
|
$items_taxes_data = [];
|
|
|
|
if(is_numeric($row['Tax 1 Percent']) && $row['Tax 1 Name'] !== '')
|
|
{
|
|
$items_taxes_data[] = array('name' => $row['Tax 1 Name'], 'percent' => $row['Tax 1 Percent']);
|
|
}
|
|
|
|
if(is_numeric($row['Tax 2 Percent']) && $row['Tax 2 Name'] !== '')
|
|
{
|
|
$items_taxes_data[] = array('name' => $row['Tax 2 Name'], 'percent' => $row['Tax 2 Percent']);
|
|
}
|
|
|
|
if(isset($items_taxes_data))
|
|
{
|
|
$this->Item_taxes->save($items_taxes_data, $item_data['item_id']);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Guess whether file extension is not in the table field, if it isn't, then it's an old-format (formerly pic_id) field, so we guess the right filename and update the table
|
|
*
|
|
* @param $item int item to update
|
|
*/
|
|
private function update_pic_filename($item)
|
|
{
|
|
$filename = pathinfo($item->pic_filename, PATHINFO_FILENAME);
|
|
|
|
// if the field is empty there's nothing to check
|
|
if(!empty($filename))
|
|
{
|
|
$ext = pathinfo($item->pic_filename, PATHINFO_EXTENSION);
|
|
if(empty($ext))
|
|
{
|
|
$images = glob("./uploads/item_pics/$item->pic_filename.*");
|
|
if(sizeof($images) > 0)
|
|
{
|
|
$new_pic_filename = pathinfo($images[0], PATHINFO_BASENAME);
|
|
$item_data = array('pic_filename' => $new_pic_filename);
|
|
$this->Item->save($item_data, $item->item_id);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
?>
|