diff --git a/admin/db/fiscalyears_db.inc b/admin/db/fiscalyears_db.inc index 459d16209..9051e4754 100644 --- a/admin/db/fiscalyears_db.inc +++ b/admin/db/fiscalyears_db.inc @@ -128,6 +128,8 @@ function check_years_before($date, $closed=false) //--------------------------------------------------------------------------------------------- function close_year($year) { + global $Refs; + $co = get_company_prefs(); if (get_gl_account($co['retained_earnings_act']) == false || get_gl_account($co['profit_loss_year_act']) == false) { @@ -157,15 +159,15 @@ function close_year($year) if ($balance != 0.0) { - $trans_type = ST_JOURNAL; - $trans_id = get_next_trans_no($trans_type); - - add_gl_trans($trans_type, $trans_id, $to, $co['retained_earnings_act'], - 0, 0, _("Closing Year"), -$balance); - add_gl_trans($trans_type, $trans_id, $to, $co['profit_loss_year_act'], - 0, 0, _("Closing Year"), $balance); - - } + $cart = new items_cart(ST_JOURNAL); + $cart->reference = $Refs->get_next(ST_JOURNAL, null, $to); + $cart->tran_date = $cart->doc_date = $cart->event_date = $to; + + $cart->add_gl_item($co['retained_earnings_act'], 0, 0, -$balance, _("Closing Year"), '', 0); + $cart->add_gl_item($co['profit_loss_year_act'], 0, 0, $balance, _("Closing Year"), '', 0); + $cart->memo_ = _("Closing Year"); + write_journal_entries($cart); + } close_transactions($to); commit_transaction(); @@ -368,10 +370,10 @@ function delete_this_fiscalyear($selected_id) { global $Refs; $trans_type = ST_JOURNAL; - $reference = $Refs->get_next($trans_type); - $Refs->save($trans_type, $trans_no, $reference); $date_ = sql2date($to); - + $reference = $Refs->get_next($trans_type, null, $date_); + add_journal($trans_type, $trans_no, $total, $date_, get_company_currency(), $reference); + $Refs->save($trans_type, $trans_no, $reference); add_audit_trail($trans_type, $trans_no, $date_); } $sql = "SELECT bank_act, SUM(amount) AS amount FROM ".TB_PREF."bank_trans WHERE trans_date <= '$to' GROUP BY bank_act"; diff --git a/gl/accruals.php b/gl/accruals.php index 5e45e3a35..3fc2b4270 100644 --- a/gl/accruals.php +++ b/gl/accruals.php @@ -1,4 +1,14 @@ . +***********************************************************************/ /********************************************** Author: Joe Hunt Name: Revenue / Cost Accruals v2.2 @@ -8,7 +18,7 @@ $path_to_root=".."; include_once($path_to_root . "/includes/session.inc"); -include_once($path_to_root . "/gl/includes/db/gl_db_trans.inc"); +include_once($path_to_root . "/includes/ui/items_cart.inc"); $js = get_js_open_window(800, 500); if (user_use_date_picker()) @@ -61,11 +71,11 @@ $date_ = begin_month($date_); // avoid skip on shorter months $date = end_month($date_); // avoid skip on shorter months } - $lastdate = ($freq == 1 ? add_days($date_, 7*$per) - : ($freq == 2 ? add_days($date_, 14*$per) - : ($freq == 3 ? add_months($date_, $per) - : add_months($date_, 3*$per)))); - + + $lastdate = ($freq == 1 ? add_days($date_, 7*$per) : + ($freq == 2 ? add_days($date_, 14*$per) : + ($freq == 3 ? end_month(add_months($date_, $per)) : + end_month(add_months($date_, 3*$per))))); if (!is_date_in_fiscalyears($lastdate, false)) { display_error(_("Some of the period dates are outside the fiscal year or are closed for further data entry. Create a new fiscal year first!")); @@ -112,31 +122,33 @@ switch($freq) { case 1: - $date = add_days($date_, $i*7); + $date = $date_ = add_days($date_, 7); break; case 2: - $date = add_days($date_, $i*14); + $date = $date_ = add_days($date_, 14); break; case 3: - $date = add_months($date_, $i*1); + $date_ = add_months($date_, 1); + $date = end_month($date_); break; case 4: - $date = add_months($date_, $i*3); + $date_ = add_months($date_, 3); + $date = end_month($date_); break; } $am0 = $am; } if (isset($_POST['go'])) { - $id = get_next_trans_no(ST_JOURNAL); - $ref = $Refs->get_next(ST_JOURNAL); - add_gl_trans(ST_JOURNAL, $id, $date, get_post('acc_act'), 0, - 0, $ref, $am0 * -1); - add_gl_trans(ST_JOURNAL, $id, $date, get_post('res_act'), get_post('dimension_id'), - get_post('dimension2_id'), $ref, $am0); - add_audit_trail(ST_JOURNAL, $id, $date); - add_comments(ST_JOURNAL, $id, $date, $memo); - $Refs->save(ST_JOURNAL, $id, $ref); + $cart = new items_cart(ST_JOURNAL); + $cart->memo_ = $memo; + $cart->reference = $Refs->get_next(ST_JOURNAL, null, $date); + $cart->tran_date = $cart->doc_date = $cart->event_date = $date; + $cart->add_gl_item(get_post('acc_act'), 0, 0, -$am0, $cart->reference); + $cart->add_gl_item(get_post('res_act'), get_post('dimension_id'), + get_post('dimension2_id'), $am0, $cart->reference); + write_journal_entries($cart); + $cart->clear_items(); } else { @@ -224,4 +236,3 @@ function frequency_list_row($label, $name, $selected=null) end_form(); end_page(); - diff --git a/gl/gl_journal.php b/gl/gl_journal.php index e4fd2f8d0..f2defddc1 100644 --- a/gl/gl_journal.php +++ b/gl/gl_journal.php @@ -21,7 +21,6 @@ include_once($path_to_root . "/gl/includes/ui/gl_journal_ui.inc"); include_once($path_to_root . "/gl/includes/gl_db.inc"); include_once($path_to_root . "/gl/includes/gl_ui.inc"); -include_once($path_to_root . "/taxes/db/tax_types_db.inc"); $js = ''; if ($SysPrefs->use_popup_windows) @@ -37,14 +36,15 @@ $_SESSION['page_title'] = _($help_context = "Journal Entry"); page($_SESSION['page_title'], false, false,'', $js); - //-------------------------------------------------------------------------------------------------- function line_start_focus() { global $Ajax; unset($_POST['Index']); - $Ajax->activate('items_table'); + $Ajax->activate('tabs'); + unset($_POST['_code_id_edit'], $_POST['code_id'], $_POST['AmountDebit'], + $_POST['AmountCredit'], $_POST['dimension_id'], $_POST['dimension2_id']); set_focus('_code_id_edit'); } //----------------------------------------------------------------------------------------------- @@ -92,7 +92,6 @@ function line_start_focus() { hyperlink_params("$path_to_root/gl/gl_journal.php", _("Entry &New Journal Entry"), "NewJournal=Yes"); display_footer_exit(); } - create_cart($_GET['trans_type'], $_GET['trans_no']); } @@ -105,44 +104,103 @@ function create_cart($type=0, $trans_no=0) unset ($_SESSION['journal_items']); } + check_is_closed($type, $trans_no); $cart = new items_cart($type); $cart->order_id = $trans_no; if ($trans_no) { + $header = get_journal($type, $trans_no); + $cart->event_date = sql2date($header['event_date']); + $cart->doc_date = sql2date($header['doc_date']); + $cart->tran_date = sql2date($header['tran_date']); + $cart->currency = $header['currency']; + $cart->rate = $header['rate']; + $cart->source_ref = $header['source_ref']; + $result = get_gl_trans($type, $trans_no); if ($result) { while ($row = db_fetch($result)) { - if ($row['amount'] == 0) continue; - $date = $row['tran_date']; - $cart->add_gl_item($row['account'], $row['dimension_id'], - $row['dimension2_id'], $row['amount'], $row['memo_'], '', $row['person_id']); + $curr_amount = $cart->rate ? round($row['amount']/$cart->rate, $_SESSION["wa_current_user"]->prefs->price_dec()) : $row['amount']; + if ($curr_amount) + $cart->add_gl_item($row['account'], $row['dimension_id'], $row['dimension2_id'], + $curr_amount, $row['memo_'], '', $row['person_id']); } } $cart->memo_ = get_comments_string($type, $trans_no); - $cart->tran_date = sql2date($date); - $cart->reference = $Refs->get($type, $trans_no); + $cart->reference = $header['reference']; + $_POST['ref_original'] = $cart->reference; // Store for comparison when updating + + // update net_amounts from tax register + + // retrieve tax details + $tax_info = $cart->collect_tax_info(); // tax amounts in reg are always consistent with GL, so we can read them from GL lines + + $taxes = get_trans_tax_details($type, $trans_no); + while ($detail = db_fetch($taxes)) + { + $tax_id = $detail['tax_type_id']; + $tax_info['net_amount'][$tax_id] = $detail['net_amount']; // we can two records for the same tax_id, but in this case net_amount is the same + $tax_info['tax_date'] = sql2date($detail['effective_date']); + $tax_info['tax_group'] = $detail['tax_group_id']; + + } + if (isset($tax_info['net_amount'])) // guess exempt sales/purchase if any tax has been found + { + $net_sum = 0; + foreach($cart->gl_items as $gl) + if (!is_tax_account($gl->code_id) && !is_subledger_account($gl->code_id, $gl->person_id)) + $net_sum += $gl->amount; + + $ex_net = abs($net_sum) - array_sum($tax_info['net_amount']); + if ($ex_net > 0) + $tax_info['net_amount_ex'] = $ex_net; + } + $cart->tax_info = $tax_info; + } else { - $cart->reference = $Refs->get_next(0); - $cart->tran_date = new_doc_date(); + $cart->tran_date = $cart->doc_date = $cart->event_date = new_doc_date(); if (!is_date_in_fiscalyear($cart->tran_date)) $cart->tran_date = end_fiscalyear(); + $cart->reference = $Refs->get_next(ST_JOURNAL, null, $cart->tran_date); $_POST['ref_original'] = -1; } $_POST['memo_'] = $cart->memo_; $_POST['ref'] = $cart->reference; $_POST['date_'] = $cart->tran_date; - + $_POST['event_date'] = $cart->event_date; + $_POST['doc_date'] = $cart->doc_date; + $_POST['currency'] = $cart->currency; + $_POST['_ex_rate'] = exrate_format($cart->rate); + $_POST['source_ref'] = $cart->source_ref; + if (isset($cart->tax_info['net_amount']) || (!$trans_no && get_company_pref('default_gl_vat'))) + $_POST['taxable_trans'] = true; $_SESSION['journal_items'] = &$cart; } -//----------------------------------------------------------------------------------------------- +function update_tax_info() +{ + + if (!isset($_SESSION['journal_items']->tax_info) || list_updated('tax_category')) + $_SESSION['journal_items']->tax_info = $_SESSION['journal_items']->collect_tax_info(); + foreach ($_SESSION['journal_items']->tax_info as $name => $value) + if (is_array($value)) + { + foreach ($value as $id => $amount) + { + $_POST[$name.'_'.$id] = price_format($amount); + } + } else + $_POST[$name] = $value; + $_POST['tax_date'] = $_SESSION['journal_items']->order_id ? $_SESSION['journal_items']->tax_info['tax_date'] : $_POST['date_']; +} + +//----------------------------------------------------------------------------------------------- if (isset($_POST['Process'])) { - $input_error = 0; if ($_SESSION['journal_items']->count_gl_items() < 1) { @@ -150,7 +208,7 @@ function create_cart($type=0, $trans_no=0) set_focus('code_id'); $input_error = 1; } - if (abs($_SESSION['journal_items']->gl_items_total()) > 0.0001) + if (abs($_SESSION['journal_items']->gl_items_total()) > 0.001) { display_error(_("The journal must balance (debits equal to credits) before it can be processed.")); set_focus('code_id'); @@ -169,21 +227,80 @@ function create_cart($type=0, $trans_no=0) set_focus('date_'); $input_error = 1; } + if (!is_date($_POST['event_date'])) + { + display_error(_("The entered date is invalid.")); + set_focus('event_date'); + $input_error = 1; + } + if (!is_date($_POST['doc_date'])) + { + display_error(_("The entered date is invalid.")); + set_focus('doc_date'); + $input_error = 1; + } if (!$Refs->is_valid($_POST['ref'])) { display_error( _("You must enter a reference.")); set_focus('ref'); $input_error = 1; } - elseif ($Refs->exists(ST_JOURNAL, $_POST['ref'])) + elseif (($_POST['ref'] != $_POST['ref_original']) && $Refs->exists(ST_JOURNAL,$_POST['ref'])) { - // The reference can exist already so long as it's the same as the original (when modifying) - if ($_POST['ref'] != $_POST['ref_original']) { - display_error( _("The entered reference is already in use.")); - set_focus('ref'); + display_error( _("The entered reference is already in use.")); + set_focus('ref'); + $input_error = 1; + } + if (get_post('currency') != get_company_pref('curr_default')) + if (isset($_POST['_ex_rate']) && !check_num('_ex_rate', 0.000001)) + { + display_error(_("The exchange rate must be numeric and greater than zero.")); + set_focus('_ex_rate'); $input_error = 1; - } + } + + if (get_post('_tabs_sel') == 'tax') + { + if (!is_date($_POST['tax_date'])) + { + display_error(_("The entered date is invalid.")); + set_focus('tax_date'); + $input_error = 1; + } + elseif (!is_date_in_fiscalyear($_POST['tax_date'])) + { + display_error(_("The entered date is out of fiscal year or is closed for further data entry.")); + set_focus('tax_date'); + $input_error = 1; + } + // FIXME: check proper tax net input values, check sum of net values against total GL an issue warning } + + if (check_value('taxable_trans')) + { + if (!tab_visible('tabs', 'tax')) + { + display_warning(_("Check tax register records before processing transaction or switch off 'Include in tax register' option.")); + $_POST['tabs_tax'] = true; // force tax tab select + $input_error = 1; + } else { + $taxes = get_all_tax_types(); + $net_amount = 0; + while ($tax = db_fetch($taxes)) + { + $tax_id = $tax['id']; + $net_amount += input_num('net_amount_'.$tax_id); + } + // in case no tax account used we have to guss tax register on customer/supplier used. + if ($net_amount && !$_SESSION['journal_items']->has_taxes() && !$_SESSION['journal_items']->has_sub_accounts()) + { + display_error(_("Cannot determine tax register to be used. You have to make at least one posting either to tax or customer/supplier account to use tax register.")); + $_POST['tabs_gl'] = true; // force gl tab select + $input_error = 1; + } + } + } + if ($input_error == 1) unset($_POST['Process']); } @@ -194,10 +311,32 @@ function create_cart($type=0, $trans_no=0) $new = $cart->order_id == 0; $cart->reference = $_POST['ref']; - $cart->memo_ = $_POST['memo_']; $cart->tran_date = $_POST['date_']; + $cart->doc_date = $_POST['doc_date']; + $cart->event_date = $_POST['event_date']; + $cart->source_ref = $_POST['source_ref']; + if (isset($_POST['memo_'])) + $cart->memo_ = $_POST['memo_']; - $trans_no = write_journal_entries($cart, check_value('Reverse')); + $cart->currency = $_POST['currency']; + if ($cart->currency != get_company_pref('curr_default')) + $cart->rate = input_num('_ex_rate'); + + if (check_value('taxable_trans')) + { + // complete tax register data + $cart->tax_info['tax_date'] = $_POST['tax_date']; + $cart->tax_info['tax_group'] = $_POST['tax_group']; + $taxes = get_all_tax_types(); + while ($tax = db_fetch($taxes)) + { + $tax_id = $tax['id']; + $cart->tax_info['net_amount'][$tax_id] = input_num('net_amount_'.$tax_id); + $cart->tax_info['rate'][$tax_id] = $tax['rate']; + } + } else + $cart->tax_info = false; + $trans_no = write_journal_entries($cart); $cart->clear_items(); new_doc_date($_POST['date_']); @@ -212,6 +351,21 @@ function create_cart($type=0, $trans_no=0) function check_item_data() { + global $Ajax; + + if (!get_post('code_id')) { + display_error(_("You must select GL account.")); + set_focus('code_id'); + return false; + } + if (is_subledger_account(get_post('code_id'))) { + if(!get_post('person_id')) { + display_error(_("You must select subledger account.")); + $Ajax->activate('items_table'); + set_focus('person_id'); + return false; + } + } if (isset($_POST['dimension_id']) && $_POST['dimension_id'] != 0 && dimension_is_closed($_POST['dimension_id'])) { display_error(_("Dimension is closed.")); @@ -274,8 +428,9 @@ function handle_update_item() $_SESSION['journal_items']->update_gl_item($_POST['Index'], $_POST['code_id'], $_POST['dimension_id'], $_POST['dimension2_id'], $amount, $_POST['LineMemo'], '', get_post('person_id')); + unset($_SESSION['journal_items']->tax_info); + line_start_focus(); } - line_start_focus(); } //----------------------------------------------------------------------------------------------- @@ -283,6 +438,7 @@ function handle_update_item() function handle_delete_item($id) { $_SESSION['journal_items']->remove_gl_item($id); + unset($_SESSION['journal_items']->tax_info); line_start_focus(); } @@ -300,10 +456,45 @@ function handle_new_item() $_SESSION['journal_items']->add_gl_item($_POST['code_id'], $_POST['dimension_id'], $_POST['dimension2_id'], $amount, $_POST['LineMemo'], '', get_post('person_id')); + unset($_SESSION['journal_items']->tax_info); line_start_focus(); } //----------------------------------------------------------------------------------------------- +if (isset($_POST['_taxable_trans_update'])) +{ if (!check_value('taxable_trans')) + $_POST['tabs_gl'] = true; // force tax tab select + else + set_focus('taxable_trans'); + $Ajax->activate('tabs'); +} + +if (tab_closed('tabs', 'gl')) +{ + $_SESSION['journal_items']->memo_ = $_POST['memo_']; +} + elseif (tab_closed('tabs', 'tax')) +{ + $cart = &$_SESSION['journal_items']; + $cart->tax_info['tax_date'] = $_POST['tax_date']; + $cart->tax_info['tax_group'] = $_POST['tax_group']; + $taxes = get_all_tax_types(); + while ($tax = db_fetch($taxes)) + { + $tax_id = $tax['id']; + $cart->tax_info['net_amount'][$tax_id] = input_num('net_amount_'.$tax_id); + $cart->tax_info['rate'][$tax_id] = $tax['rate']; + } +} +if (tab_opened('tabs', 'gl')) +{ + $_POST['memo_'] = $_SESSION['journal_items']->memo_; +} elseif (tab_opened('tabs', 'tax')) +{ + set_focus('tax_date'); +} + + $id = find_submit('Delete'); if ($id != -1) handle_delete_item($id); @@ -319,30 +510,69 @@ function handle_new_item() if (isset($_POST['go'])) { - display_quick_entries($_SESSION['journal_items'], $_POST['person_id'], input_num('totamount'), QE_JOURNAL); + display_quick_entries($_SESSION['journal_items'], $_POST['quick'], input_num('totamount'), QE_JOURNAL, get_post('aux_info')); $_POST['totamount'] = price_format(0); $Ajax->activate('totamount'); line_start_focus(); -} +} + +if (list_updated('tax_category')) +{ + $Ajax->activate('tabs'); +} + //----------------------------------------------------------------------------------------------- start_form(); display_order_header($_SESSION['journal_items']); -start_table(TABLESTYLE2, "width='90%'", 10); -start_row(); -echo ""; -display_gl_items(_("Rows"), $_SESSION['journal_items']); -gl_options_controls(); -echo ""; -end_row(); -end_table(1); - -submit_center('Process', _("Process Journal Entry"), true , - _('Process journal entry only if debits equal to credits'), 'default'); +tabbed_content_start('tabs', array( + 'gl' => array(_('&GL postings'), true), + 'tax' => array(_('&Tax register'), check_value('taxable_trans')), + )); + + switch (get_post('_tabs_sel')) { + default: + case 'gl': + start_table(TABLESTYLE2, "width='90%'", 10); + start_row(); + echo ""; + display_gl_items(_("Rows"), $_SESSION['journal_items']); + gl_options_controls(); + echo ""; + end_row(); + end_table(1); + break; + + case 'tax': + update_tax_info(); + display_heading(_("Tax register record")); + start_table(TABLESTYLE2, "width=40%"); + date_row(_("VAT date:"), 'tax_date', '', "colspan='3'"); + tax_groups_list_row(_("Tax group:"), 'tax_group'); + end_table(1); + + start_table(TABLESTYLE2, "width=60%"); + table_header(array(_('Name'), _('Input Tax'), _('Output Tax'), _('Net amount'))); + $taxes = get_all_tax_types(); + while ($tax = db_fetch($taxes)) + { + start_row(); + label_cell($tax['name'].' '.$tax['rate'].'%'); + amount_cell(input_num('tax_in_'.$tax['id'])); + amount_cell(input_num('tax_out_'.$tax['id'])); + + amount_cells(null, 'net_amount_'.$tax['id']); + end_row(); + } + end_table(1); + break; + }; + submit_center('Process', _("Process Journal Entry"), true , + _('Process journal entry only if debits equal to credits'), 'default'); +br(); +tabbed_content_end(); end_form(); -//------------------------------------------------------------------------------------------------ end_page(); - diff --git a/gl/includes/db/gl_db_accounts.inc b/gl/includes/db/gl_db_accounts.inc index 00b8fbe34..25bc84fce 100644 --- a/gl/includes/db/gl_db_accounts.inc +++ b/gl/includes/db/gl_db_accounts.inc @@ -206,6 +206,18 @@ function is_subledger_account($account) return $myrow[0]; } +function get_subaccount_data($code_id, $person_id) +{ + $sql = "SELECT debtor_ref as name, branch_code as id + FROM ".TB_PREF."cust_branch branch LEFT JOIN ".TB_PREF."debtors_master d ON branch.debtor_no = d.debtor_no + WHERE branch.receivables_account=".db_escape($code_id)." AND d.debtor_no=".db_escape($person_id) + ." UNION SELECT supp_ref as name, '' as id FROM ".TB_PREF."suppliers supp + WHERE supplier_id=".db_escape($person_id)." AND payable_account=".db_escape($code_id); + $result = db_query($sql, 'cannot retrieve counterparty name'); + + return db_fetch($result); +} + function get_subaccount_name($code_id, $person_id) { $sql = "SELECT debtor_ref as ref FROM ".TB_PREF."cust_branch branch LEFT JOIN ".TB_PREF."debtors_master d ON branch.debtor_no = d.debtor_no diff --git a/gl/includes/db/gl_db_banking.inc b/gl/includes/db/gl_db_banking.inc index bba72d72e..cd197af79 100644 --- a/gl/includes/db/gl_db_banking.inc +++ b/gl/includes/db/gl_db_banking.inc @@ -37,14 +37,29 @@ function add_exchange_variation($trans_no, $date_, $acc_id, $account, $diff = $amount - $for_amount; if (floatcmp($diff,0)) { - if ($trans_no == null) - $trans_no = get_next_trans_no(ST_JOURNAL); + // generate journal entry // FIXME: use cart? + global $Refs; + + begin_transaction(); + $trans_no = get_next_trans_no(ST_JOURNAL); + $ref = $Refs->get_next(ST_JOURNAL); + + add_journal(ST_JOURNAL, $trans_no, $diff, $date_ , $currency, $ref, '', $rate, $date_, $date_); + $Refs->save(ST_JOURNAL, $trans_no, $ref); + add_audit_trail(ST_JOURNAL, $trans_no, $date_); + add_comments(ST_JOURNAL, $trans_no, $date_, $memo); + if ($person_type_id == null) $person_type_id = PT_MISC; add_gl_trans(ST_JOURNAL, $trans_no, $date_, $account, 0, 0, _("Exchange Variance"), - -$diff, null, $person_type_id, $person_id); + $diff, null, $person_type_id, $person_id); + + // positive change in value is positive variance for AR and bank accounts, and negative for AP + $variance_act = ($diff < 0 && $person_id==PT_SUPPLIER) || ($diff > 0 && $person_id != PT_SUPPLIER) + ? 'exchange_diff_act' : 'exchange_diff_neg_act'; add_gl_trans(ST_JOURNAL, $trans_no, $date_, get_company_pref('exchange_diff_act'), 0, 0, - _("Exchange Variance"), $diff, null, $person_type_id, $person_id); + _("Exchange Variance"), -$diff, null, $person_type_id, $person_id); + commit_transaction(); return true; } return false; @@ -56,15 +71,21 @@ function add_cust_supp_revaluation($ledger_act, $ex_act, $date, $amount, $person global $Refs; if ($amount == 0) return; + + begin_transaction(); $trans_no = get_next_trans_no(ST_JOURNAL); + $ref = $Refs->get_next(ST_JOURNAL); + + add_journal(ST_JOURNAL, $trans_no, $amount, $date, $currency, $ref, '', $rate, $date, $date); + $Refs->save(ST_JOURNAL, $trans_no, $ref); + add_audit_trail(ST_JOURNAL, $trans_no, $date); + add_gl_trans(ST_JOURNAL, $trans_no, $date, $ledger_act, 0, 0, _("Exchange Variance"), $amount, null, $person_type_id, $person_id); add_gl_trans(ST_JOURNAL, $trans_no, $date, $ex_act, 0, 0, _("Exchange Variance"), -$amount, null, $person_type_id, $person_id); add_comments(ST_JOURNAL, $trans_no, $date, $memo); - $ref = $Refs->get_next(ST_JOURNAL); - $Refs->save(ST_JOURNAL, $trans_no, $ref); - add_audit_trail(ST_JOURNAL, $trans_no, $date); + commit_transaction(); } function get_cust_account_curr_balances($date) diff --git a/gl/includes/db/gl_db_trans.inc b/gl/includes/db/gl_db_trans.inc index cac714b06..d42bd7326 100644 --- a/gl/includes/db/gl_db_trans.inc +++ b/gl/includes/db/gl_db_trans.inc @@ -475,102 +475,6 @@ function get_tax_summary($from, $to) return db_query($sql,"Cannot retrieve tax summary"); } -//-------------------------------------------------------------------------------- -// Write/update journal entries. -// -function write_journal_entries(&$cart, $reverse, $use_transaction=true) -{ - global $Refs; - - $date_ = $cart->tran_date; - $ref = $cart->reference; - $memo_ = $cart->memo_; - $trans_type = $cart->trans_type; - $new = $cart->order_id == 0; - - if ($new) - $cart->order_id = get_next_trans_no($trans_type); - - $trans_id = $cart->order_id; - - if ($use_transaction) - begin_transaction(); - - if(!$new) - void_journal_trans($trans_type, $trans_id, false); - - foreach ($cart->gl_items as $journal_item) - { - // post to first found bank account using given gl acount code. - $is_bank_to = is_bank_account($journal_item->code_id); - - add_gl_trans($trans_type, $trans_id, $date_, $journal_item->code_id, - $journal_item->dimension_id, $journal_item->dimension2_id, - $journal_item->reference, $journal_item->amount, null, - $journal_item->person_type_id, - $journal_item->person_id); - - if ($is_bank_to) - { - add_bank_trans($trans_type, $trans_id, $is_bank_to, $ref, - $date_, $journal_item->amount, 0, "", get_company_currency(), - "Cannot insert a destination bank transaction"); - } - // store tax details if the gl account is a tax account - add_gl_tax_details($journal_item->code_id, - ST_JOURNAL, $trans_id, $journal_item->amount, 1, $date_, $memo_); - } - - $Refs->save($trans_type, $trans_id, $ref); - if ($new) { - add_comments($trans_type, $trans_id, $date_, $memo_); - } else { - update_comments($trans_type, $trans_id, null, $memo_); - } - - add_audit_trail($trans_type, $trans_id, $date_); - - if ($reverse) - { - //$reversingDate = date(user_date_display(), - // Mktime(0,0,0,get_month($date_)+1,1,get_year($date_))); - $reversingDate = begin_month(add_months($date_, 1)); - - $trans_id_reverse = get_next_trans_no($trans_type); - - foreach ($cart->gl_items as $journal_item) - { - $is_bank_to = is_bank_account($journal_item->code_id); - - add_gl_trans($trans_type, $trans_id_reverse, $reversingDate, - $journal_item->code_id, $journal_item->dimension_id, $journal_item->dimension2_id, - $journal_item->reference, -$journal_item->amount, - null, $journal_item->person_type_id, $journal_item->person_id); - - if ($is_bank_to) - { - add_bank_trans($trans_type, $trans_id_reverse, $is_bank_to, $ref, - $reversingDate, -$journal_item->amount, - 0, "", get_company_currency(), - "Cannot insert a destination bank transaction"); - } - // store tax details if the gl account is a tax account - add_gl_tax_details($journal_item->code_id, - ST_JOURNAL, $trans_id, $journal_item->amount, 1, $reversingDate, $memo_); - } - - add_comments($trans_type, $trans_id_reverse, $reversingDate, $memo_); - - $Refs->save($trans_type, $trans_id_reverse, $ref); - add_audit_trail($trans_type, $trans_id_reverse, $reversingDate); - } - - if ($use_transaction) - commit_transaction(); - - return $trans_id; -} - //-------------------------------------------------------------------------------------------------- function exists_gl_trans($type, $trans_id) @@ -614,21 +518,6 @@ function clear_gl_trans($type, $trans_id, $nested=false) commit_transaction(); } -//---------------------------------------------------------------------------------------- - -function void_journal_trans($type, $type_no, $use_transaction=true) -{ - if ($use_transaction) - begin_transaction(); - - void_bank_trans($type, $type_no, true); -// void_gl_trans($type, $type_no, true); // this is done above -// void_trans_tax_details($type, $type_no); // ditto - - if ($use_transaction) - commit_transaction(); -} - function get_sql_for_journal_inquiry($filter, $from, $to, $ref='', $memo='', $alsoclosed=false) { diff --git a/gl/includes/db/gl_journal.inc b/gl/includes/db/gl_journal.inc new file mode 100644 index 000000000..f3f49533d --- /dev/null +++ b/gl/includes/db/gl_journal.inc @@ -0,0 +1,166 @@ +. +***********************************************************************/ +function add_journal($type, $trans_no, $amount, $tran_date, $currency, $reference, $source_ref='', $rate=1, + $event_date='', $doc_date='') +{ + $sql = "INSERT INTO ".TB_PREF."journal( + `type`,`trans_no`, `amount`, `currency`, `rate`, `reference`, `source_ref`, `tran_date`, + `event_date`, `doc_date`) + VALUES(" + .db_escape($type)."," + .db_escape($trans_no)."," + .db_escape($amount)."," + .db_escape($currency)."," + .db_escape($rate)."," + .db_escape($reference)."," + .db_escape($source_ref)."," + ."'".date2sql($tran_date)."'," + ."'".date2sql($event_date)."'," + ."'".date2sql($doc_date)."')"; + + return db_query($sql, 'cannot add journal entry'); +} + +function update_journal($type, $trans_no, $amount, $tran_date, $currency, $reference, $source_ref='', $rate=1, + $event_date='', $doc_date='') +{ + $sql = "UPDATE ".TB_PREF."journal SET " + ."`amount`=".db_escape($amount)."," + ."`currency`=".db_escape($currency)."," + ."`rate`=".db_escape($rate)."," + ."`reference`=".db_escape($reference)."," + ."`source_ref`=".db_escape($source_ref)."," + ."`tran_date`="."'".date2sql($tran_date)."'," + ."`event_date`="."'".date2sql($event_date)."'," + ."`doc_date`="."'".date2sql($doc_date)."') + WHERE `type`=".db_escape($type)." AND " ."`trans_no`=".db_escape($trans_no); + + return db_query($sql, 'cannot update journal entry'); +} + +function delete_journal($type, $trans_no) +{ + $sql = "DELETE FROM ".TB_PREF."journal + WHERE `type`=".db_escape($type)." AND " ."`trans_no`=".db_escape($trans_no); + + return db_query($sql, 'cannot delete journal entry'); +} + +function get_journal($type, $trans_no) +{ + $sql = "SELECT * FROM ".TB_PREF."journal + WHERE `type`=".db_escape($type)." AND " ."`trans_no`=".db_escape($trans_no); + + $myrow= db_query($sql, 'cannot retrieve journal entry'); + return db_fetch($myrow); +} + +// +// Write headers in debtor_trans for allocation purposes. +// Amount in customer currency +// +function write_cust_journal($trans_type, $trans_no, $branch_id, $date, $ref, $amount, $rate) +{ + // we have to select any branch_id for given AR_act - in fact w + $sql = "INSERT INTO ".TB_PREF."debtor_trans (trans_no, type, debtor_no, branch_code, tran_date, reference, ov_amount, rate) + SELECT " + .db_escape($trans_no).", ".db_escape($trans_type).", debtor_no," + .db_escape($branch_id).",'".date2sql($date)."', ".db_escape($ref)."," + .db_escape($amount).", ".db_escape($rate)." + FROM ".TB_PREF."cust_branch WHERE branch_code=".db_escape($branch_id); + + return db_query($sql, 'cannot write cust_journal'); +} + +// +// Write headers in supp_trans for allocation purposes. +// Amount in supplier currency +// +function write_supp_journal($trans_type, $trans_no, $supp_id, $date, $ref, $amount, $rate, $src_ref) +{ + $sql = "INSERT INTO ".TB_PREF."supp_trans (trans_no, type, supplier_id, tran_date, reference, ov_amount, rate, supp_reference) + VALUES (".db_escape($trans_no).", ".db_escape($trans_type).", ".db_escape($supp_id).", '".date2sql($date)."'," + .db_escape($ref).", ".db_escape($amount).",".db_escape($rate).",".db_escape($src_ref).")"; + + return db_query($sql, 'cannot write supp_journal'); +} + +//-------------------------------------------------------------------------------- +// Write/update journal entries. +// +function write_journal_entries(&$cart) +{ + global $Refs; + + $date_ = $cart->tran_date; + $ref = $cart->reference; + $memo_ = $cart->memo_; + $trans_type = $cart->trans_type; + $new = $cart->order_id == 0; + + begin_transaction(); + + if (!$new) + { + $msg = void_transaction($trans_type, $cart->order_id, Today(), _("Document reentered.")); + if ($msg) + { + display_error($msg); + return false; + } + } + + $trans_id = $cart->order_id = get_next_trans_no($trans_type); + $total = $cart->gl_items_total_debit(); + + $cart->write_gl(); + + add_journal($trans_type, $trans_id, $total, $date_ , $cart->currency, $ref, + $cart->source_ref, $cart->rate, $cart->event_date, $cart->doc_date); + + $Refs->save($trans_type, $trans_id, $ref); + if ($new) { + add_comments($trans_type, $trans_id, $date_, $memo_); + } else { + update_comments($trans_type, $trans_id, null, $memo_); + } + + add_audit_trail($trans_type, $trans_id, $date_); + + commit_transaction(); + + return $trans_id; +} + +//---------------------------------------------------------------------------------------- + +function void_journal_trans($type, $type_no, $use_transaction=true) +{ + if ($use_transaction) + begin_transaction(); + + $sql = "UPDATE ".TB_PREF."journal SET amount=0 + WHERE type=".db_escape($type)." AND trans_no=".db_escape($type_no); + + $result = db_query($sql, "could not void journal transaction for type=$type and trans_no=$type_no"); + + void_bank_trans($type, $type_no, true); + +// void_gl_trans($type, $type_no, true); // this is done above +// void_trans_tax_details($type, $type_no); // ditto +// void_supp_allocations($type, $type_no); // ditto +// void_cust_allocations($type, $type_no); // ditto + + if ($use_transaction) + commit_transaction(); +} + diff --git a/gl/includes/gl_db.inc b/gl/includes/gl_db.inc index 242ecf04a..2577ecc38 100644 --- a/gl/includes/gl_db.inc +++ b/gl/includes/gl_db.inc @@ -12,6 +12,7 @@ include_once($path_to_root . "/includes/banking.inc"); include_once($path_to_root . "/gl/includes/db/gl_db_trans.inc"); +include_once($path_to_root . "/gl/includes/db/gl_journal.inc"); include_once($path_to_root . "/gl/includes/db/gl_db_bank_trans.inc"); include_once($path_to_root . "/gl/includes/db/gl_db_banking.inc"); include_once($path_to_root . "/gl/includes/db/gl_db_bank_accounts.inc"); diff --git a/gl/includes/ui/gl_journal_ui.inc b/gl/includes/ui/gl_journal_ui.inc index 6384e1fd7..67cbb1557 100644 --- a/gl/includes/ui/gl_journal_ui.inc +++ b/gl/includes/ui/gl_journal_ui.inc @@ -20,48 +20,65 @@ function display_order_header(&$Order) $qes = has_quick_entries(QE_JOURNAL); $new = $Order->order_id==0; - - hidden('ref_original'); start_outer_table(TABLESTYLE2, "width='90%'"); - table_section(1, $qes ? "20%" : ""); + table_section(1); + + date_row(_("Journal Date:"), 'date_', '', $new, 0,0,0,null, true); + if (input_changed('date_')) + { + unset($_POST['ref']); + $Ajax->activate('ref'); + } - date_row(_("Date:"), 'date_', '', $new); + currencies_list_row(_('Currency:'), 'currency', null, true); + if (list_updated('currency')) + unset($_POST['_ex_rate']); + exchange_rate_display(get_company_pref('curr_default'), get_post('currency'), get_post('date_'), true); - table_section(2, $qes ? "20%" : "50%"); - ref_row(_("Reference:"), 'ref', ''); + if (list_updated('currency')) + $Order->clear_items(); + + table_section(2); + + date_row(_("Document Date:"), 'doc_date', '', $new); + date_row(_("Event Date:"), 'event_date', '', $new); + text_row(_("Source ref:"), 'source_ref', null, 30, 60); if ($new) { - table_section(3, "20%"); - start_row(); - check_cells(_("Reverse Transaction:"), 'Reverse', null); - end_row(); - } + table_section(3); + } + + ref_row(_("Reference:"), 'ref', null, get_post('ref'), false, ST_JOURNAL, get_post('date_')); + hidden('ref_original'); if ($qes !== false) { - table_section(3, "40%"); + table_section(3); + quick_entries_list_row(_("Quick Entry").":", 'quick', null, QE_JOURNAL, true); + start_row(); - quick_entries_list_cells(_("Quick Entry").":", 'quick', null, QE_JOURNAL, true); $qid = get_quick_entry(get_post('quick')); if (list_updated('quick')) { unset($_POST['totamount']); // enable default $Ajax->activate('totamount'); } + end_row(); if ($qid['bal_type'] == 1) { - end_row(); - start_row(); $accname = get_gl_account_name($qid['base_desc']); - label_cell(($qid['base_amount'] == 0 ? _("Yearly") : _("Monthly")) . " ". _("balance from account")." ". - $qid['base_desc']." ".$accname."  ".submit('go', _("Go"), false, false, true), "colspan=2"); + label_row(($qid['base_amount'] == 0 ? _("Yearly") : _("Monthly")) . " ". _("balance from account")." ". + $qid['base_desc']." ".$accname."  ".submit('go', _("Go"), false, false, true),'', "colspan=2"); } else - amount_cells($qid['base_desc'].":", 'totamount', price_format($qid['base_amount']), + { + text_row(_('Additional info:'), 'aux_info', null, 35, 255); + amount_row($qid['base_desc'].":", 'totamount', price_format($qid['base_amount']), null, "  ".submit('go', _("Go"), false, false, true)); - end_row(); + } } + check_row(_('Include in tax register:'), 'taxable_trans', null, true); end_outer_table(1); } @@ -75,6 +92,7 @@ function display_gl_items($title, &$order) $dim = get_company_pref('use_dimension'); + $id = find_submit('Edit'); $sub_type = is_subledger_account(get_post('code_id')); $has_subaccounts = $order->has_sub_accounts(); @@ -98,7 +116,6 @@ function display_gl_items($title, &$order) $k = 0; - $id = find_submit('Edit'); if ($id == -1) $id = get_post('Index', -1); @@ -111,6 +128,7 @@ function display_gl_items($title, &$order) $acc = $item->code_id . ($item->person_id ? sprintf(' %05d', $item->person_id) : ''); label_cells($acc, $item->description); + if ($sub_type || $has_subaccounts) label_cell($item->person_name); if ($dim >= 1) @@ -146,7 +164,7 @@ function display_gl_items($title, &$order) if ($order->count_gl_items()) { - $colspan = ($dim == 2 ? "4" : ($dim == 1 ? "3" : "2")); + $colspan = ($dim == 2 ? "4" : ($dim == 1 ? "3" : "2")) + ($sub_type || $has_subaccounts ? 1 : 0); start_row(); label_cell(_("Total"), "align=right colspan=" . $colspan); amount_cell($order->gl_items_total_debit()); @@ -198,8 +216,10 @@ function gl_edit_item_controls(&$order, $dim, $sub_accounts, $Index=null) echo gl_all_accounts_list('code_id', null, $skip_bank, true, _('[Select account]'), true, false, false); if (is_subledger_account(get_post('code_id'))) - { - subledger_list_cells(null, 'person_id', get_post('code_id')); + { // for home currency postings show all customers + $sel_cur = get_post('currency', $order->currency); + subledger_list_cells(null, 'person_id', get_post('code_id'), null, false, false, + get_company_currency() == $sel_cur ? null : $sel_cur); } elseif ($order->has_sub_accounts()) label_cell(''); if ($dim >= 1) @@ -210,28 +230,14 @@ function gl_edit_item_controls(&$order, $dim, $sub_accounts, $Index=null) } else { - - if (!list_updated('code_id')) - { - // Adding a new row - $_POST['AmountDebit'] = ''; //price_format(0); - $_POST['AmountCredit'] = ''; //price_format(0); - $_POST['dimension_id'] = 0; - $_POST['dimension2_id'] = 0; - //$_POST['LineMemo'] = ""; // let memo go to next line Joe Hunt 2010-05-30 - $_POST['_code_id_edit'] = ""; - $_POST['code_id'] = ""; - } - if(isset($_POST['_code_id_update'])) { - $Ajax->activate('code_id'); - } - $skip_bank = !$_SESSION["wa_current_user"]->can_access('SA_BANKJOURNAL'); echo gl_all_accounts_list('code_id', null, $skip_bank, true, _('[Select account]'), true, false, false); - if ($sub_accounts) { - subledger_list_cells(null, 'person_id', get_post('code_id')); + // for home currency postings show all customers + $sel_cur = get_post('currency', $order->currency); + subledger_list_cells(null, 'person_id', get_post('code_id'), null, false, false, + get_company_currency() == $sel_cur ? null : $sel_cur); } elseif ($order->has_sub_accounts()) label_cell(''); @@ -242,6 +248,11 @@ function gl_edit_item_controls(&$order, $dim, $sub_accounts, $Index=null) dimensions_list_cells(null, 'dimension2_id', null, true, " ", false, 2); } + if (get_post('_code_id_update')) + { + $Ajax->activate('code_id'); + set_focus($sub_accounts ? 'person_id' : 'AmountDebit'); + } if ($dim < 1) hidden('dimension_id', 0); if ($dim < 2) diff --git a/includes/db/inventory_db.inc b/includes/db/inventory_db.inc index 225499d4b..dea42fdae 100644 --- a/includes/db/inventory_db.inc +++ b/includes/db/inventory_db.inc @@ -14,11 +14,13 @@ function get_qoh_on_date($stock_id, $location=null, $date_=null) if ($date_ == null) $date_ = Today(); - $date = date2sql($date_); - - $sql = "SELECT SUM(qty) FROM ".TB_PREF."stock_moves - WHERE stock_id=".db_escape($stock_id)." - AND tran_date <= '$date'"; + $date = date2sql($date_); + $sql = "SELECT SUM(qty) + FROM ".TB_PREF."stock_moves st + LEFT JOIN ".TB_PREF."voided v ON st.type=v.type AND st.trans_no=v.id + WHERE ISNULL(v.id) + AND stock_id=".db_escape($stock_id)." + AND tran_date <= '$date'"; if ($location != null) $sql .= " AND loc_code = ".db_escape($location); @@ -242,6 +244,8 @@ function get_purchases_from_trans($stock_id, $from) function adjust_deliveries($stock_id, $material_cost, $to) { + global $Refs; + if (!is_inventory_item($stock_id)) return; @@ -259,7 +263,7 @@ function adjust_deliveries($stock_id, $material_cost, $to) $row = get_purchases_from_trans($stock_id, $from); $purchase_diff = 0; - $old_purchase_cost = 0; + $old_purchase_cost = $new_purchase_cost = 0; if ($row != false) { $old_purchase_cost = $row[1]; @@ -268,28 +272,28 @@ function adjust_deliveries($stock_id, $material_cost, $to) } $diff = $sales_diff - $purchase_diff; - + if ($diff != 0) { - $update_no = get_next_trans_no(ST_COSTUPDATE); - if (!is_date_in_fiscalyear($to)) - $to = end_fiscalyear(); - $stock_gl_code = get_stock_gl_code($stock_id); $dec = user_price_dec(); $old_cost = -round2($old_sales_cost-$old_purchase_cost,$dec); $new_cost = -round2($new_sales_cost-$new_purchase_cost,$dec); - $memo_ = sprintf(_("Cost was %s changed to %s x quantity on hand for item '%s'"), - number_format2($old_cost, 2), number_format2($new_cost, 2), $stock_id); - add_gl_trans_std_cost(ST_COSTUPDATE, $update_no, $to, $stock_gl_code["cogs_account"], - $stock_gl_code["dimension_id"], $stock_gl_code["dimension2_id"], $memo_, $diff); + $cart = new items_cart(ST_COSTUPDATE); + $cart->tran_date = $cart->doc_date = $cart->event_date = $to; + if (!is_date_in_fiscalyear($cart->tran_date)) + $cart->tran_date = end_fiscalyear(); + $cart->reference = $Refs->get_next(ST_COSTUPDATE, null, $cart->tran_date, $to); + + $cart->memo_ = _("Cost was ") . $old_cost. _(" changed to ") . $new_cost . _(" for item ")."'$stock_id'"; + + $cart->add_gl_item($stock_gl_code["cogs_account"], $stock_gl_code["dimension_id"], $stock_gl_code["dimension2_id"], $diff); + $cart->add_gl_item($stock_gl_code["inventory_account"], 0, 0, -$diff); - add_gl_trans_std_cost(ST_COSTUPDATE, $update_no, $to, $stock_gl_code["inventory_account"], 0, 0, $memo_, - -$diff); - add_audit_trail(ST_COSTUPDATE, $update_no, $to); - } + write_journal_entries($cart); + } } function get_stock_gl_code($stock_id) @@ -321,6 +325,10 @@ function handle_negative_inventory($stock_id, $quantity, $standard_cost, $date_) if ($diff != 0) { + begin_transaction(); + add_journal(ST_JOURNAL, $id, $diff, $date_, get_company_currency(), $ref); + $Refs->save(ST_JOURNAL, $id, $ref); + $stock_gl_code = get_stock_gl_code($stock_id); $memo = _("Zero/negative inventory handling"); //Reverse the inventory effect if $qoh <=0 @@ -337,6 +345,7 @@ function handle_negative_inventory($stock_id, $quantity, $standard_cost, $date_) add_audit_trail(ST_JOURNAL, $id, $date_); add_comments(ST_JOURNAL, $id, $date_, $memo); $Refs->save(ST_JOURNAL, $id, $ref); + commit_transaction(); } } } diff --git a/includes/types.inc b/includes/types.inc index 2c233be66..dc2145eb9 100644 --- a/includes/types.inc +++ b/includes/types.inc @@ -243,6 +243,9 @@ define('BO_SUPPLIER', 3); include_once($path_to_root . '/includes/sysnames.inc'); +// tax register type +define('TR_OUTPUT', 0); // sales +define('TR_INPUT', 1); // purchase //--------------------------------------------------------------------------------- // Constants optionally redefined locally // diff --git a/includes/ui/allocation_cart.inc b/includes/ui/allocation_cart.inc index ae8f7d9c6..954209a6b 100644 --- a/includes/ui/allocation_cart.inc +++ b/includes/ui/allocation_cart.inc @@ -33,7 +33,7 @@ class allocation function allocation($type, $trans_no, $person_id = null, $person_type_id=null) { $this->allocs = array(); - + $this->trans_no = $trans_no; $this->type = $type; if ($person_id) @@ -130,10 +130,9 @@ class allocation $this->date_ = sql2date($trans["tran_date"]); $this->person_curr = $trans['curr_code']; $this->currency = isset($trans['bank_curr_code']) ? $trans['bank_curr_code'] : $trans['curr_code']; - $this->bank_amount = @$trans["bank_amount"]; + $this->bank_amount = isset($trans["bank_amount"]) ? $trans["bank_amount"] : $trans["Total"]; // not set for journal entry $this->amount = $trans["Total"]; - } else - $this->date_ = Today(); + } } /* Now populate the array of possible (and previous actual) allocations for this customer/supplier. First get the transactions that have @@ -172,7 +171,6 @@ class allocation while ($myrow = db_fetch($trans_items)) { -//_vd($myrow); $this->add_or_update_item ($myrow["type"], $myrow["trans_no"], sql2date($myrow["tran_date"]), sql2date($myrow["due_date"]), @@ -185,12 +183,14 @@ class allocation // function write() { + global $no_exchange_variations; + begin_transaction(); if ($this->person_type == PT_SUPPLIER) - clear_supp_alloctions($this->type, $this->trans_no, $this->date_); + clear_supp_alloctions($this->type, $this->trans_no, $this->person_id, $this->date_); else - clear_cust_alloctions($this->type, $this->trans_no); + clear_cust_alloctions($this->type, $this->trans_no, $this->person_id, $this->date_); // now add the new allocations $total_allocated = 0; @@ -204,21 +204,22 @@ class allocation if ($this->person_type == PT_SUPPLIER) { add_supp_allocation($amount, $this->type, $this->trans_no, - $alloc_item->type, $alloc_item->type_no, $this->date_); + $alloc_item->type, $alloc_item->type_no, $this->person_id, $this->date_); - update_supp_trans_allocation($alloc_item->type, $alloc_item->type_no); + update_supp_trans_allocation($alloc_item->type, $alloc_item->type_no, $this->person_id); } else { add_cust_allocation($amount, $this->type, $this->trans_no, - $alloc_item->type, $alloc_item->type_no, $this->date_); + $alloc_item->type, $alloc_item->type_no, $this->person_id, $this->date_); - update_debtor_trans_allocation($alloc_item->type, $alloc_item->type_no); + update_debtor_trans_allocation($alloc_item->type, $alloc_item->type_no, $this->person_id); } // Exchange Variations Joe Hunt 2008-09-20 //////////////////// - if (!in_array($alloc_item->type, array(ST_SALESQUOTE, ST_SALESORDER, ST_PURCHORDER))) - exchange_variation($this->type, $this->trans_no, - $alloc_item->type, $alloc_item->type_no, $this->date_, - $amount, $this->person_type); + if ($alloc_item->type != ST_SALESORDER && !@$no_exchange_variations + && $alloc_item->type != ST_PURCHORDER && $alloc_item->type != ST_JOURNAL && $this->type != ST_JOURNAL) + exchange_variation($this->type, $this->trans_no, + $alloc_item->type, $alloc_item->type_no, $this->date_, + $amount, $this->person_type); ////////////////////////////////////////////////////////////// $total_allocated += $alloc_item->current_allocated; @@ -226,9 +227,9 @@ class allocation } /*end of the loop through the array of allocations made */ if ($this->person_type == PT_SUPPLIER) - update_supp_trans_allocation($this->type, $this->trans_no); + update_supp_trans_allocation($this->type, $this->trans_no, $this->person_id); else - update_debtor_trans_allocation($this->type, $this->trans_no); + update_debtor_trans_allocation($this->type, $this->trans_no, $this->person_id); commit_transaction(); @@ -284,7 +285,7 @@ function show_allocatable($show_totals) { if (count($cart->allocs)) { - if ($cart->currency != $cart->person_curr) +// if ($cart->currency != $cart->person_curr) display_heading(sprintf(_("Allocated amounts in %s:"), $cart->person_curr)); start_table(TABLESTYLE, "width='60%'"); $th = array(_("Transaction Type"), _("#"), $supp_ref ? _("Supplier Ref"): _("Ref"), _("Date"), _("Due Date"), _("Amount"), @@ -328,7 +329,8 @@ function show_allocatable($show_totals) { if ($_SESSION['alloc']->type == ST_SUPPCREDIT || $_SESSION['alloc']->type == ST_SUPPAYMENT - || $_SESSION['alloc']->type == ST_BANKPAYMENT) + || $_SESSION['alloc']->type == ST_BANKPAYMENT || + ($_SESSION['alloc']->type == ST_JOURNAL && $_SESSION['alloc']->person_type == PT_SUPPLIER)) $amount = -$amount; */ $amount = abs($cart->amount); @@ -360,7 +362,6 @@ function check_allocations() for ($counter = 0; $counter < get_post("TotalNumberOfAllocs"); $counter++) { if (!isset($_POST['amount'.$counter])) continue; - if (!check_num('amount' . $counter, 0)) { display_error(_("The entry for one or more amounts is invalid or negative.")); @@ -386,7 +387,8 @@ function check_allocations() /* $amount = $_SESSION['alloc']->amount; - if (in_array($_SESSION['alloc']->type, array(ST_BANKPAYMENT, ST_SUPPCREDIT, ST_SUPPAYMENT))) + if (in_array($_SESSION['alloc']->type, array(ST_BANKPAYMENT, ST_SUPPCREDIT, ST_SUPPAYMENT)) || + ($_SESSION['alloc']->type==ST_JOURNAL && $_SESSION['alloc']->person_type == PT_SUPPLIER)) $amount = -$amount; */ $amount = abs($_SESSION['alloc']->amount); @@ -399,3 +401,22 @@ function check_allocations() return true; } + +//---------------------------------------------------------------------------------------- +// +// Returns sales or purchase invoice allocations to be reallocated after invoice edition. +// +function get_inv_allocations($trans_no, $trans_type, $person_id) +{ + $allocs = array(); + if ($trans_type == ST_SUPPINVOICE || $trans_type == ST_SUPPCREDIT) + $result = get_allocatable_from_supp_transactions($person_id, $trans_no, $trans_type); + else + $result = get_allocatable_from_cust_transactions($person_id, $trans_no, $trans_type); + + while($dat = db_fetch($result)) + { + $allocs[] = array('type'=> $dat['type'], 'trans_no'=> $dat['trans_no'], 'amount'=>$dat['alloc']); + } + return $allocs; +} diff --git a/includes/ui/items_cart.inc b/includes/ui/items_cart.inc index c836f487f..e149865f6 100644 --- a/includes/ui/items_cart.inc +++ b/includes/ui/items_cart.inc @@ -23,17 +23,29 @@ class items_cart var $from_loc; var $to_loc; var $tran_date; + var $doc_date; + var $event_date; var $transfer_type; var $increase; var $memo_; var $branch_id; var $reference; var $original_amount; - - function items_cart($type) + var $currency; + var $rate; + var $source_ref; + var $vat_category; + + var $tax_info; // tax info for the GL transaction + + function items_cart($type, $trans_no=0) { $this->trans_type = $type; + $this->order_id = $trans_no; $this->clear_items(); + if (in_array($type, array(ST_LOCTRANSFER, ST_INVADJUST, ST_COSTUPDATE, ST_MANUISSUE, ST_MANURECEIVE, ST_JOURNAL))) + $this->currency = get_company_pref('curr_default'); + $this->rate = 1; } // --------------- line item functions @@ -81,42 +93,25 @@ class items_cart return count($this->line_items); } - /* - Checks cart quantities on document_date. - Returns array of stock_ids which stock quantities would go negative on some day. - */ function check_qoh($location, $date_, $reverse=false) { - $low_stock = array(); - - // collect quantities by stock_id - $qtys = array(); foreach ($this->line_items as $line_no => $line_item) { - $qty = $reverse ? -$line_item->quantity : $line_item->quantity; - - $qtys[$line_item->stock_id]['qty'] = $qty + @$qtys[$line_item->stock_id]['qty']; - $qtys[$line_item->stock_id]['line'] = $line_no; - } - - foreach($qtys as $stock_id => $sum) - { - $fail = check_negative_stock($stock_id, $sum['qty'], $location, $date_); - if ($fail) - $low_stock[] = $stock_id; + $item_ret = $line_item->check_qoh($location, $date_, $reverse); + if ($item_ret != null) + return $line_no; } - - return $low_stock; + return -1; } // ----------- GL item functions - function add_gl_item($code_id, $dimension_id, $dimension2_id, $amount, $reference, $description=null, $person_id=null) + function add_gl_item($code_id, $dimension_id, $dimension2_id, $amount, $memo='', $act_descr=null, $person_id=null) { if (isset($code_id) && $code_id != "" && isset($amount) && isset($dimension_id) && isset($dimension2_id)) { - $this->gl_items[] = new gl_item($code_id, $dimension_id, $dimension2_id, $amount, $reference, $description, $person_id); + $this->gl_items[] = new gl_item($code_id, $dimension_id, $dimension2_id, $amount, $memo, $act_descr, $person_id); return true; } else @@ -128,7 +123,7 @@ class items_cart return false; } - function update_gl_item($index, $code_id, $dimension_id, $dimension2_id, $amount, $reference, $description=null, $person_id=null) + function update_gl_item($index, $code_id, $dimension_id, $dimension2_id, $amount, $memo='', $act_descr=null, $person_id=null) { $this->gl_items[$index]->code_id = $code_id; $this->gl_items[$index]->person_id = $person_id; @@ -137,7 +132,9 @@ class items_cart if ($gl_type) { $this->gl_items[$index]->person_type_id = $gl_type > 0 ? PT_CUSTOMER : PT_SUPPLIER; - $this->gl_items[$index]->person_name = get_subaccount_name($code_id, $person_id); + $data = get_subaccount_data($code_id, $person_id); + $this->gl_items[$index]->person_name = $data['name']; + $this->gl_items[$index]->branch_id = $data['id']; } else { $this->gl_items[$index]->person_type_id = $this->gl_items[$index]->person_name = ''; @@ -145,11 +142,11 @@ class items_cart $this->gl_items[$index]->dimension_id = $dimension_id; $this->gl_items[$index]->dimension2_id = $dimension2_id; $this->gl_items[$index]->amount = $amount; - $this->gl_items[$index]->reference = $reference; - if ($description == null) + $this->gl_items[$index]->reference = $memo; + if ($act_descr == null) $this->gl_items[$index]->description = get_gl_account_name($code_id); else - $this->gl_items[$index]->description = $description; + $this->gl_items[$index]->description = $act_descr; } @@ -216,6 +213,228 @@ class items_cart } return false; } + + // + // Check if cart contains postings to tax accounts + // + function has_taxes() + { + foreach ($this->gl_items as $gl_item) + { + if (is_tax_account($gl_item->code_id)) + return true; + } + return false; + } + + /* + Collect tax info from the GL transaction lines and return as array of values: + 'tax_date' - tax date + 'tax_group' - related counterparty tax group + 'tax_category' - tax category (not set for now) + 'net_amount' - tax amounts array indexed by tax type id + 'tax_in', 'tax_out' - tax amounts array indexed by tax type id + 'tax_reg' - tax register used + */ + function collect_tax_info() + { + $tax_info = array(); + $subledger_sum = $net_sum = 0; + + $tax_info['tax_date'] = $this->tran_date; + $vat_percent = get_company_pref('partial_vat_percent'); + $factor = $vat_percent && ($this->vat_category == VC_PARTIAL) ? $vat_percent/100: 1; + + foreach($this->gl_items as $gl) + { + if ($person_type = is_subledger_account($gl->code_id, $gl->person_id)) + { + $tax_info['person_type'] = $person_type < 0 ? PT_SUPPLIER : PT_CUSTOMER; + $tax_info['person_id'] = $gl->person_id; + + if ($tax_info['person_type'] == PT_CUSTOMER) + { + $branch = get_default_branch($gl->person_id); + $tax_info['tax_group'] = $branch['tax_group_id']; + } else { + $supplier = get_supplier($gl->person_id); + $tax_info['tax_group'] = $supplier['tax_group_id']; + } + $subledger_sum += $gl->amount; + } elseif ($tax_id = is_tax_account($gl->code_id)) + { + $tax_type = get_tax_type($tax_id); + if ($gl->code_id == $tax_type['purchasing_gl_code']) { + if (!isset($tax_info['tax_in'][$tax_id])) + $tax_info['tax_in'][$tax_id] = 0; + $tax_info['tax_in'][$tax_id] += $gl->amount; + $tax_info['tax_reg'] = TR_INPUT; + } else { + if (!isset($tax_info['tax_out'][$tax_id])) + $tax_info['tax_out'][$tax_id] = 0; + $tax_info['tax_out'][$tax_id] -= $gl->amount; + if (!isset($tax_info['tax_reg'])) // TR_INPUT has priority (EU are posted on both accounts) + $tax_info['tax_reg'] = TR_OUTPUT; + } + if ($tax_type['rate']) + { + // assume transaction adjustment for negative tax in/out + $sign = (@$tax_info['tax_in'][$tax_id] < 0 || @$tax_info['tax_out'][$tax_id] < 0) ? -1 : 1; + // we can have both input and output tax postings in some cases like intra-EU trade. + // so just calculate net_amount from the higher in/out tax + $tax_info['net_amount'][$tax_id] + = $sign*round2(max(abs(@$tax_info['tax_in'][$tax_id]), abs(@$tax_info['tax_out'][$tax_id]))/$tax_type['rate']*100, 2)/$factor; + + } + } else + $net_sum += $gl->amount; + } + // if no tax amount posted guess register type from person_type used (e.g. export invoice) + if (!isset($tax_info['tax_reg']) && isset($tax_info['person_type'])) + $tax_info['tax_reg'] = $tax_info['person_type']==PT_CUSTOMER ? TR_OUTPUT : TR_INPUT; + + if (count(@$tax_info['net_amount'])) // guess exempt sales/purchase if any tax has been found + { + $ex_net = abs($net_sum) - @array_sum($tax_info['net_amount']); + if ($ex_net != 0) + $tax_info['net_amount_ex'] = $ex_net; + } + + return $tax_info; + } + + function set_currency($curr, $rate=0) + { + $this->currency = $curr; + $this->rate = $rate; + } + + /* + Reduce number of necessary gl posting lines. + */ + function reduce_gl() + { + /* reduce additional postings */ + $codes = array(); + foreach($this->gl_items as $n => $gl) + { + $prev = @$codes[$gl->code_id][$gl->person_id][$gl->dimension_id][$gl->dimension2_id][$gl->reference]; + if (isset($prev)) { // add amount to previous line for the same gl_code dims and memo + $this->gl_items[$prev]->amount += $gl->amount; + if ($this->gl_items[$prev]->amount == 0) // discard if overall amount==0 + { + unset($this->gl_items[$prev], $codes[$gl->code_id][$gl->person_id][$gl->dimension_id][$gl->dimension2_id][$gl->reference]); + } + unset($this->gl_items[$n]); + } else + $codes[$gl->code_id][$gl->person_id][$gl->dimension_id][$gl->dimension2_id][$gl->reference] = $n; + } + } + /* + Write transaction GL postings, creating tax records and updating AP/AR/bank ledger if needed. + */ + function write_gl($check_balance = true) + { + $delta = $this->gl_items_total(); + if ($check_balance && floatcmp($delta, 0) !=0) + { + $this->add_gl_item(get_company_pref($delta>0 ? 'rounding_db_act' : 'rounding_cr_act'), + 0, 0, -$delta, ''); + error_log(sprintf( _("Rounding error %s encountered for trans_type:%s,trans_no:%s"), $delta, $this->trans_type, $this->order_id)); + } + + $bank_trans = $supp_trans = $cust_trans = array(); + $total_gl = 0; + foreach($this->gl_items as $gl) + { + $total_gl += add_gl_trans($this->trans_type, $this->order_id, $this->tran_date, $gl->code_id, $gl->dimension_id, $gl->dimension2_id, + $gl->reference, $gl->amount, $this->currency, $gl->person_type_id, $gl->person_id, "", $this->rate); + + // post to first found bank account using given gl acount code. + $is_bank_to = is_bank_account($gl->code_id); + if ($is_bank_to && (get_bank_account_currency($is_bank_to) == $this->currency)) // do not register exchange variations in bank trans + { + if (!isset($bank_trans[$is_bank_to])) + $bank_trans[$is_bank_to] = 0; + + $bank_trans[$is_bank_to] += $gl->amount; + } elseif ($gl->person_id) + { + $home_currency = get_company_currency(); + // collect per counterparty amounts (in case more than one posting was done to the account), + // do not post exchange variations to AR/AP (journal in not customer/supplier currency) + if ($gl->person_type_id==PT_SUPPLIER && (get_supplier_currency($gl->person_id) == $this->currency || $this->currency != $home_currency)) + $supp_trans[$gl->person_id] = @$supp_trans[$gl->person_id] + $gl->amount; + else + if ($gl->person_type_id==PT_CUSTOMER && (get_customer_currency(null, $gl->branch_id) == $this->currency || $this->currency != $home_currency)) + $cust_trans[$gl->branch_id] = @$cust_trans[$gl->branch_id] + $gl->amount; + } + + } + // post currency roundings if any + if ($check_balance && floatcmp($total_gl, 0)) + add_gl_trans($this->trans_type, $this->order_id, $this->tran_date, + get_company_pref($total_gl>0 ? 'rounding_db_act' : 'rounding_cr_act'), 0, 0, _('Exchange rate roundings'), -$total_gl); + + // update bank ledger if used + foreach($bank_trans as $bank_id => $amount) + add_bank_trans($this->trans_type, $this->order_id, $bank_id, $this->reference, + $this->tran_date, $amount, 0, "", $this->currency, + "Cannot insert a destination bank transaction"); + + // add AP/AR for journal transaction + if ($this->trans_type == ST_JOURNAL) + { + // update AR + foreach($cust_trans as $branch_id => $amount) + if (floatcmp($amount, 0)) + write_cust_journal($this->trans_type, $this->order_id, $branch_id, $this->tran_date, + $this->reference, -$amount, $this->rate); + // update AP + foreach($supp_trans as $supp_id => $amount) + if (floatcmp($amount, 0)) + write_supp_journal($this->trans_type, $this->order_id, $supp_id, $this->tran_date, + $this->reference, -$amount, $this->rate, $this->source_ref); + } + + // generate tax records for journal transaction + if ($this->trans_type == ST_JOURNAL && is_array($this->tax_info)) + { + foreach($this->tax_info['net_amount'] as $tax_id => $net) + { + if (!$net) + continue; + + // in EU VAT system intra-community goods aquisition is posted to both purchasing and sales tax accounts, + // but included only in purchase register. To avoid double registering ELSE is used below! + if (isset($this->tax_info['tax_in'][$tax_id])) + { + $tax = $this->tax_info['tax_in'][$tax_id]; + $reg = TR_INPUT; + } + elseif (isset($this->tax_info['tax_out'][$tax_id])) + { + $tax = $this->tax_info['tax_out'][$tax_id]; + $reg = TR_OUTPUT; + } + elseif (isset($this->tax_info['tax_reg'])) // e.g. export + { + $tax = 0; + $reg = $this->tax_info['tax_reg']; + } else + continue; + + $tax_nominal = $this->tax_info['rate'][$tax_id]/100*$net; + add_trans_tax_details($this->trans_type, $this->order_id, + $tax_id, $this->tax_info['rate'][$tax_id], 0, $tax_nominal, $net, $this->rate, + $this->tran_date, + $this->source_ref, + $this->tax_info['tax_group'], + $this->tax_info['tax_date'], + $tax, $this->tax_info['tax_category'], 0, $reg); + } + } + } } //-------------------------------------------------------------------------------------------- @@ -257,14 +476,10 @@ class line_item $this->price = 0; } - /* - This method is generally obsolete and subject to removal in FA 2.4 (preserved for now to support 2.3 extensions). - Use items_cart::check_qoh instead. - */ function check_qoh($location, $date_, $reverse) { global $SysPrefs; - + if (!$SysPrefs->allow_negative_stock()) { if (has_stock_holding($this->mb_flag)) @@ -276,9 +491,11 @@ class line_item if ($quantity >= 0) return null; - $fail = check_negative_stock($this->stock_id, $quantity, $location, $date_); - if ($fail) - return $this; + $qoh = get_qoh_on_date($this->stock_id, $location, $date_); + if ($quantity + $qoh < 0) + { + return $this; + } } } @@ -300,16 +517,17 @@ class gl_item var $person_id; var $person_type_id; var $person_name; + var $branch_id; - function gl_item($code_id, $dimension_id, $dimension2_id, $amount, $reference, - $description=null, $person_id=null) + function gl_item($code_id=null, $dimension_id=0, $dimension2_id=0, $amount=0, $memo='', + $act_descr=null, $person_id=null) { //echo "adding $index, $code_id, $dimension_id, $amount, $reference
"; - if ($description == null) + if ($act_descr == null && $code_id) $this->description = get_gl_account_name($code_id); else - $this->description = $description; + $this->description = $act_descr; $this->code_id = $code_id; $this->person_id = $person_id; @@ -317,14 +535,13 @@ class gl_item if ($gl_type) { $this->person_type_id = $gl_type > 0 ? PT_CUSTOMER : PT_SUPPLIER; - $this->person_name = get_subaccount_name($code_id, $person_id); + $data = get_subaccount_data($code_id, $person_id); + $this->person_name = $data['name']; + $this->branch_id = $data['id']; } $this->dimension_id = $dimension_id; $this->dimension2_id = $dimension2_id; - $this->amount = $amount; - $this->reference = $reference; + $this->amount = round($amount, 2); + $this->reference = $memo; } } - -//--------------------------------------------------------------------------------------- - diff --git a/includes/ui/ui_controls.inc b/includes/ui/ui_controls.inc index 616d99b65..89decab4d 100644 --- a/includes/ui/ui_controls.inc +++ b/includes/ui/ui_controls.inc @@ -28,8 +28,8 @@ function get_post($name, $dflt='') } return $ret; } else - return is_float($dflt) ? input_num($name, $dflt) : - ((!isset($_POST[$name]) || $_POST[$name] === '') ? $dflt : $_POST[$name]); + return is_float($dflt) ? input_num($name, $dflt) : + ((!isset($_POST[$name]) /*|| $_POST[$name] === ''*/) ? $dflt : $_POST[$name]); } //--------------------------------------------------------------------------------- $form_nested = -1; @@ -41,7 +41,6 @@ function start_form($multi=false, $dummy=false, $action="", $name="") if (++$form_nested) return; - if ($name != "") $name = "name='$name'"; if ($action == "") @@ -67,10 +66,12 @@ function end_form($breaks=0) br($breaks); hidden('_focus'); hidden('_modified', get_post('_modified', 0)); + hidden('_confirmed'); // helper for final form confirmation hidden('_token', $_SESSION['csrf_token']); echo implode('', $hidden_fields)."\n"; $Ajax->activate('_token'); + $Ajax->activate('_confirmed'); } function check_csrf_token() @@ -186,15 +187,15 @@ function hyperlink_back($center=true, $no_menu=true, $type_no=0, $trans_no=0, $f include_once($path_to_root."/admin/db/attachments_db.inc"); $id = has_attachment($type_no, $trans_no); $attach = get_attachment_string($type_no, $trans_no); - echo $attach; - } + echo $attach; + } $width = ($id != 0 ? "30%" : "20%"); start_table(false, "width='$width'"); start_row(); if ($no_menu) { echo ""._("Print")."\n"; - } + } echo "".($no_menu ? _("Close") : _("Back"))."\n"; end_row(); end_table(); @@ -238,7 +239,7 @@ function viewer_link($label, $url='', $class='', $id='', $icon=null) $pars = access_string($label); if (user_graphic_links() && $icon) $pars[0] = set_icon($icon, $pars[0]); - $preview_str = "$pars[0]"; +- $preview_str = "$pars[0]"; } else $preview_str = $label; @@ -247,7 +248,6 @@ function viewer_link($label, $url='', $class='', $id='', $icon=null) function menu_link($url, $label, $id=null) { - $id = default_focus($id); $pars = access_string($label); return "$pars[0]"; @@ -255,8 +255,7 @@ function menu_link($url, $label, $id=null) function submenu_option($title, $url, $id=null) { - global $path_to_root; - display_note(menu_link($path_to_root . $url, $title, $id), 0, 1); + display_note( menu_link($url, $title, $id), 0, 1); } function submenu_view($title, $type, $number, $id=null) @@ -449,6 +448,28 @@ function tab_changed($name) return array('from' => $from = get_post("_{$name}_sel"), 'to' => $to); } +/* + Check whether tab has been just switched on +*/ +function tab_opened($name, $tab) +{ + return (get_post('_'.$name.'_sel') != $tab) && (find_submit($name.'_', false) == $tab); +} +/* + Check whether tab has been just switched off +*/ +function tab_closed($name, $tab) +{ + return (get_post('_'.$name.'_sel') == $tab) && (find_submit($name.'_', false) != $tab); +} +/* + Check whether tab is visible on current page +*/ +function tab_visible($name, $tab) +{ + $new = find_submit($name.'_', false); + return (get_post('_'.$name.'_sel') == $tab && !$new) || $new==$tab; +} /* Table editor interfaces. Key is editor type 0 => url of editor page @@ -480,7 +501,7 @@ function set_editor($type, $input, $caller=true) $Editors[$key] = array( $path_to_root . $popup_editors[$type][0], $input, $popup_editors[$type][3], $popup_editors[$type][4]); - + $help = 'F' . ($key - 111) . ' - '; $help .= $popup_editors[$type][2]; $Pagehelp[] = $help; @@ -599,7 +620,22 @@ function confirm_dialog($submit, $msg) { } else return get_post('DialogConfirm', 0); } +/* + Confirm dialog to be used optionally in final form checking routine. + Displays warning conditionally unless it was displayed +*/ +function display_confirmation($msg) +{ + global $Ajax; + if (!get_post('_confirmed')) + { + $_POST['_confirmed'] = 1; + display_warning($msg); + return false; + } else + return true; +} /* Block menu/shortcut links during transaction procesing. */ @@ -628,4 +664,3 @@ function page_modified($status = true) } else add_js_source($js); } - diff --git a/includes/ui/ui_input.inc b/includes/ui/ui_input.inc index de9c11531..9ca13632a 100644 --- a/includes/ui/ui_input.inc +++ b/includes/ui/ui_input.inc @@ -37,6 +37,14 @@ function find_submit($prefix, $numeric=true) } return $numeric ? -1 : null; } +/* + Helper function. + Returns true if input $name with $submit_on_change option set is subject to update. +*/ +function input_changed($name) +{ + return isset($_POST['_'.$name.'_changed']); +} //------------------------------------------------------------------------------ // diff --git a/inventory/includes/db/items_trans_db.inc b/inventory/includes/db/items_trans_db.inc index 3c734c270..b1a7f0e8c 100644 --- a/inventory/includes/db/items_trans_db.inc +++ b/inventory/includes/db/items_trans_db.inc @@ -56,15 +56,21 @@ function stock_cost_update($stock_id, $material_cost, $labour_cost, $overhead_co if ($value_of_change != 0) { $stock_gl_code = get_stock_gl_code($stock_id); - $update_no = get_next_trans_no(ST_COSTUPDATE); - $memo_ = sprintf(_("Cost was %s changed to %s x quantity on hand for item '%s'"), - number_format2($last_cost, 2), number_format2($new_cost, 2), $stock_id); - add_gl_trans_std_cost(ST_COSTUPDATE, $update_no, $date_, $stock_gl_code["adjustment_account"], - $stock_gl_code["dimension_id"], $stock_gl_code["dimension2_id"], $memo_, (-$value_of_change)); - add_gl_trans_std_cost(ST_COSTUPDATE, $update_no, $date_, $stock_gl_code["inventory_account"], 0, 0, $memo_, - $value_of_change); + $cart = new items_cart(ST_COSTUPDATE); + $cart->tran_date = $cart->doc_date = $cart->event_date = $date_; + if (!is_date_in_fiscalyear($cart->tran_date)) + $cart->tran_date = end_fiscalyear(); + $cart->reference = $Refs->get_next(ST_COSTUPDATE, null, $cart->tran_date, $date_); + $cart->memo_ = sprintf(_("Cost was %s changed to %s x quantity on hand of %s"), + number_format2($last_cost, 2), number_format2($new_cost), $qoh); + + $cart->add_gl_item($stock_gl_code["adjustment_account"], + $stock_gl_code["dimension_id"], $stock_gl_code["dimension2_id"], -$value_of_change); + $cart->add_gl_item($stock_gl_code["inventory_account"], 0, 0, $value_of_change); + + write_journal_entries($cart); change_stock_moves_std_cost($stock_id, $date_, $new_cost - $last_cost); } } diff --git a/manufacturing/includes/db/work_order_costing_db.inc b/manufacturing/includes/db/work_order_costing_db.inc index 418eacd96..8d8e1517f 100644 --- a/manufacturing/includes/db/work_order_costing_db.inc +++ b/manufacturing/includes/db/work_order_costing_db.inc @@ -110,6 +110,7 @@ function add_overhead_cost($stock_id, $qty, $date_, $costs, $adj_only=false) $ref = $Refs->get_next(ST_JOURNAL); $stock_gl_code = get_stock_gl_code($stock_id); + add_journal(ST_JOURNAL, $id, $costs, $date_, get_company_currency(), $ref); $memo = "WO Overhead cost settlement JV for zero/negative respository of ".$stock_id; //Reverse the inventory effect if $qoh <=0 add_gl_trans_std_cost(ST_JOURNAL, $id, $date_, @@ -163,7 +164,8 @@ function add_labour_cost($stock_id, $qty, $date_, $costs, $adj_only=false) $id = get_next_trans_no(ST_JOURNAL); $ref = $Refs->get_next(ST_JOURNAL); - + add_journal(ST_JOURNAL, $id, $costs, $date_, get_company_currency(), $ref); + $stock_gl_code = get_stock_gl_code($stock_id); $memo = "WO labour cost settlement JV for zero/negative respository of ".$stock_id; //Reverse the inventory effect if $qoh <=0 @@ -176,7 +178,7 @@ function add_labour_cost($stock_id, $qty, $date_, $costs, $adj_only=false) $stock_gl_code["adjustment_account"], $stock_gl_code['dimension_id'], $stock_gl_code['dimension2_id'], $memo, $costs); - + add_audit_trail(ST_JOURNAL, $id, $date_); add_comments(ST_JOURNAL, $id, $date_, $memo); $Refs->save(ST_JOURNAL, $id, $ref); @@ -185,8 +187,8 @@ function add_labour_cost($stock_id, $qty, $date_, $costs, $adj_only=false) } } else - { - if ($qoh + $qty != 0) + { + if ($qoh + $qty != 0) $labour_cost = ($qoh * $labour_cost + $qty * $costs) / ($qoh + $qty); } $sql = "UPDATE ".TB_PREF."stock_master SET labour_cost=".db_escape($labour_cost)." @@ -218,6 +220,7 @@ function add_issue_cost($stock_id, $qty, $date_, $costs, $adj_only=false) $id = get_next_trans_no(ST_JOURNAL); $ref = $Refs->get_next(ST_JOURNAL); + add_journal(ST_JOURNAL, $id, $costs, $date_, get_company_currency(), $ref); $stock_gl_code = get_stock_gl_code($stock_id); $memo = "WO Issue settlement JV for zero/negative respository of ".$stock_id; @@ -272,7 +275,8 @@ function add_wo_costs_journal($wo_id, $amount, $cost_type, $cr_acc, $db_acc, $da add_bank_trans(ST_JOURNAL, $journal_id, $is_bank_to, "", $date, -$amount, PT_WORKORDER, $wo_id, get_company_currency(), "Cannot insert a destination bank transaction"); - } + } else + add_journal(ST_JOURNAL, $journal_id, $amount, $date, get_company_currency(), $ref); add_gl_trans_std_cost(ST_JOURNAL, $journal_id, $date, $db_acc, $dim1, $dim2, $wo_cost_types[$cost_type], $amount); diff --git a/purchasing/includes/db/invoice_db.inc b/purchasing/includes/db/invoice_db.inc index ed8c95328..b14c7199a 100644 --- a/purchasing/includes/db/invoice_db.inc +++ b/purchasing/includes/db/invoice_db.inc @@ -332,7 +332,8 @@ function add_supp_invoice(&$supp_trans) // do not receive as ref because we chan global $Refs; $id = get_next_trans_no(ST_JOURNAL); - $ref = $Refs->get_next(ST_JOURNAL); + $ref = $Refs->get_next(ST_JOURNAL, null, $date_); + add_journal(ST_JOURNAL, $id, $diff, $date_, get_company_currency(), $ref); $stock_id = $entered_grn->item_code; $stock_gl_code = get_stock_gl_code($stock_id); $memo = _("Supplier invoice adjustment for zero inventory of ").$stock_id." "._("Invoice")." ".$supp_trans->reference; @@ -381,9 +382,9 @@ function add_supp_invoice(&$supp_trans) // do not receive as ref because we chan if ($allocate_amount != 0) { add_supp_allocation($allocate_amount, ST_SUPPCREDIT, $invoice_id, ST_SUPPINVOICE, $invoice_no, - $date_); - update_supp_trans_allocation(ST_SUPPINVOICE, $invoice_no); - update_supp_trans_allocation(ST_SUPPCREDIT, $invoice_id); + $supp_trans->supplier_id, $date_); + update_supp_trans_allocation(ST_SUPPINVOICE, $invoice_no, $supp_trans->supplier_id); + update_supp_trans_allocation(ST_SUPPCREDIT, $invoice_id, $supp_trans->supplier_id); exchange_variation(ST_SUPPCREDIT, $invoice_id, ST_SUPPINVOICE, $supp_trans->src_docs, $date_, $allocate_amount, PT_SUPPLIER); @@ -600,6 +601,7 @@ function void_supp_invoice($type, $type_no) //Chaitanya : Post a journal entry $id = get_next_trans_no(ST_JOURNAL); $ref = $Refs->get_next(ST_JOURNAL); + add_journal(ST_JOURNAL, $id, $details_row["quantity"] * $diff, $old_date, get_company_currency(), $ref); $stock_id = $details_row["stock_id"]; $stock_gl_code = get_stock_gl_code($stock_id); $memo = "Reversing Supplier invoice adjustment for zero inventory of ".$stock_id." Invoice: ".$trans['reference']; diff --git a/purchasing/includes/db/suppalloc_db.inc b/purchasing/includes/db/suppalloc_db.inc index 2d1b96bd3..57e76b35f 100644 --- a/purchasing/includes/db/suppalloc_db.inc +++ b/purchasing/includes/db/suppalloc_db.inc @@ -12,15 +12,15 @@ //---------------------------------------------------------------------------------------- function add_supp_allocation($amount, $trans_type_from, $trans_no_from, - $trans_type_to, $trans_no_to, $date_) + $trans_type_to, $trans_no_to, $person_id, $date_) { $date = date2sql($date_); $sql = "INSERT INTO ".TB_PREF."supp_allocations ( amt, date_alloc, - trans_type_from, trans_no_from, trans_no_to, trans_type_to) + trans_type_from, trans_no_from, trans_no_to, trans_type_to, person_id) VALUES (".db_escape($amount).", '$date', " .db_escape($trans_type_from).", ".db_escape($trans_no_from).", " - .db_escape($trans_no_to).", ".db_escape($trans_type_to).")"; + .db_escape($trans_no_to).", ".db_escape($trans_type_to).", ".db_escape($person_id).")"; db_query($sql, "A supplier allocation could not be added to the database"); } @@ -50,48 +50,51 @@ function get_supp_trans_allocation_balance($trans_type, $trans_no) //---------------------------------------------------------------------------------------- // Update supplier trans alloc field according to current status of supp_allocations // -function update_supp_trans_allocation($trans_type, $trans_no) +function update_supp_trans_allocation($trans_type, $trans_no, $person_id) { $sql = "UPDATE `".TB_PREF.($trans_type==ST_PURCHORDER ? 'purch_orders' : 'supp_trans')."` trans, - (SELECT sum(amt) amt from ".TB_PREF."supp_allocations - WHERE (trans_type_to=".db_escape($trans_type)." AND trans_no_to=".db_escape($trans_no).") - OR (trans_type_from=".db_escape($trans_type)." AND trans_no_from=".db_escape($trans_no).")) allocated - SET + (SELECT person_id, sum(amt) amt from ".TB_PREF."supp_allocations + WHERE person_id=".db_escape($person_id)." AND ((trans_type_to=".db_escape($trans_type)." AND trans_no_to=".db_escape($trans_no).") + OR (trans_type_from=".db_escape($trans_type)." AND trans_no_from=".db_escape($trans_no)."))) allocated + SET trans.alloc=IFNULL(allocated.amt, 0) - WHERE " . ($trans_type==ST_PURCHORDER ? + WHERE trans.supplier_id=person_id AND " . ($trans_type==ST_PURCHORDER ? "trans.order_no=".db_escape($trans_no) : "trans.type=".db_escape($trans_type)." AND trans.trans_no=".db_escape($trans_no)); db_query($sql, "The supp transaction record could not be modified for the allocation against it"); } - //------------------------------------------------------------------------------------------------------------- function void_supp_allocations($type, $type_no, $date="") { - return clear_supp_alloctions($type, $type_no, $date); + return clear_supp_alloctions($type, $type_no, null, $date); } //------------------------------------------------------------------------------------------------------------- -function clear_supp_alloctions($type, $type_no, $date="") +function clear_supp_alloctions($type, $type_no, $person_id=null, $date="") { $sql = "UPDATE ".TB_PREF."supp_allocations ca - LEFT JOIN ".TB_PREF."supp_trans paym ON ca.trans_type_from=paym.type AND ca.trans_no_from=paym.trans_no - LEFT JOIN ".TB_PREF."supp_trans st ON ca.trans_type_to=st.type AND ca.trans_no_to=st.trans_no - LEFT JOIN ".TB_PREF."purch_orders po ON ca.trans_type_to=".ST_PURCHORDER." AND ca.trans_no_to=po.order_no + LEFT JOIN ".TB_PREF."supp_trans paym ON ca.trans_type_from=paym.type AND ca.trans_no_from=paym.trans_no AND ca.person_id=paym.supplier_id + LEFT JOIN ".TB_PREF."supp_trans st ON ca.trans_type_to=st.type AND ca.trans_no_to=st.trans_no AND ca.person_id=st.supplier_id + LEFT JOIN ".TB_PREF."purch_orders po ON ca.trans_type_to=".ST_PURCHORDER." AND ca.trans_no_to=po.order_no AND ca.person_id=po.supplier_id SET paym.alloc=paym.alloc - ca.amt, st.alloc=st.alloc - ca.amt, po.alloc=po.alloc - ca.amt - WHERE (ca.trans_type_from=".db_escape($type)." AND ca.trans_no_from=".db_escape($type_no).") - OR (ca.trans_type_to=".db_escape($type)." AND ca.trans_no_to=".db_escape($type_no).")"; - db_query($sql, "could not clear allocation"); + WHERE ((ca.trans_type_from=".db_escape($type)." AND ca.trans_no_from=".db_escape($type_no).") + OR (ca.trans_type_to=".db_escape($type)." AND ca.trans_no_to=".db_escape($type_no)."))"; + if ($person_id) + $sql .= " AND ca.person_id=".db_escape($person_id); + db_query($sql, "could not clear allocation"); // remove any allocations for this transaction $sql = "DELETE FROM ".TB_PREF."supp_allocations - WHERE (trans_type_from=".db_escape($type)." AND trans_no_from=".db_escape($type_no).") - OR (trans_type_to=".db_escape($type)." AND trans_no_to=".db_escape($type_no).")"; + WHERE ((trans_type_from=".db_escape($type)." AND trans_no_from=".db_escape($type_no).") + OR (trans_type_to=".db_escape($type)." AND trans_no_to=".db_escape($type_no)."))"; + if ($person_id) + $sql .= " AND person_id=".db_escape($person_id); db_query($sql, "could not void supp transactions for type=$type and trans_no=$type_no"); // is this necessary? @@ -120,7 +123,7 @@ function get_allocatable_from_supp_sql($supplier_id=null, $settled) .TB_PREF."supp_trans as trans, " .TB_PREF."suppliers as supplier" ." WHERE trans.supplier_id=supplier.supplier_id - AND type IN(".ST_SUPPAYMENT.",".ST_SUPPCREDIT.",".ST_BANKPAYMENT.") AND (trans.ov_amount < 0)"; + AND type IN(".ST_SUPPAYMENT.",".ST_SUPPCREDIT.",".ST_BANKPAYMENT.",".ST_JOURNAL.") AND (trans.ov_amount < 0)"; if (!$settled) $sql .= " AND (round(abs(ov_amount+ov_gst+ov_discount)-alloc,6) > 0)"; @@ -133,6 +136,10 @@ function get_allocatable_from_supp_sql($supplier_id=null, $settled) function get_allocatable_purch_orders($supplier_id = null, $trans_no=null, $type=null) { + $due_dates = "SELECT order_no, MIN(delivery_date) as date + FROM ".TB_PREF."purch_order_details det + GROUP BY det.order_no"; + $sql = "SELECT ".ST_PURCHORDER." as type, porder.order_no as trans_no, @@ -142,14 +149,16 @@ function get_allocatable_purch_orders($supplier_id = null, $trans_no=null, $type supplier.curr_code, total as Total, porder.alloc, - porder.ord_date as due_date, + due_dates.date as due_date, supplier.address, amt, requisition_no as supp_ref FROM ".TB_PREF."purch_orders as porder LEFT JOIN ".TB_PREF."suppliers as supplier ON porder.supplier_id = supplier.supplier_id - LEFT JOIN ".TB_PREF."supp_allocations as alloc ON porder.order_no = alloc.trans_no_to AND alloc.trans_type_to=".ST_PURCHORDER." + LEFT JOIN ".TB_PREF."supp_allocations as alloc + ON porder.order_no = alloc.trans_no_to AND alloc.trans_type_to=".ST_PURCHORDER." AND alloc.person_id=porder.supplier_id LEFT JOIN ".TB_PREF."grn_batch as grn ON porder.order_no = grn.purch_order_no + LEFT JOIN ($due_dates) due_dates ON due_dates.order_no=porder.order_no WHERE total>0"; if ($trans_no != null and $type != null) @@ -159,7 +168,9 @@ function get_allocatable_purch_orders($supplier_id = null, $trans_no=null, $type } else { - $sql .= " AND round(prep_amount) > 0 AND ISNULL(grn.purch_order_no)"; // only sales orders with prepayment level set and no yet received +// FIXME: change to form below when prepayments terms finally can be selected in PO entry form: +// $sql .= " AND round(prep_amount) > 0 AND ISNULL(grn.purch_order_no)"; // only sales orders with prepayment level set and no yet received + $sql .= " AND ISNULL(grn.purch_order_no)"; // only sales orders no yet received } if ($supplier_id) $sql .= " AND porder.supplier_id=".db_escape($supplier_id); @@ -187,7 +198,8 @@ function get_allocatable_to_supp_transactions($supplier_id=null, $trans_no=null, supp_reference FROM ".TB_PREF."supp_trans as trans - LEFT JOIN ".TB_PREF."supp_allocations as alloc ON trans.trans_no = alloc.trans_no_to AND trans.type = alloc.trans_type_to," + LEFT JOIN ".TB_PREF."supp_allocations as alloc + ON trans.trans_no = alloc.trans_no_to AND trans.type = alloc.trans_type_to AND alloc.person_id=trans.supplier_id," .TB_PREF."suppliers as supplier WHERE trans.supplier_id=supplier.supplier_id"; @@ -208,9 +220,10 @@ function get_allocatable_to_supp_transactions($supplier_id=null, $trans_no=null, $orders = get_allocatable_purch_orders($supplier_id, $trans_no, $type); $sql = "($sql ORDER BY trans_no) \nUNION \n($orders)"; -//_vd($sql); + return db_query($sql." ORDER BY due_date", "Cannot retreive alloc to transactions"); } + //------------------------------------------------------------------------------------------------------------- function get_allocatable_from_supp_transactions($supplier_id, $trans_no=null, $type=null) @@ -234,7 +247,8 @@ function get_allocatable_from_supp_transactions($supplier_id, $trans_no=null, $t .TB_PREF."supp_allocations as alloc WHERE trans.supplier_id=supplier.supplier_id AND trans.trans_no = alloc.trans_no_from - AND trans.type = alloc.trans_type_from"; + AND trans.type = alloc.trans_type_from + AND trans.supplier_id = alloc.person_id"; if ($trans_no != null and $type != null) { @@ -247,15 +261,14 @@ function get_allocatable_from_supp_transactions($supplier_id, $trans_no=null, $t AND trans.type NOT IN (".implode(',',array(ST_SUPPAYMENT,ST_BANKPAYMENT)).")"; $sql .= " GROUP BY type, trans_no"; } - +//_vd($sql); return db_query($sql." ORDER BY due_date", "Cannot retreive alloc to transactions"); } - -function get_sql_for_supplier_allocation_inquiry($from, $to, $filter, $supplier_id, $all=false) +function get_sql_for_supplier_allocation_inquiry() { - $date_after = date2sql($from); - $date_to = date2sql($to); + $date_after = date2sql($_POST['TransAfterDate']); + $date_to = date2sql($_POST['TransToDate']); $sql = "SELECT trans.type, @@ -271,38 +284,40 @@ function get_sql_for_supplier_allocation_inquiry($from, $to, $filter, $supplier_ ((trans.type = ".ST_SUPPINVOICE." OR trans.type = ".ST_SUPPCREDIT.") AND trans.due_date < '" . date2sql(Today()) . "') AS OverDue, trans.supplier_id FROM " - .TB_PREF."supp_trans as trans, " + .TB_PREF."supp_trans as trans + LEFT JOIN ".TB_PREF."voided as v + ON trans.trans_no=v.id AND trans.type=v.type," .TB_PREF."suppliers as supplier WHERE supplier.supplier_id = trans.supplier_id AND trans.tran_date >= '$date_after' - AND trans.tran_date <= '$date_to'"; - - if ($supplier_id != ALL_TEXT) - $sql .= " AND trans.supplier_id = ".db_escape($supplier_id); + AND trans.tran_date <= '$date_to' + AND ISNULL(v.date_)"; - if ($filter != ALL_TEXT) + if ($_POST['supplier_id'] != ALL_TEXT) + $sql .= " AND trans.supplier_id = ".db_escape($_POST['supplier_id']); + if (isset($_POST['filterType']) && $_POST['filterType'] != ALL_TEXT) { - if (($filter == '1') || ($filter == '2')) + if (($_POST['filterType'] == '1') || ($_POST['filterType'] == '2')) // invoices { $sql .= " AND trans.type = ".ST_SUPPINVOICE." "; } - elseif ($filter == '3') + elseif ($_POST['filterType'] == '3') // payments { $sql .= " AND trans.type = ".ST_SUPPAYMENT." "; } - elseif (($filter == '4') || ($filter == '5')) + elseif (($_POST['filterType'] == '4') || ($_POST['filterType'] == '5')) // credits { $sql .= " AND trans.type = ".ST_SUPPCREDIT." "; } - if (($filter == '2') || ($filter == '5')) + if (($_POST['filterType'] == '2') || ($_POST['filterType'] == '5')) // overdude { $today = date2sql(Today()); $sql .= " AND trans.due_date < '$today' "; } } - if (!$all) + if (!check_value('showSettled')) { $sql .= " AND (round(abs(ov_amount + ov_gst + ov_discount) - alloc,6) != 0) "; } diff --git a/purchasing/includes/db/suppliers_db.inc b/purchasing/includes/db/suppliers_db.inc index c3a3b798c..affdb6270 100644 --- a/purchasing/includes/db/suppliers_db.inc +++ b/purchasing/includes/db/suppliers_db.inc @@ -93,7 +93,8 @@ function get_supplier_details($supplier_id, $to=null, $all=true) if ($all) $value = "(trans.ov_amount + trans.ov_gst + trans.ov_discount)"; else - $value = "IF (trans.type=".ST_SUPPINVOICE." OR trans.type=".ST_BANKDEPOSIT.", + $value = "IF (trans.type=".ST_SUPPINVOICE." OR trans.type=".ST_BANKDEPOSIT." + OR (trans.type=".ST_JOURNAL." AND (trans.ov_amount + trans.ov_gst + trans.ov_discount)>0), (trans.ov_amount + trans.ov_gst + trans.ov_discount - trans.alloc), (trans.ov_amount + trans.ov_gst + trans.ov_discount + trans.alloc))"; $due = "IF (trans.type=".ST_SUPPINVOICE." OR trans.type=".ST_SUPPCREDIT.",trans.due_date,trans.tran_date)"; diff --git a/purchasing/includes/purchasing_db.inc b/purchasing/includes/purchasing_db.inc index 149b42d9d..5182313a5 100644 --- a/purchasing/includes/purchasing_db.inc +++ b/purchasing/includes/purchasing_db.inc @@ -219,9 +219,9 @@ function add_direct_supp_trans($cart) if ($cart->cash_account) { $pmt_no = write_supp_payment(0, $inv->supplier_id, $cart->cash_account, $inv->tran_date, $Refs->get_next(ST_SUPPAYMENT), $total, 0, _('Payment for:').$inv->supp_reference .' ('.$type_shortcuts[ST_SUPPINVOICE].$inv_no.')'); - add_supp_allocation($total, ST_SUPPAYMENT, $pmt_no, ST_SUPPINVOICE, $inv_no, $inv->tran_date); - update_supp_trans_allocation(ST_SUPPINVOICE, $inv_no); - update_supp_trans_allocation(ST_SUPPAYMENT, $pmt_no); + add_supp_allocation($total, ST_SUPPAYMENT, $pmt_no, ST_SUPPINVOICE, $inv_no, $inv->supplier_id, $inv->tran_date); + update_supp_trans_allocation(ST_SUPPINVOICE, $inv_no, $inv->supplier_id); + update_supp_trans_allocation(ST_SUPPAYMENT, $pmt_no, $inv->supplier_id); } commit_transaction(); // save PO+GRN+PI(+SP) return $inv_no; diff --git a/reporting/includes/reporting.inc b/reporting/includes/reporting.inc index 114696c38..68c443ea4 100644 --- a/reporting/includes/reporting.inc +++ b/reporting/includes/reporting.inc @@ -116,9 +116,11 @@ function print_document_link($doc_no, $link_text, $link=true, $type_no, 'PARAM_3' => '', 'PARAM_4' => $def_orientation); break; + default: + return null; // default: $ar = array(); } - + return print_link($link_text, $rep, $ar, "", $icon, $class, $id); } // diff --git a/sales/includes/db/branches_db.inc b/sales/includes/db/branches_db.inc index 52c41a786..80f00a6d2 100644 --- a/sales/includes/db/branches_db.inc +++ b/sales/includes/db/branches_db.inc @@ -251,3 +251,13 @@ function _get_branch_contacts($branch_code, $action=null, $customer_id=null, $de return $results; } +function get_default_branch($customer_id, $ar_account=null) +{ + $sql = "SELECT * + FROM ".TB_PREF."cust_branch WHERE debtor_no = ".db_escape($customer_id); + if($ar_account) + $sql .= " AND receivables_account=".db_escape($ar_account); + $result = db_query($sql,"cannot retrieve default branch"); + return db_fetch($result); +} + diff --git a/sales/includes/db/cust_trans_db.inc b/sales/includes/db/cust_trans_db.inc index 65db5a753..dfca4cc81 100644 --- a/sales/includes/db/cust_trans_db.inc +++ b/sales/includes/db/cust_trans_db.inc @@ -300,6 +300,7 @@ function get_sql_for_customer_inquiry($from, $to, $cust_id = ALL_TEXT, $filter = debtor.name, branch.br_name, debtor.curr_code, + debtor.debtor_no, (trans.ov_amount + trans.ov_gst + trans.ov_freight + trans.ov_freight_tax + trans.ov_discount) AS TotalAmount, "; if ($filter != ALL_TEXT) @@ -312,17 +313,21 @@ function get_sql_for_customer_inquiry($from, $to, $cust_id = ALL_TEXT, $filter = $sql .= "trans.alloc AS Allocated, ((trans.type = ".ST_SALESINVOICE.") AND trans.due_date < '" . date2sql(Today()) . "') AS OverDue , - Sum(line.quantity-line.qty_done) AS Outstanding + Sum(line.quantity-line.qty_done) AS Outstanding, + Sum(line.qty_done) AS HasChild FROM " .TB_PREF."debtor_trans as trans LEFT JOIN ".TB_PREF."debtor_trans_details as line - ON trans.trans_no=line.debtor_trans_no AND trans.type=line.debtor_trans_type," - .TB_PREF."debtors_master as debtor, " - .TB_PREF."cust_branch as branch + ON trans.trans_no=line.debtor_trans_no AND trans.type=line.debtor_trans_type + LEFT JOIN ".TB_PREF."voided as v + ON trans.trans_no=v.id AND trans.type=v.type + LEFT JOIN ".TB_PREF."cust_branch as branch ON trans.branch_code=branch.branch_code," + .TB_PREF."debtors_master as debtor WHERE debtor.debtor_no = trans.debtor_no AND trans.tran_date >= '$date_after' AND trans.tran_date <= '$date_to' - AND trans.branch_code = branch.branch_code"; + AND trans.branch_code = branch.branch_code + AND ISNULL(v.date_)"; if ($cust_id != ALL_TEXT) $sql .= " AND trans.debtor_no = ".db_escape($cust_id); diff --git a/sales/includes/db/custalloc_db.inc b/sales/includes/db/custalloc_db.inc index 099e8420f..42eaff595 100644 --- a/sales/includes/db/custalloc_db.inc +++ b/sales/includes/db/custalloc_db.inc @@ -12,13 +12,14 @@ //---------------------------------------------------------------------------------------- function add_cust_allocation($amount, $trans_type_from, $trans_no_from, - $trans_type_to, $trans_no_to) + $trans_type_to, $trans_no_to, $person_id, $date_) { + $date = date2sql($date_); $sql = "INSERT INTO ".TB_PREF."cust_allocations ( amt, date_alloc, - trans_type_from, trans_no_from, trans_no_to, trans_type_to) - VALUES ($amount, Now(), ".db_escape($trans_type_from).", ".db_escape($trans_no_from).", ".db_escape($trans_no_to) - .", ".db_escape($trans_type_to).")"; + trans_type_from, trans_no_from, trans_no_to, trans_type_to, person_id) + VALUES ($amount, '$date', ".db_escape($trans_type_from).", ".db_escape($trans_no_from).", ".db_escape($trans_no_to) + .", ".db_escape($trans_type_to).", ".db_escape($person_id).")"; db_query($sql, "A customer allocation could not be added to the database"); } @@ -32,54 +33,62 @@ function delete_cust_allocation($trans_id) return db_query($sql, "The existing allocation $trans_id could not be deleted"); } +//---------------------------------------------------------------------------------------- + +function get_cust_allocation($trans_id) +{ + $sql = "SELECT * FROM ".TB_PREF."cust_allocations WHERE id = ".db_escape($trans_id); + return db_fetch(db_query($sql), "Cannot retrieve customer allocation $trans_id"); +} + //---------------------------------------------------------------------------------------- // Update debtor trans alloc field according to current status of cust_allocations // -function update_debtor_trans_allocation($trans_type, $trans_no) +function update_debtor_trans_allocation($trans_type, $trans_no, $person_id) { - $sql = "UPDATE `".TB_PREF."debtor_trans` trans, - (SELECT sum(amt) amt from ".TB_PREF."cust_allocations - WHERE (trans_type_to=".db_escape($trans_type)." AND trans_no_to=".db_escape($trans_no).") - OR (trans_type_from=".db_escape($trans_type)." AND trans_no_from=".db_escape($trans_no).")) allocated + $sql = + "UPDATE `".TB_PREF.($trans_type==ST_SALESORDER ? 'sales_orders' : 'debtor_trans')."` trans, + (SELECT sum(amt) amt FROM ".TB_PREF."cust_allocations + WHERE person_id=".db_escape($person_id)." AND ((trans_type_to=".db_escape($trans_type)." AND trans_no_to=".db_escape($trans_no).") + OR (trans_type_from=".db_escape($trans_type)." AND trans_no_from=".db_escape($trans_no)."))) allocated SET trans.alloc=IFNULL(allocated.amt,0) - WHERE trans.type=".db_escape($trans_type)." AND trans_no=".db_escape($trans_no); - + WHERE trans.debtor_no=".db_escape($person_id)." AND ".($trans_type==ST_SALESORDER ? + "trans.trans_type=".db_escape($trans_type)." AND order_no=".db_escape($trans_no) + : "trans.type=".db_escape($trans_type)." AND trans_no=".db_escape($trans_no)); db_query($sql, "The debtor transaction record could not be modified for the allocation against it"); } -function get_cust_allocation($trans_id) -{ - $sql = "SELECT * FROM ".TB_PREF."cust_allocations WHERE id = ".db_escape($trans_id); - return db_fetch(db_query($sql), "Cannot retrieve customer allocation $trans_id"); -} - //------------------------------------------------------------------------------------------------------------- - +// function void_cust_allocations($type, $type_no, $date="") { - return clear_cust_alloctions($type, $type_no, $date); + return clear_cust_alloctions($type, $type_no, null, $date); } //------------------------------------------------------------------------------------------------------------- - -function clear_cust_alloctions($type, $type_no, $date="") +// +function clear_cust_alloctions($type, $type_no, $person_id=null, $date="") { $sql = "UPDATE ".TB_PREF."cust_allocations ca - LEFT JOIN ".TB_PREF."debtor_trans paym ON ca.trans_type_from=paym.type AND ca.trans_no_from=paym.trans_no - LEFT JOIN ".TB_PREF."debtor_trans dt ON ca.trans_type_to=dt.type AND ca.trans_no_to=dt.trans_no - LEFT JOIN ".TB_PREF."sales_orders so ON ca.trans_type_to=so.trans_type AND ca.trans_no_to=so.order_no + LEFT JOIN ".TB_PREF."debtor_trans paym ON ca.trans_type_from=paym.type AND ca.trans_no_from=paym.trans_no AND ca.person_id=paym.debtor_no + LEFT JOIN ".TB_PREF."debtor_trans dt ON ca.trans_type_to=dt.type AND ca.trans_no_to=dt.trans_no AND ca.person_id=dt.debtor_no + LEFT JOIN ".TB_PREF."sales_orders so ON ca.trans_type_to=so.trans_type AND ca.trans_no_to=so.order_no AND ca.person_id=so.debtor_no SET paym.alloc=paym.alloc - ca.amt, dt.alloc=dt.alloc - ca.amt, so.alloc=so.alloc - ca.amt - WHERE (ca.trans_type_from=".db_escape($type)." AND ca.trans_no_from=".db_escape($type_no).") - OR (ca.trans_type_to=".db_escape($type)." AND ca.trans_no_to=".db_escape($type_no).")"; - db_query($sql, "could not clear allocation"); + WHERE ((ca.trans_type_from=".db_escape($type)." AND ca.trans_no_from=".db_escape($type_no).") + OR (ca.trans_type_to=".db_escape($type)." AND ca.trans_no_to=".db_escape($type_no)."))"; + if ($person_id) + $sql .= " AND ca.person_id=".db_escape($person_id); + db_query($sql, "could not clear allocation"); // remove any allocations for this transaction $sql = "DELETE FROM ".TB_PREF."cust_allocations - WHERE (trans_type_from=".db_escape($type)." AND trans_no_from=".db_escape($type_no).") - OR (trans_type_to=".db_escape($type)." AND trans_no_to=".db_escape($type_no).")"; + WHERE ((trans_type_from=".db_escape($type)." AND trans_no_from=".db_escape($type_no).") + OR (trans_type_to=".db_escape($type)." AND trans_no_to=".db_escape($type_no)."))"; + if ($person_id) + $sql .= " AND person_id=".db_escape($person_id); db_query($sql, "could not void debtor transactions for type=$type and trans_no=$type_no"); // is this necessary? @@ -105,12 +114,13 @@ function get_allocatable_from_cust_sql($customer_id=null, $settled) trans.version, round(abs(ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount-alloc),6) <= 0 AS settled, trans.debtor_no + FROM " .TB_PREF."debtor_trans as trans, " .TB_PREF."debtors_master as debtor" ." WHERE trans.debtor_no=debtor.debtor_no AND (((type=".ST_CUSTPAYMENT." OR type=".ST_BANKDEPOSIT.") AND (trans.ov_amount > 0))" - ." OR (type=".ST_CUSTCREDIT." AND (ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount)>0))"; + ." OR ( (type=".ST_CUSTCREDIT. " OR type=".ST_JOURNAL. ") AND (ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount)>0))"; if (!$settled) $sql .= " AND (round(abs(ov_amount+ov_gst+ov_freight+ov_freight_tax-ov_discount-alloc),6) > 0)"; @@ -135,10 +145,13 @@ function get_allocatable_sales_orders($customer_id = null, $trans_no=null, $type sorder.delivery_date as due_date, debtor.address, sorder.version, - amt + amt, + sorder.debtor_no, + sorder.branch_code FROM ".TB_PREF."sales_orders as sorder LEFT JOIN ".TB_PREF."debtors_master as debtor ON sorder.debtor_no = debtor.debtor_no - LEFT JOIN ".TB_PREF."cust_allocations as alloc ON sorder.order_no = alloc.trans_no_to AND sorder.trans_type = alloc.trans_type_to + LEFT JOIN ".TB_PREF."cust_allocations as alloc + ON sorder.order_no = alloc.trans_no_to AND sorder.trans_type = alloc.trans_type_to AND alloc.person_id=sorder.debtor_no LEFT JOIN (SELECT order_, sum(prep_amount) amount FROM ".TB_PREF."debtor_trans dt WHERE prep_amount>0 AND dt.type=".ST_SALESINVOICE." GROUP BY order_) as invoiced ON sorder.order_no = invoiced.order_ WHERE sorder.trans_type=".ST_SALESORDER; @@ -170,14 +183,17 @@ function get_allocatable_to_cust_transactions($customer_id = null, $trans_no=nul trans.tran_date, debtor.name AS DebtorName, debtor.curr_code, - ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount AS Total, + IF(prep_amount, prep_amount, ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount) AS Total, trans.alloc, trans.due_date, debtor.address, trans.version, - amt + amt, + trans.debtor_no, + trans.branch_code FROM ".TB_PREF."debtor_trans as trans - LEFT JOIN ".TB_PREF."cust_allocations as alloc ON trans.trans_no = alloc.trans_no_to AND trans.type = alloc.trans_type_to," + LEFT JOIN ".TB_PREF."cust_allocations as alloc + ON trans.trans_no = alloc.trans_no_to AND trans.type = alloc.trans_type_to AND alloc.person_id=trans.debtor_no," .TB_PREF."debtors_master as debtor WHERE trans.debtor_no=debtor.debtor_no"; @@ -191,10 +207,23 @@ function get_allocatable_to_cust_transactions($customer_id = null, $trans_no=nul } else { - $sql .= " AND round(IF(prep_amount, prep_amount, ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount)-alloc,6) > 0 - AND trans.type NOT IN (".implode(',',array(ST_CUSTPAYMENT,ST_BANKDEPOSIT,ST_CUSTCREDIT,ST_CUSTDELIVERY)).")"; + $sql .= " + AND ( + trans.type='".ST_SALESINVOICE."' + AND round(IF(prep_amount, prep_amount, ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount)-alloc,6) > 0 + OR + trans.type='". ST_CUSTCREDIT."' + AND round(-IF(prep_amount, prep_amount, ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount)-alloc,6) > 0 + OR + trans.type = '". ST_JOURNAL."' + AND ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount<0 + OR + trans.type = '". ST_BANKPAYMENT."' + AND ov_amount+ov_gst+ov_freight+ov_freight_tax+ov_discount>0 + )"; $sql .= " GROUP BY type, trans_no"; } + $orders = get_allocatable_sales_orders($customer_id, $trans_no, $type); $sql = "($sql ORDER BY trans_no) \nUNION \n($orders)"; @@ -218,13 +247,15 @@ function get_allocatable_from_cust_transactions($customer_id, $trans_no=null, $t trans.due_date, debtor.address, trans.version, - amt + amt, + trans.debtor_no FROM ".TB_PREF."debtor_trans as trans," .TB_PREF."debtors_master as debtor," .TB_PREF."cust_allocations as alloc WHERE trans.debtor_no=debtor.debtor_no AND trans.trans_no = alloc.trans_no_from - AND trans.type = alloc.trans_type_from"; + AND trans.type = alloc.trans_type_from + AND trans.debtor_no = alloc.person_id"; if ($trans_no != null and $type != null) { @@ -258,12 +289,12 @@ function get_sql_for_customer_allocation_inquiry($from, $to, $customer, $filterT trans.due_date, debtor.name, debtor.curr_code, - debtor.debtor_no, (trans.ov_amount + trans.ov_gst + trans.ov_freight + trans.ov_freight_tax + trans.ov_discount) AS TotalAmount, trans.alloc AS Allocated, ((trans.type = ".ST_SALESINVOICE.") - AND trans.due_date < '" . date2sql(Today()) . "') AS OverDue + AND trans.due_date < '" . date2sql(Today()) . "') AS OverDue, + trans.debtor_no FROM " .TB_PREF."debtor_trans as trans, " .TB_PREF."debtors_master as debtor @@ -312,23 +343,22 @@ function get_sql_for_customer_allocation_inquiry($from, $to, $customer, $filterT ."trans.ov_freight + trans.ov_freight_tax + " ."trans.ov_discount)) - trans.alloc,6) != 0) "; } - return $sql; } function credit_sales_invoice_allocate($invoice_no, $credit_no, $amount, $date) { - $sql = "SELECT ov_freight+ov_gst+ov_amount+ov_freight_tax as total, alloc FROM ".TB_PREF."debtor_trans + $sql = "SELECT ov_freight+ov_gst+ov_amount+ov_freight_tax as total, alloc, debtor_no FROM ".TB_PREF."debtor_trans WHERE (`type`=".ST_SALESINVOICE." AND trans_no=".db_escape($invoice_no).")"; $result = db_query($sql, "can't retrieve invoice totals"); $invoice = db_fetch($result); $free = $invoice['total'] - $invoice['alloc']; - + if ($free < $amount) { // if there is not enough unallocated amount - remove some payment allocations $sql = "SELECT * FROM ".TB_PREF."cust_allocations - WHERE (trans_type_to=".ST_SALESINVOICE." AND trans_no_to=".db_escape($invoice_no).") + WHERE (trans_type_to=".ST_SALESINVOICE." AND trans_no_to=".db_escape($invoice_no)." AND person_id=".db_escape($invoice['debtor_no']).") AND trans_type_from <> ".ST_CUSTCREDIT; $result = db_query($sql, "can't retrieve invoice allocations"); @@ -338,10 +368,10 @@ function credit_sales_invoice_allocate($invoice_no, $credit_no, $amount, $date) delete_cust_allocation($alloc['id']); if ($unalloc < $alloc['amt']) add_cust_allocation($alloc['amt']-$unalloc, $alloc['trans_type_from'], - $alloc['trans_no_from'], ST_SALESINVOICE, $invoice_no); + $alloc['trans_no_from'], ST_SALESINVOICE, $invoice_no, $invoice['debtor_no'], $date); - update_debtor_trans_allocation($alloc['trans_type_to'], $alloc['trans_no_to']); - update_debtor_trans_allocation($alloc['trans_type_from'], $alloc['trans_no_from']); + update_debtor_trans_allocation($alloc['trans_type_to'], $alloc['trans_no_to'], $invoice['debtor_no']); + update_debtor_trans_allocation($alloc['trans_type_from'], $alloc['trans_no_from'], $invoice['debtor_no']); $free += $unalloc; } } @@ -352,12 +382,11 @@ function credit_sales_invoice_allocate($invoice_no, $credit_no, $amount, $date) Check all credit notes allocated to this invoice for summarized freight charges.")); return false; } - update_debtor_trans_allocation(ST_SALESINVOICE, $invoice_no); - update_debtor_trans_allocation(ST_CUSTCREDIT, $credit_no); - add_cust_allocation($amount, ST_CUSTCREDIT, $credit_no, ST_SALESINVOICE, $invoice_no); + add_cust_allocation($amount, ST_CUSTCREDIT, $credit_no, ST_SALESINVOICE, $invoice_no, $invoice['debtor_no'], $date); + update_debtor_trans_allocation(ST_SALESINVOICE, $invoice_no, $invoice['debtor_no']); + update_debtor_trans_allocation(ST_CUSTCREDIT, $credit_no, $invoice['debtor_no']); exchange_variation(ST_CUSTCREDIT, $credit_no, ST_SALESINVOICE, $invoice_no, $date, $amount, PT_CUSTOMER); return true; } - diff --git a/sales/includes/db/customers_db.inc b/sales/includes/db/customers_db.inc index 2be25faca..3f7e6598c 100644 --- a/sales/includes/db/customers_db.inc +++ b/sales/includes/db/customers_db.inc @@ -70,12 +70,11 @@ function get_customer_details($customer_id, $to=null, $all=true) $past1 = get_company_pref('past_due_days'); $past2 = 2 * $past1; // removed - debtor_trans.alloc from all summations + $sign = "IF(`type` IN(".implode(',', array(ST_CUSTCREDIT,ST_CUSTPAYMENT,ST_BANKDEPOSIT,ST_JOURNAL))."), -1, 1)"; if ($all) - $value = "IFNULL(IF(trans.type=11 OR trans.type=12 OR trans.type=2, -1, 1) - * (trans.ov_amount + trans.ov_gst + trans.ov_freight + trans.ov_freight_tax + trans.ov_discount),0)"; + $value = "IFNULL($sign*(trans.ov_amount + trans.ov_gst + trans.ov_freight + trans.ov_freight_tax + trans.ov_discount),0)"; else - $value = "IFNULL(IF(trans.type=11 OR trans.type=12 OR trans.type=2, -1, 1) - * (trans.ov_amount + trans.ov_gst + trans.ov_freight + trans.ov_freight_tax + trans.ov_discount - + $value = "IFNULL($sign*(trans.ov_amount + trans.ov_gst + trans.ov_freight + trans.ov_freight_tax + trans.ov_discount - trans.alloc),0)"; $due = "IF (trans.type=10, trans.due_date, trans.tran_date)"; $sql = "SELECT ".TB_PREF."debtors_master.name, ".TB_PREF."debtors_master.curr_code, ".TB_PREF."payment_terms.terms, @@ -188,9 +187,11 @@ function get_customer_by_ref($reference) //---------------------------------------------------------------------------------- -function get_customer_currency($customer_id) +function get_customer_currency($customer_id=null, $branch_id=null) { - $sql = "SELECT curr_code FROM ".TB_PREF."debtors_master WHERE debtor_no = ".db_escape($customer_id); + $sql = "SELECT curr_code FROM ".TB_PREF."debtors_master cust + LEFT JOIN ".TB_PREF."cust_branch branch ON branch.debtor_no=cust.debtor_no + WHERE " .(isset($branch_id) ? "branch_code = ".db_escape($branch_id) : "cust.debtor_no = ".db_escape($customer_id)); $result = db_query($sql, "Retreive currency of customer $customer_id"); diff --git a/sales/includes/db/sales_invoice_db.inc b/sales/includes/db/sales_invoice_db.inc index c38d69542..f1ead0c6d 100644 --- a/sales/includes/db/sales_invoice_db.inc +++ b/sales/includes/db/sales_invoice_db.inc @@ -197,7 +197,7 @@ function write_sales_invoice(&$invoice) $invoice->Branch, $invoice->pos['pos_account'], $date_, $Refs->get_next(ST_CUSTPAYMENT), $amount-$discount, $discount, _('Cash invoice').' '.$invoice_no); - add_cust_allocation($amount, ST_CUSTPAYMENT, $pmtno, ST_SALESINVOICE, $invoice_no); + add_cust_allocation($amount, ST_CUSTPAYMENT, $pmtno, ST_SALESINVOICE, $invoice_no, $invoice->customer_id, $date_); update_debtor_trans_allocation(ST_SALESINVOICE, $invoice_no); update_debtor_trans_allocation(ST_CUSTPAYMENT, $pmtno); diff --git a/sql/alter2.4.sql b/sql/alter2.4.sql index 8b74324fa..eedb05662 100644 --- a/sql/alter2.4.sql +++ b/sql/alter2.4.sql @@ -154,3 +154,49 @@ WHERE si.grn_item_id=-1 AND (gl.dimension_id OR gl.dimension2_id) ALTER TABLE `0_quick_entries` ADD COLUMN `usage` varchar(120) NULL AFTER `description`; ALTER TABLE `0_quick_entry_lines` ADD COLUMN `memo` tinytext NOT NULL AFTER `amount`; + +# multiply allocations to single jiurnal transaction +ALTER TABLE `0_cust_allocations` ADD COLUMN `person_id` int(11) DEFAULT NULL AFTER `id`; +UPDATE `0_cust_allocations` alloc LEFT JOIN `0_debtor_trans` trans ON alloc.trans_no_to=trans.trans_no AND alloc.trans_type_to=trans.type + SET alloc.person_id = trans.debtor_no; + +ALTER TABLE `0_supp_allocations` ADD COLUMN `person_id` int(11) DEFAULT NULL AFTER `id`; +UPDATE `0_supp_allocations` alloc LEFT JOIN `0_supp_trans` trans ON alloc.trans_no_to=trans.trans_no AND alloc.trans_type_to=trans.type + SET alloc.person_id = trans.supplier_id; + +ALTER TABLE `0_cust_allocations` DROP KEY `trans_type_from`; +ALTER TABLE `0_cust_allocations` ADD UNIQUE KEY(`person_id`,`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`); +ALTER TABLE `0_supp_allocations` DROP KEY `trans_type_from`; +ALTER TABLE `0_supp_allocations` ADD UNIQUE KEY(`person_id`,`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`); + +# full support for any journal transaction +DROP TABLE IF EXISTS `0_journal`; +CREATE TABLE `0_journal` ( + `type` smallint(6) NOT NULL DEFAULT '0', + `trans_no` int(11) NOT NULL DEFAULT '0', + `tran_date` date DEFAULT '0000-00-00', + `reference` varchar(60) NOT NULL DEFAULT '', + `source_ref` varchar(60) NOT NULL DEFAULT '', + `event_date` date DEFAULT '0000-00-00', + `doc_date` date NOT NULL DEFAULT '0000-00-00', + `currency` char(3) NOT NULL DEFAULT '', + `amount` double NOT NULL DEFAULT '0', + `rate` double NOT NULL DEFAULT '1', + PRIMARY KEY `Type_and_Number` (`type`,`trans_no`), + KEY `tran_date` (`tran_date`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8 ; + +INSERT INTO `0_journal` (`type`, `trans_no`, `tran_date`, `reference`, `event_date`,`doc_date`,`currency`,`amount`) + SELECT `gl`.`type`, `gl`.`type_no`, `gl`.`tran_date`, `ref`.`reference`, `gl`.`event_date`, + `gl`.`doc_date`, `sys_curr`.`value`, SUM(IF(`gl`.`amount`>0,`gl`.`amount`,0)) + FROM `0_gl_trans` gl LEFT JOIN `0_refs` ref ON gl.type = ref.type AND gl.type_no=ref.id + LEFT JOIN `0_sys_prefs` sys_curr ON `sys_curr`.`name`='curr_default' + WHERE `gl`.`type` IN(0, 35) + GROUP BY `type`,`type_no`; + +# allow multiply customers.suppliers in single journal transaction +ALTER TABLE `0_debtor_trans` DROP PRIMARY KEY; +ALTER TABLE `0_debtor_trans` ADD PRIMARY KEY (`type`,`trans_no`, `debtor_no`); +ALTER TABLE `0_supp_trans` DROP PRIMARY KEY; +ALTER TABLE `0_supp_trans` ADD PRIMARY KEY (`type`,`trans_no`, `supplier_id`); + diff --git a/sql/en_US-demo.sql b/sql/en_US-demo.sql index aced2220f..f286b1436 100644 --- a/sql/en_US-demo.sql +++ b/sql/en_US-demo.sql @@ -563,6 +563,7 @@ INSERT INTO `0_currencies` VALUES('DK Kroner', 'DKK', 'kr', 'Denmark', 'Ore', 1, DROP TABLE IF EXISTS `0_cust_allocations`; CREATE TABLE IF NOT EXISTS `0_cust_allocations` ( `id` int(11) NOT NULL auto_increment, + `person_id` int(11) DEFAULT NULL, `amt` double unsigned default NULL, `date_alloc` date NOT NULL default '0000-00-00', `trans_no_from` int(11) default NULL, @@ -570,7 +571,7 @@ CREATE TABLE IF NOT EXISTS `0_cust_allocations` ( `trans_no_to` int(11) default NULL, `trans_type_to` int(11) default NULL, PRIMARY KEY (`id`), - UNIQUE KEY (`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), + UNIQUE KEY `trans_type_from` (`person_id`,`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), KEY `From` (`trans_type_from`,`trans_no_from`), KEY `To` (`trans_type_to`,`trans_no_to`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=2 ; @@ -579,7 +580,7 @@ CREATE TABLE IF NOT EXISTS `0_cust_allocations` ( -- Dumping data for table `0_cust_allocations` -- -INSERT INTO `0_cust_allocations` VALUES(1, 37.68, '2014-06-21', 3, 11, 18, 10); +INSERT INTO `0_cust_allocations` VALUES(1, 3, 37.68, '2014-06-21', 3, 11, 18, 10); -- -------------------------------------------------------- @@ -1108,6 +1109,27 @@ CREATE TABLE IF NOT EXISTS `0_item_units` ( INSERT INTO `0_item_units` VALUES('each', 'Each', 0, 0); INSERT INTO `0_item_units` VALUES('hr', 'Hours', 1, 0); +--- Structure of table `0_journal` + +DROP TABLE IF EXISTS `0_journal`; +CREATE TABLE `0_journal` ( + `type` smallint(6) NOT NULL DEFAULT '0', + `trans_no` int(11) NOT NULL DEFAULT '0', + `tran_date` date DEFAULT '0000-00-00', + `reference` varchar(60) NOT NULL DEFAULT '', + `source_ref` varchar(60) NOT NULL DEFAULT '', + `event_date` date DEFAULT '0000-00-00', + `doc_date` date NOT NULL DEFAULT '0000-00-00', + `currency` char(3) NOT NULL DEFAULT '', + `amount` double NOT NULL DEFAULT '0', + `rate` double NOT NULL DEFAULT '1', + PRIMARY KEY (`type`,`trans_no`), + KEY `tran_date` (`tran_date`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8 ; + +--- Data of table `0_journal` + + -- -------------------------------------------------------- -- @@ -1916,6 +1938,7 @@ INSERT INTO `0_suppliers` VALUES(3, 'Money Makers Ltd.', 'Money Makers', 'Mailin DROP TABLE IF EXISTS `0_supp_allocations`; CREATE TABLE IF NOT EXISTS `0_supp_allocations` ( `id` int(11) NOT NULL auto_increment, + `person_id` int(11) DEFAULT NULL, `amt` double unsigned default NULL, `date_alloc` date NOT NULL default '0000-00-00', `trans_no_from` int(11) default NULL, @@ -1923,7 +1946,7 @@ CREATE TABLE IF NOT EXISTS `0_supp_allocations` ( `trans_no_to` int(11) default NULL, `trans_type_to` int(11) default NULL, PRIMARY KEY (`id`), - UNIQUE KEY (`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), + UNIQUE KEY `trans_type_from` (`person_id`,`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), KEY `From` (`trans_type_from`,`trans_no_from`), KEY `To` (`trans_type_to`,`trans_no_to`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=2 ; @@ -1932,7 +1955,7 @@ CREATE TABLE IF NOT EXISTS `0_supp_allocations` ( -- Dumping data for table `0_supp_allocations` -- -INSERT INTO `0_supp_allocations` VALUES(1, 3465, '2014-06-21', 4, 22, 7, 20); +INSERT INTO `0_supp_allocations` VALUES(1, 2, 3465, '2014-06-21', 4, 22, 7, 20); -- -------------------------------------------------------- diff --git a/sql/en_US-new.sql b/sql/en_US-new.sql index b5ccd6782..b4191c003 100644 --- a/sql/en_US-new.sql +++ b/sql/en_US-new.sql @@ -529,6 +529,7 @@ INSERT INTO `0_currencies` VALUES('Pounds', 'GBP', '?', 'England', 'Pence', 1, 0 DROP TABLE IF EXISTS `0_cust_allocations`; CREATE TABLE IF NOT EXISTS `0_cust_allocations` ( `id` int(11) NOT NULL auto_increment, + `person_id` int(11) DEFAULT NULL, `amt` double unsigned default NULL, `date_alloc` date NOT NULL default '0000-00-00', `trans_no_from` int(11) default NULL, @@ -536,7 +537,7 @@ CREATE TABLE IF NOT EXISTS `0_cust_allocations` ( `trans_no_to` int(11) default NULL, `trans_type_to` int(11) default NULL, PRIMARY KEY (`id`), - UNIQUE KEY (`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), + UNIQUE KEY `trans_type_from` (`person_id`,`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), KEY `From` (`trans_type_from`,`trans_no_from`), KEY `To` (`trans_type_to`,`trans_no_to`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ; @@ -954,6 +955,27 @@ CREATE TABLE IF NOT EXISTS `0_item_units` ( INSERT INTO `0_item_units` VALUES('each', 'Each', 0, 0); INSERT INTO `0_item_units` VALUES('hr', 'Hours', 0, 0); +--- Structure of table `0_journal` + +DROP TABLE IF EXISTS `0_journal`; +CREATE TABLE `0_journal` ( + `type` smallint(6) NOT NULL DEFAULT '0', + `trans_no` int(11) NOT NULL DEFAULT '0', + `tran_date` date DEFAULT '0000-00-00', + `reference` varchar(60) NOT NULL DEFAULT '', + `source_ref` varchar(60) NOT NULL DEFAULT '', + `event_date` date DEFAULT '0000-00-00', + `doc_date` date NOT NULL DEFAULT '0000-00-00', + `currency` char(3) NOT NULL DEFAULT '', + `amount` double NOT NULL DEFAULT '0', + `rate` double NOT NULL DEFAULT '1', + PRIMARY KEY (`type`,`trans_no`), + KEY `tran_date` (`tran_date`) +) ENGINE=InnoDB DEFAULT CHARSET=utf8 ; + +--- Data of table `0_journal` + + -- -------------------------------------------------------- -- @@ -1686,6 +1708,7 @@ CREATE TABLE IF NOT EXISTS `0_suppliers` ( DROP TABLE IF EXISTS `0_supp_allocations`; CREATE TABLE IF NOT EXISTS `0_supp_allocations` ( `id` int(11) NOT NULL auto_increment, + `person_id` int(11) DEFAULT NULL, `amt` double unsigned default NULL, `date_alloc` date NOT NULL default '0000-00-00', `trans_no_from` int(11) default NULL, @@ -1693,7 +1716,7 @@ CREATE TABLE IF NOT EXISTS `0_supp_allocations` ( `trans_no_to` int(11) default NULL, `trans_type_to` int(11) default NULL, PRIMARY KEY (`id`), - UNIQUE KEY (`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), + UNIQUE KEY `trans_type_from` (`person_id`,`trans_type_from`,`trans_no_from`,`trans_type_to`,`trans_no_to`), KEY `From` (`trans_type_from`,`trans_no_from`), KEY `To` (`trans_type_to`,`trans_no_to`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;