dolibarr  19.0.0-dev
accountingaccount.class.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2013-2014 Olivier Geffroy <jeff@jeffinfo.com>
3  * Copyright (C) 2013-2021 Alexandre Spangaro <aspangaro@open-dsi.fr>
4  * Copyright (C) 2013-2021 Florian Henry <florian.henry@open-concept.pro>
5  * Copyright (C) 2014 Juanjo Menent <jmenent@2byte.es>
6  * Copyright (C) 2015 Ari Elbaz (elarifr) <github@accedinfo.com>
7  * Copyright (C) 2018 Frédéric France <frederic.france@netlogic.fr>
8  *
9  * This program is free software; you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 3 of the License, or
12  * (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program. If not, see <https://www.gnu.org/licenses/>.
21  */
22 
29 require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
30 require_once DOL_DOCUMENT_ROOT.'/societe/class/societe.class.php';
31 require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
32 
37 {
41  public $element = 'accounting_account';
42 
46  public $table_element = 'accounting_account';
47 
51  public $picto = 'billr';
52 
57  public $ismultientitymanaged = 1;
58 
63  public $restrictiononfksoc = 1;
64 
68  public $db;
69 
73  public $id;
74 
78  public $rowid;
79 
85  public $datec;
86 
90  public $fk_pcg_version;
91 
95  public $pcg_type;
96 
100  public $account_number;
101 
105  public $account_parent;
106 
110  public $account_category;
111 
115  public $account_category_label;
116 
120  public $status;
121 
125  public $label;
126 
130  public $labelshort;
131 
135  public $fk_user_author;
136 
140  public $fk_user_modif;
141 
145  public $active;
146 
150  public $reconcilable;
151 
155  private $accountingaccount_codetotid_cache = array();
156 
157 
158  const STATUS_ENABLED = 1;
159  const STATUS_DISABLED = 0;
160 
161 
167  public function __construct($db)
168  {
169  global $conf;
170 
171  $this->db = $db;
172  $this->next_prev_filter = "fk_pcg_version IN (SELECT pcg_version FROM ".MAIN_DB_PREFIX."accounting_system WHERE rowid = ".((int) getDolGlobalInt('CHARTOFACCOUNTS')).")"; // Used to add a filter in Form::showrefnav method
173  }
174 
184  public function fetch($rowid = null, $account_number = null, $limittocurrentchart = 0, $limittoachartaccount = '')
185  {
186  global $conf;
187 
188  if ($rowid || $account_number) {
189  $sql = "SELECT a.rowid as rowid, a.datec, a.tms, a.fk_pcg_version, a.pcg_type, a.account_number, a.account_parent, a.label, a.labelshort, a.fk_accounting_category, a.fk_user_author, a.fk_user_modif, a.active, a.reconcilable";
190  $sql .= ", ca.label as category_label";
191  $sql .= " FROM ".MAIN_DB_PREFIX."accounting_account as a";
192  $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."c_accounting_category as ca ON a.fk_accounting_category = ca.rowid";
193  $sql .= " WHERE";
194  if ($rowid) {
195  $sql .= " a.rowid = ".(int) $rowid;
196  } elseif ($account_number) {
197  $sql .= " a.account_number = '".$this->db->escape($account_number)."'";
198  $sql .= " AND a.entity = ".$conf->entity;
199  }
200  if (!empty($limittocurrentchart)) {
201  $sql .= ' AND a.fk_pcg_version IN (SELECT pcg_version FROM '.MAIN_DB_PREFIX.'accounting_system WHERE rowid = '.((int) getDolGlobalInt('CHARTOFACCOUNTS')).')';
202  }
203  if (!empty($limittoachartaccount)) {
204  $sql .= " AND a.fk_pcg_version = '".$this->db->escape($limittoachartaccount)."'";
205  }
206 
207  dol_syslog(get_class($this)."::fetch rowid=".$rowid." account_number=".$account_number, LOG_DEBUG);
208 
209  $result = $this->db->query($sql);
210  if ($result) {
211  $obj = $this->db->fetch_object($result);
212 
213  if ($obj) {
214  $this->id = $obj->rowid;
215  $this->rowid = $obj->rowid;
216  $this->ref = $obj->account_number;
217  $this->datec = $this->db->jdate($obj->datec);
218  $this->date_creation = $this->db->jdate($obj->datec);
219  $this->date_modification = $this->db->jdate($obj->tms);
220  //$this->tms = $this->datem;
221  $this->fk_pcg_version = $obj->fk_pcg_version;
222  $this->pcg_type = $obj->pcg_type;
223  $this->account_number = $obj->account_number;
224  $this->account_parent = $obj->account_parent;
225  $this->label = $obj->label;
226  $this->labelshort = $obj->labelshort;
227  $this->account_category = $obj->fk_accounting_category;
228  $this->account_category_label = $obj->category_label;
229  $this->fk_user_author = $obj->fk_user_author;
230  $this->fk_user_modif = $obj->fk_user_modif;
231  $this->active = $obj->active;
232  $this->status = $obj->active;
233  $this->reconcilable = $obj->reconcilable;
234 
235  return $this->id;
236  } else {
237  return 0;
238  }
239  } else {
240  $this->error = "Error ".$this->db->lasterror();
241  $this->errors[] = "Error ".$this->db->lasterror();
242  }
243  }
244  return -1;
245  }
246 
254  public function create($user, $notrigger = 0)
255  {
256  global $conf;
257  $error = 0;
258  $now = dol_now();
259 
260  // Clean parameters
261  if (isset($this->fk_pcg_version)) {
262  $this->fk_pcg_version = trim($this->fk_pcg_version);
263  }
264  if (isset($this->pcg_type)) {
265  $this->pcg_type = trim($this->pcg_type);
266  }
267  if (isset($this->account_number)) {
268  $this->account_number = trim($this->account_number);
269  }
270  if (isset($this->label)) {
271  $this->label = trim($this->label);
272  }
273  if (isset($this->labelshort)) {
274  $this->labelshort = trim($this->labelshort);
275  }
276 
277  if (empty($this->pcg_type) || $this->pcg_type == '-1') {
278  $this->pcg_type = 'XXXXXX';
279  }
280  // Check parameters
281  // Put here code to add control on parameters values
282 
283  // Insert request
284  $sql = "INSERT INTO " . MAIN_DB_PREFIX . "accounting_account(";
285  $sql .= "datec";
286  $sql .= ", entity";
287  $sql .= ", fk_pcg_version";
288  $sql .= ", pcg_type";
289  $sql .= ", account_number";
290  $sql .= ", account_parent";
291  $sql .= ", label";
292  $sql .= ", labelshort";
293  $sql .= ", fk_accounting_category";
294  $sql .= ", fk_user_author";
295  $sql .= ", active";
296  $sql .= ", reconcilable";
297  $sql .= ") VALUES (";
298  $sql .= " '".$this->db->idate($now)."'";
299  $sql .= ", ".((int) $conf->entity);
300  $sql .= ", ".(empty($this->fk_pcg_version) ? 'NULL' : "'".$this->db->escape($this->fk_pcg_version)."'");
301  $sql .= ", ".(empty($this->pcg_type) ? 'NULL' : "'".$this->db->escape($this->pcg_type)."'");
302  $sql .= ", ".(empty($this->account_number) ? 'NULL' : "'".$this->db->escape($this->account_number)."'");
303  $sql .= ", ".(empty($this->account_parent) ? 0 : (int) $this->account_parent);
304  $sql .= ", ".(empty($this->label) ? "''" : "'".$this->db->escape($this->label)."'");
305  $sql .= ", ".(empty($this->labelshort) ? "''" : "'".$this->db->escape($this->labelshort)."'");
306  $sql .= ", ".(empty($this->account_category) ? 0 : (int) $this->account_category);
307  $sql .= ", ".((int) $user->id);
308  $sql .= ", ".(int) $this->active;
309  $sql .= ", ".(int) $this->reconcilable;
310  $sql .= ")";
311 
312  $this->db->begin();
313 
314  dol_syslog(get_class($this)."::create", LOG_DEBUG);
315  $resql = $this->db->query($sql);
316  if (!$resql) {
317  $error++;
318  $this->errors[] = "Error " . $this->db->lasterror();
319  }
320 
321  if (!$error) {
322  $this->id = $this->db->last_insert_id(MAIN_DB_PREFIX . "accounting_account");
323 
324  // Uncomment this and change MYOBJECT to your own tag if you
325  // want this action to call a trigger.
326  //if (! $error && ! $notrigger) {
327 
328  // // Call triggers
329  // $result=$this->call_trigger('MYOBJECT_CREATE',$user);
330  // if ($result < 0) $error++;
331  // // End call triggers
332  //}
333  }
334 
335  // Commit or rollback
336  if ($error) {
337  foreach ($this->errors as $errmsg) {
338  dol_syslog(get_class($this) . "::create " . $errmsg, LOG_ERR);
339  $this->error .= ($this->error ? ', ' . $errmsg : $errmsg);
340  }
341  $this->db->rollback();
342  return -1 * $error;
343  } else {
344  $this->db->commit();
345  return $this->id;
346  }
347  }
348 
355  public function update($user)
356  {
357  // Check parameters
358  if (empty($this->pcg_type) || $this->pcg_type == '-1') {
359  $this->pcg_type = 'XXXXXX';
360  }
361 
362  $this->db->begin();
363 
364  $sql = "UPDATE " . MAIN_DB_PREFIX . "accounting_account ";
365  $sql .= " SET fk_pcg_version = " . ($this->fk_pcg_version ? "'" . $this->db->escape($this->fk_pcg_version) . "'" : "null");
366  $sql .= " , pcg_type = " . ($this->pcg_type ? "'" . $this->db->escape($this->pcg_type) . "'" : "null");
367  $sql .= " , account_number = '" . $this->db->escape($this->account_number) . "'";
368  $sql .= " , account_parent = " . (int) $this->account_parent;
369  $sql .= " , label = " . ($this->label ? "'" . $this->db->escape($this->label) . "'" : "''");
370  $sql .= " , labelshort = " . ($this->labelshort ? "'" . $this->db->escape($this->labelshort) . "'" : "''");
371  $sql .= " , fk_accounting_category = " . (empty($this->account_category) ? 0 : (int) $this->account_category);
372  $sql .= " , fk_user_modif = " . ((int) $user->id);
373  $sql .= " , active = " . (int) $this->active;
374  $sql .= " , reconcilable = " . (int) $this->reconcilable;
375  $sql .= " WHERE rowid = " . ((int) $this->id);
376 
377  dol_syslog(get_class($this)."::update", LOG_DEBUG);
378  $result = $this->db->query($sql);
379  if ($result) {
380  $this->db->commit();
381  return 1;
382  } else {
383  if ($this->db->lasterrno() == 'DB_ERROR_RECORD_ALREADY_EXISTS') {
384  $this->error = $this->db->lasterror();
385  $this->db->rollback();
386  return -2;
387  }
388 
389  $this->error = $this->db->lasterror();
390  $this->db->rollback();
391  return -1;
392  }
393  }
394 
400  public function checkUsage()
401  {
402  global $langs;
403 
404  $sql = "(SELECT fk_code_ventilation FROM ".MAIN_DB_PREFIX."facturedet";
405  $sql .= " WHERE fk_code_ventilation=".((int) $this->id).")";
406  $sql .= "UNION";
407  $sql .= " (SELECT fk_code_ventilation FROM ".MAIN_DB_PREFIX."facture_fourn_det";
408  $sql .= " WHERE fk_code_ventilation=".((int) $this->id).")";
409 
410  dol_syslog(get_class($this)."::checkUsage", LOG_DEBUG);
411  $resql = $this->db->query($sql);
412 
413  if ($resql) {
414  $num = $this->db->num_rows($resql);
415  if ($num > 0) {
416  $this->error = $langs->trans('ErrorAccountancyCodeIsAlreadyUse');
417  return 0;
418  } else {
419  return 1;
420  }
421  } else {
422  $this->error = $this->db->lasterror();
423  return -1;
424  }
425  }
426 
434  public function delete($user, $notrigger = 0)
435  {
436  $error = 0;
437 
438  $result = $this->checkUsage();
439 
440  if ($result > 0) {
441  $this->db->begin();
442 
443  if (!$error) {
444  $sql = "DELETE FROM " . MAIN_DB_PREFIX . "accounting_account";
445  $sql .= " WHERE rowid=" . ((int) $this->id);
446 
447  dol_syslog(get_class($this) . "::delete sql=" . $sql);
448  $resql = $this->db->query($sql);
449  if (!$resql) {
450  $error++;
451  $this->errors[] = "Error " . $this->db->lasterror();
452  }
453  }
454 
455  // Commit or rollback
456  if ($error) {
457  foreach ($this->errors as $errmsg) {
458  dol_syslog(get_class($this) . "::delete " . $errmsg, LOG_ERR);
459  $this->error .= ($this->error ? ', ' . $errmsg : $errmsg);
460  }
461  $this->db->rollback();
462  return -1 * $error;
463  } else {
464  $this->db->commit();
465  return 1;
466  }
467  } else {
468  return -1;
469  }
470  }
471 
485  public function getNomUrl($withpicto = 0, $withlabel = 0, $nourl = 0, $moretitle = '', $notooltip = 0, $save_lastsearch_value = -1, $withcompletelabel = 0, $option = '')
486  {
487  global $langs, $conf, $hookmanager;
488  require_once DOL_DOCUMENT_ROOT . '/core/lib/accounting.lib.php';
489 
490  if (!empty($conf->dol_no_mouse_hover)) {
491  $notooltip = 1; // Force disable tooltips
492  }
493 
494  $result = '';
495 
496  $url = '';
497  $labelurl = '';
498  if (empty($option) || $option == 'ledger') {
499  $url = DOL_URL_ROOT . '/accountancy/bookkeeping/listbyaccount.php?search_accountancy_code_start=' . urlencode($this->account_number) . '&search_accountancy_code_end=' . urlencode($this->account_number);
500  $labelurl = $langs->trans("ShowAccountingAccountInLedger");
501  } elseif ($option == 'journals') {
502  $url = DOL_URL_ROOT . '/accountancy/bookkeeping/list.php?search_accountancy_code_start=' . urlencode($this->account_number) . '&search_accountancy_code_end=' . urlencode($this->account_number);
503  $labelurl = $langs->trans("ShowAccountingAccountInJournals");
504  } elseif ($option == 'accountcard') {
505  $url = DOL_URL_ROOT . '/accountancy/admin/card.php?id=' . urlencode($this->id);
506  $labelurl = $langs->trans("ShowAccountingAccount");
507  }
508 
509  // Add param to save lastsearch_values or not
510  $add_save_lastsearch_values = ($save_lastsearch_value == 1 ? 1 : 0);
511  if ($save_lastsearch_value == -1 && preg_match('/list\.php/', $_SERVER["PHP_SELF"])) {
512  $add_save_lastsearch_values = 1;
513  }
514  if ($add_save_lastsearch_values) {
515  $url .= '&save_lastsearch_values=1';
516  }
517 
518  $picto = 'accounting_account';
519  $label = '';
520 
521  if (empty($this->labelshort) || $withcompletelabel == 1) {
522  $labeltoshow = $this->label;
523  } else {
524  $labeltoshow = $this->labelshort;
525  }
526 
527  $label = '<u>' . $labelurl . '</u>';
528  if (!empty($this->account_number)) {
529  $label .= '<br><b>' . $langs->trans('AccountAccounting') . ':</b> ' . length_accountg($this->account_number);
530  }
531  if (!empty($labeltoshow)) {
532  $label .= '<br><b>' . $langs->trans('Label') . ':</b> ' . $labeltoshow;
533  }
534  if ($moretitle) {
535  $label .= ' - ' . $moretitle;
536  }
537 
538  $linkclose = '';
539  if (empty($notooltip)) {
540  if (!empty($conf->global->MAIN_OPTIMIZEFORTEXTBROWSER)) {
541  $label = $labelurl;
542  $linkclose .= ' alt="' . dol_escape_htmltag($label, 1) . '"';
543  }
544  $linkclose .= ' title="' . dol_escape_htmltag($label, 1) . '"';
545  $linkclose .= ' class="classfortooltip"';
546  }
547 
548  $linkstart = '<a href="' . $url . '"';
549  $linkstart .= $linkclose . '>';
550  $linkend = '</a>';
551 
552  if ($nourl) {
553  $linkstart = '';
554  $linkclose = '';
555  $linkend = '';
556  }
557 
558  $label_link = length_accountg($this->account_number);
559  if ($withlabel) {
560  $label_link .= ' - ' . ($nourl ? '<span class="opacitymedium">' : '') . $labeltoshow . ($nourl ? '</span>' : '');
561  }
562 
563  if ($withpicto) {
564  $result .= ($linkstart . img_object(($notooltip ? '' : $label), $picto, ($notooltip ? '' : 'class="classfortooltip"'), 0, 0, $notooltip ? 0 : 1) . $linkend);
565  }
566  if ($withpicto && $withpicto != 2) {
567  $result .= ' ';
568  }
569  if ($withpicto != 2) {
570  $result .= $linkstart . $label_link . $linkend;
571  }
572  global $action;
573  $hookmanager->initHooks(array($this->element . 'dao'));
574  $parameters = array('id'=>$this->id, 'getnomurl' => &$result);
575  $reshook = $hookmanager->executeHooks('getNomUrl', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
576  if ($reshook > 0) {
577  $result = $hookmanager->resPrint;
578  } else {
579  $result .= $hookmanager->resPrint;
580  }
581  return $result;
582  }
583 
590  public function info($id)
591  {
592  $sql = 'SELECT a.rowid, a.datec, a.fk_user_author, a.fk_user_modif, a.tms as date_modification';
593  $sql .= ' FROM ' . MAIN_DB_PREFIX . 'accounting_account as a';
594  $sql .= ' WHERE a.rowid = ' . ((int) $id);
595 
596  dol_syslog(get_class($this) . '::info sql=' . $sql);
597  $resql = $this->db->query($sql);
598 
599  if ($resql) {
600  if ($this->db->num_rows($resql)) {
601  $obj = $this->db->fetch_object($resql);
602  $this->id = $obj->rowid;
603 
604  $this->user_creation_id = $obj->fk_user_author;
605  $this->user_modification_id = $obj->fk_user_modif;
606  $this->date_creation = $this->db->jdate($obj->datec);
607  $this->date_modification = $this->db->jdate($obj->date_modification);
608  }
609  $this->db->free($resql);
610  } else {
611  dol_print_error($this->db);
612  }
613  }
614 
622  public function accountDeactivate($id, $mode = 0)
623  {
624  $result = $this->checkUsage();
625 
626  $fieldtouse = 'active';
627  if ($mode == 1) {
628  $fieldtouse = 'reconcilable';
629  }
630 
631  if ($result > 0) {
632  $this->db->begin();
633 
634  $sql = "UPDATE ".MAIN_DB_PREFIX."accounting_account ";
635  $sql .= "SET ".$fieldtouse." = '0'";
636  $sql .= " WHERE rowid = ".((int) $id);
637 
638  dol_syslog(get_class($this)."::accountDeactivate ".$fieldtouse, LOG_DEBUG);
639  $result = $this->db->query($sql);
640 
641  if ($result) {
642  $this->db->commit();
643  return 1;
644  } else {
645  $this->error = $this->db->lasterror();
646  $this->db->rollback();
647  return -1;
648  }
649  } else {
650  return -1;
651  }
652  }
653 
654 
662  public function accountActivate($id, $mode = 0)
663  {
664  // phpcs:enable
665  $this->db->begin();
666 
667  $fieldtouse = 'active';
668  if ($mode == 1) {
669  $fieldtouse = 'reconcilable';
670  }
671 
672  $sql = "UPDATE ".MAIN_DB_PREFIX."accounting_account";
673  $sql .= " SET ".$fieldtouse." = '1'";
674  $sql .= " WHERE rowid = ".((int) $id);
675 
676  dol_syslog(get_class($this)."::account_activate ".$fieldtouse, LOG_DEBUG);
677  $result = $this->db->query($sql);
678  if ($result) {
679  $this->db->commit();
680  return 1;
681  } else {
682  $this->error = $this->db->lasterror();
683  $this->db->rollback();
684  return -1;
685  }
686  }
687 
694  public function getLibStatut($mode = 0)
695  {
696  return $this->LibStatut($this->status, $mode);
697  }
698 
699  // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
707  public function LibStatut($status, $mode = 0)
708  {
709  // phpcs:enable
710  if (empty($this->labelStatus) || empty($this->labelStatusShort)) {
711  global $langs;
712  $langs->load("users");
713  $this->labelStatus[self::STATUS_ENABLED] = $langs->transnoentitiesnoconv('Enabled');
714  $this->labelStatus[self::STATUS_DISABLED] = $langs->transnoentitiesnoconv('Disabled');
715  $this->labelStatusShort[self::STATUS_ENABLED] = $langs->transnoentitiesnoconv('Enabled');
716  $this->labelStatusShort[self::STATUS_DISABLED] = $langs->transnoentitiesnoconv('Disabled');
717  }
718 
719  $statusType = 'status4';
720  if ($status == self::STATUS_DISABLED) {
721  $statusType = 'status5';
722  }
723 
724  return dolGetStatus($this->labelStatus[$status], $this->labelStatusShort[$status], '', $statusType, $mode);
725  }
726 
741  public function getAccountingCodeToBind(Societe $buyer, Societe $seller, Product $product, $facture, $factureDet, $accountingAccount = array(), $type = '')
742  {
743  global $conf;
744  global $hookmanager;
745 
746  // Instantiate hooks for external modules
747  $hookmanager->initHooks(array('accountancyBindingCalculation'));
748 
749  // Execute hook accountancyBindingCalculation
750  $parameters = array('buyer' => $buyer, 'seller' => $seller, 'product' => $product, 'facture' => $facture, 'factureDet' => $factureDet ,'accountingAccount'=>$accountingAccount, $type);
751  $reshook = $hookmanager->executeHooks('accountancyBindingCalculation', $parameters); // Note that $action and $object may have been modified by some hooks
752 
753  if (empty($reshook)) {
754  $const_name = '';
755  if ($type == 'customer') {
756  $const_name = "SOLD";
757  } elseif ($type == 'supplier') {
758  $const_name = "BUY";
759  }
760 
761  require_once DOL_DOCUMENT_ROOT . '/core/lib/company.lib.php';
762  $isBuyerInEEC = isInEEC($buyer);
763  $isSellerInEEC = isInEEC($seller);
764  $code_l = ''; // Default value for generic product/service
765  $code_p = ''; // Value for the product/service in parameter ($product)
766  $code_t = ''; // Default value of product account for the thirdparty
767  $suggestedid = '';
768 
769  // Level 1 (define $code_l): Search suggested default account for product/service
770  $suggestedaccountingaccountbydefaultfor = '';
771  if ($factureDet->product_type == 1) {
772  if ($buyer->country_code == $seller->country_code || empty($buyer->country_code)) { // If buyer in same country than seller (if not defined, we assume it is same country)
773  $code_l = getDolGlobalString('ACCOUNTING_SERVICE_' . $const_name . '_ACCOUNT');
774  $suggestedaccountingaccountbydefaultfor = '';
775  } else {
776  if ($isSellerInEEC && $isBuyerInEEC && $factureDet->tva_tx != 0) { // European intravat sale, but with a VAT
777  $code_l = getDolGlobalString('ACCOUNTING_SERVICE_' . $const_name . '_ACCOUNT');
778  $suggestedaccountingaccountbydefaultfor = 'eecwithvat';
779  } elseif ($isSellerInEEC && $isBuyerInEEC && empty($buyer->tva_intra)) { // European intravat sale, without VAT intra community number
780  $code_l = getDolGlobalString('ACCOUNTING_SERVICE_' . $const_name . '_ACCOUNT');
781  $suggestedaccountingaccountbydefaultfor = 'eecwithoutvatnumber';
782  } elseif ($isSellerInEEC && $isBuyerInEEC) { // European intravat sale
783  $code_l = getDolGlobalString('ACCOUNTING_SERVICE_' . $const_name . '_INTRA_ACCOUNT');
784  $suggestedaccountingaccountbydefaultfor = 'eec';
785  } else { // Foreign sale
786  $code_l = getDolGlobalString('ACCOUNTING_SERVICE_' . $const_name . '_EXPORT_ACCOUNT');
787  $suggestedaccountingaccountbydefaultfor = 'export';
788  }
789  }
790  } elseif ($factureDet->product_type == 0) {
791  if ($buyer->country_code == $seller->country_code || empty($buyer->country_code)) { // If buyer in same country than seller (if not defined, we assume it is same country)
792  $code_l = getDolGlobalString('ACCOUNTING_PRODUCT_' . $const_name . '_ACCOUNT');
793  $suggestedaccountingaccountbydefaultfor = '';
794  } else {
795  if ($isSellerInEEC && $isBuyerInEEC && $factureDet->tva_tx != 0) { // European intravat sale, but with a VAT
796  $code_l = getDolGlobalString('ACCOUNTING_PRODUCT_' . $const_name . '_ACCOUNT');
797  $suggestedaccountingaccountbydefaultfor = 'eecwithvat';
798  } elseif ($isSellerInEEC && $isBuyerInEEC && empty($buyer->tva_intra)) { // European intravat sale, without VAT intra community number
799  $code_l = getDolGlobalString('ACCOUNTING_PRODUCT_' . $const_name . '_ACCOUNT');
800  $suggestedaccountingaccountbydefaultfor = 'eecwithoutvatnumber';
801  } elseif ($isSellerInEEC && $isBuyerInEEC) { // European intravat sale
802  $code_l = getDolGlobalString('ACCOUNTING_PRODUCT_' . $const_name . '_INTRA_ACCOUNT');
803  $suggestedaccountingaccountbydefaultfor = 'eec';
804  } else {
805  $code_l = getDolGlobalString('ACCOUNTING_PRODUCT_' . $const_name . '_EXPORT_ACCOUNT');
806  $suggestedaccountingaccountbydefaultfor = 'export';
807  }
808  }
809  }
810  if ($code_l == -1) {
811  $code_l = '';
812  }
813 
814  // Level 2 (define $code_p): Search suggested account for product/service (similar code exists in page index.php to make automatic binding)
815  $suggestedaccountingaccountfor = '';
816  if ((($buyer->country_code == $seller->country_code) || empty($buyer->country_code))) {
817  // If buyer in same country than seller (if not defined, we assume it is same country)
818  if ($type == 'customer' && !empty($product->accountancy_code_sell)) {
819  $code_p = $product->accountancy_code_sell;
820  } elseif ($type == 'supplier' && !empty($product->accountancy_code_buy)) {
821  $code_p = $product->accountancy_code_buy;
822  }
823  $suggestedid = $accountingAccount['dom'];
824  $suggestedaccountingaccountfor = 'prodserv';
825  } else {
826  if ($isSellerInEEC && $isBuyerInEEC && $factureDet->tva_tx != 0) {
827  // European intravat sale, but with VAT
828  if ($type == 'customer' && !empty($product->accountancy_code_sell)) {
829  $code_p = $product->accountancy_code_sell;
830  } elseif ($type == 'supplier' && !empty($product->accountancy_code_buy)) {
831  $code_p = $product->accountancy_code_buy;
832  }
833  $suggestedid = $accountingAccount['dom'];
834  $suggestedaccountingaccountfor = 'eecwithvat';
835  } elseif ($isSellerInEEC && $isBuyerInEEC && empty($buyer->tva_intra)) {
836  // European intravat sale, without VAT intra community number
837  if ($type == 'customer' && !empty($product->accountancy_code_sell)) {
838  $code_p = $product->accountancy_code_sell;
839  } elseif ($type == 'supplier' && !empty($product->accountancy_code_buy)) {
840  $code_p = $product->accountancy_code_buy;
841  }
842  $suggestedid = $accountingAccount['dom']; // There is a doubt for this case. Is it an error on vat or we just forgot to fill vat number ?
843  $suggestedaccountingaccountfor = 'eecwithoutvatnumber';
844  } elseif ($isSellerInEEC && $isBuyerInEEC && !empty($product->accountancy_code_sell_intra)) {
845  // European intravat sale
846  if ($type == 'customer' && !empty($product->accountancy_code_sell_intra)) {
847  $code_p = $product->accountancy_code_sell_intra;
848  } elseif ($type == 'supplier' && !empty($product->accountancy_code_buy_intra)) {
849  $code_p = $product->accountancy_code_buy_intra;
850  }
851  $suggestedid = $accountingAccount['intra'];
852  $suggestedaccountingaccountfor = 'eec';
853  } else {
854  // Foreign sale
855  if ($type == 'customer' && !empty($product->accountancy_code_sell_export)) {
856  $code_p = $product->accountancy_code_sell_export;
857  } elseif ($type == 'supplier' && !empty($product->accountancy_code_buy_export)) {
858  $code_p = $product->accountancy_code_buy_export;
859  }
860  $suggestedid = $accountingAccount['export'];
861  $suggestedaccountingaccountfor = 'export';
862  }
863  }
864 
865  // Level 3 (define $code_t): Search suggested account for this thirdparty (similar code exists in page index.php to make automatic binding)
866  if (!empty($conf->global->ACCOUNTANCY_USE_PRODUCT_ACCOUNT_ON_THIRDPARTY)) {
867  if (!empty($buyer->code_compta_product)) {
868  $code_t = $buyer->code_compta_product;
869  $suggestedid = $accountingAccount['thirdparty'];
870  $suggestedaccountingaccountfor = 'thirdparty';
871  }
872  }
873 
874  // Manage Deposit
875  if (getDolGlobalString('ACCOUNTING_ACCOUNT_' . strtoupper($type) . '_DEPOSIT')) {
876  if ($factureDet->desc == "(DEPOSIT)" || $facture->type == $facture::TYPE_DEPOSIT) {
877  $accountdeposittoventilated = new self($this->db);
878  if ($type == 'customer') {
879  $result = $accountdeposittoventilated->fetch('', $conf->global->ACCOUNTING_ACCOUNT_CUSTOMER_DEPOSIT, 1);
880  } elseif ($type == 'supplier') {
881  $result = $accountdeposittoventilated->fetch('', $conf->global->ACCOUNTING_ACCOUNT_SUPPLIER_DEPOSIT, 1);
882  }
883  if (isset($result) && $result < 0) {
884  return -1;
885  }
886 
887  $code_l = $accountdeposittoventilated->ref;
888  $code_p = '';
889  $code_t = '';
890  $suggestedid = $accountdeposittoventilated->rowid;
891  $suggestedaccountingaccountfor = 'deposit';
892  }
893 
894  // For credit note invoice, if origin invoice is a deposit invoice, force also on specific customer/supplier deposit account
895  if (!empty($facture->fk_facture_source)) {
896  $invoiceSource = new $facture($this->db);
897  $invoiceSource->fetch($facture->fk_facture_source);
898 
899  if ($facture->type == $facture::TYPE_CREDIT_NOTE && $invoiceSource->type == $facture::TYPE_DEPOSIT) {
900  $accountdeposittoventilated = new self($this->db);
901  if ($type == 'customer') {
902  $accountdeposittoventilated->fetch('', $conf->global->ACCOUNTING_ACCOUNT_CUSTOMER_DEPOSIT, 1);
903  } elseif ($type == 'supplier') {
904  $accountdeposittoventilated->fetch('', $conf->global->ACCOUNTING_ACCOUNT_SUPPLIER_DEPOSIT, 1);
905  }
906  $code_l = $accountdeposittoventilated->ref;
907  $code_p = '';
908  $code_t = '';
909  $suggestedid = $accountdeposittoventilated->rowid;
910  $suggestedaccountingaccountfor = 'deposit';
911  }
912  }
913  }
914 
915  // If $suggestedid could not be guessed yet, we set it from the generic default accounting code $code_l
916  if (empty($suggestedid) && empty($code_p) && !empty($code_l) && empty($conf->global->ACCOUNTANCY_DO_NOT_AUTOFILL_ACCOUNT_WITH_GENERIC)) {
917  if (empty($this->accountingaccount_codetotid_cache[$code_l])) {
918  $tmpaccount = new self($this->db);
919  $result = $tmpaccount->fetch(0, $code_l, 1);
920  if ($result < 0) {
921  return -1;
922  }
923  if ($tmpaccount->id > 0) {
924  $suggestedid = $tmpaccount->id;
925  }
926  $this->accountingaccount_codetotid_cache[$code_l] = $tmpaccount->id;
927  } else {
928  $suggestedid = $this->accountingaccount_codetotid_cache[$code_l];
929  }
930  }
931  return array(
932  'suggestedaccountingaccountbydefaultfor' => $suggestedaccountingaccountbydefaultfor,
933  'suggestedaccountingaccountfor' => $suggestedaccountingaccountfor,
934  'suggestedid' => $suggestedid,
935  'code_l' => $code_l,
936  'code_p' => $code_p,
937  'code_t' => $code_t,
938  );
939  } else {
940  if (is_array($hookmanager->resArray) && !empty($hookmanager->resArray)) {
941  return $hookmanager->resArray;
942  }
943  }
944  }
945 }
length_accountg($account)
Return General accounting account with defined length (used for product and miscellaneous)
$object ref
Definition: info.php:78
Class to manage accounting accounts.
LibStatut($status, $mode=0)
Return the label of a given status.
accountDeactivate($id, $mode=0)
Deactivate an account (for status active or status reconcilable)
__construct($db)
Constructor.
checkUsage()
Check usage of accounting code.
update($user)
Update record.
getNomUrl($withpicto=0, $withlabel=0, $nourl=0, $moretitle='', $notooltip=0, $save_lastsearch_value=-1, $withcompletelabel=0, $option='')
Return clicable name (with picto eventually)
create($user, $notrigger=0)
Insert new accounting account in chart of accounts.
accountActivate($id, $mode=0)
Account activated.
info($id)
Information on record.
fetch($rowid=null, $account_number=null, $limittocurrentchart=0, $limittoachartaccount='')
Load record in memory.
getAccountingCodeToBind(Societe $buyer, Societe $seller, Product $product, $facture, $factureDet, $accountingAccount=array(), $type='')
Return a suggested account (from chart of accounts) to bind.
getLibStatut($mode=0)
Return the label of the status.
Parent class of all other business classes (invoices, contracts, proposals, orders,...
Class to manage products or services.
Class to manage third parties objects (customers, suppliers, prospects...)
isInEEC($object)
Return if a country of an object is inside the EEC (European Economic Community)
if(isModEnabled('facture') && $user->hasRight('facture', 'lire')) if((isModEnabled('fournisseur') &&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD) && $user->hasRight("fournisseur", "facture", "lire"))||(isModEnabled('supplier_invoice') && $user->hasRight("supplier_invoice", "lire"))) if(isModEnabled('don') && $user->hasRight('don', 'lire')) if(isModEnabled('tax') &&!empty($user->rights->tax->charges->lire)) if(isModEnabled('facture') &&isModEnabled('commande') && $user->hasRight("commande", "lire") &&empty($conf->global->WORKFLOW_DISABLE_CREATE_INVOICE_FROM_ORDER)) $sql
Social contributions to pay.
Definition: index.php:746
print *****$script_file(".$version.") pid c cd cd cd description as p label as s rowid
dol_print_error($db='', $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
img_object($titlealt, $picto, $moreatt='', $pictoisfullpath=false, $srconly=0, $notitle=0)
Show a picto called object_picto (generic function)
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return dolibarr global constant int value.
dolGetStatus($statusLabel='', $statusLabelShort='', $html='', $statusType='status0', $displayMode=0, $url='', $params=array())
Output the badge of a status.
getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Returns text escaped for inclusion in HTML alt or title or value tags, or into values of HTML input f...