dolibarr  17.0.4
myobject.class.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2017 Laurent Destailleur <eldy@users.sourceforge.net>
3  * Copyright (C) ---Put here your own copyright and developer email---
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 3 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program. If not, see <https://www.gnu.org/licenses/>.
17  */
18 
25 // Put here all includes required by your class file
26 require_once DOL_DOCUMENT_ROOT.'/core/class/commonobject.class.php';
27 //require_once DOL_DOCUMENT_ROOT . '/societe/class/societe.class.php';
28 //require_once DOL_DOCUMENT_ROOT . '/product/class/product.class.php';
29 
33 class MyObject extends CommonObject
34 {
38  public $module = 'mymodule';
39 
43  public $element = 'myobject';
44 
48  public $table_element = 'mymodule_myobject';
49 
54  public $ismultientitymanaged = 0;
55 
59  public $isextrafieldmanaged = 1;
60 
64  public $picto = 'fa-file';
65 
66 
67  const STATUS_DRAFT = 0;
68  const STATUS_VALIDATED = 1;
69  const STATUS_CANCELED = 9;
70 
71 
111  // BEGIN MODULEBUILDER PROPERTIES
115  public $fields = array(
116  'rowid' => array('type'=>'integer', 'label'=>'TechnicalID', 'enabled'=>1, 'visible'=>-2, 'noteditable'=>1, 'notnull'=> 1, 'index'=>1, 'position'=>1, 'comment'=>'Id', 'css'=>'left'),
117  'entity' => array('type'=>'integer', 'label'=>'Entity', 'enabled'=>1, 'visible'=>0, 'notnull'=> 1, 'default'=>1, 'index'=>1, 'position'=>10),
118  'ref' => array('type'=>'varchar(128)', 'label'=>'Ref', 'enabled'=>1, 'visible'=>1, 'noteditable'=>0, 'default'=>'', 'notnull'=> 1, 'showoncombobox'=>1, 'index'=>1, 'position'=>20, 'searchall'=>1, 'comment'=>'Reference of object', 'validate'=>1),
119  'label' => array('type'=>'varchar(255)', 'label'=>'Label', 'enabled'=>1, 'visible'=>1, 'position'=>30, 'searchall'=>1, 'css'=>'minwidth300', 'cssview'=>'wordbreak', 'help'=>'Help text', 'showoncombobox'=>2, 'validate'=>1, 'alwayseditable'=>1),
120  'amount' => array('type'=>'price', 'label'=>'Amount', 'enabled'=>1, 'visible'=>1, 'default'=>'null', 'position'=>40, 'searchall'=>0, 'isameasure'=>1, 'help'=>'Help text for amount', 'validate'=>1),
121  'qty' => array('type'=>'real', 'label'=>'Qty', 'enabled'=>1, 'visible'=>1, 'default'=>'0', 'position'=>45, 'searchall'=>0, 'isameasure'=>1, 'help'=>'Help text for quantity', 'css'=>'maxwidth75imp', 'validate'=>1),
122  'fk_soc' => array('type'=>'integer:Societe:societe/class/societe.class.php:1:((status:=:1) AND (entity:IN:__SHARED_ENTITIES__))', 'picto'=>'company', 'label'=>'ThirdParty', 'visible'=> 1, 'enabled'=>'$conf->societe->enabled', 'position'=>50, 'notnull'=>-1, 'index'=>1, 'help'=>'OrganizationEventLinkToThirdParty', 'validate'=>1, 'css'=>'maxwidth500 widthcentpercentminusxx', 'csslist'=>'tdoverflowmax150'),
123  'fk_project' => array('type'=>'integer:Project:projet/class/project.class.php:1', 'label'=>'Project', 'picto'=>'project', 'enabled'=>'$conf->project->enabled', 'visible'=>-1, 'position'=>52, 'notnull'=>-1, 'index'=>1, 'validate'=>1, 'css'=>'maxwidth500 widthcentpercentminusxx', 'csslist'=>'tdoverflowmax150'),
124  'description' => array('type'=>'text', 'label'=>'Description', 'enabled'=>1, 'visible'=>3, 'position'=>60, 'validate'=>1),
125  'note_public' => array('type'=>'html', 'label'=>'NotePublic', 'enabled'=>1, 'visible'=>0, 'position'=>61, 'validate'=>1, 'cssview'=>'wordbreak'),
126  'note_private' => array('type'=>'html', 'label'=>'NotePrivate', 'enabled'=>1, 'visible'=>0, 'position'=>62, 'validate'=>1, 'cssview'=>'wordbreak'),
127  'date_creation' => array('type'=>'datetime', 'label'=>'DateCreation', 'enabled'=>1, 'visible'=>-2, 'notnull'=> 1, 'position'=>500),
128  'tms' => array('type'=>'timestamp', 'label'=>'DateModification', 'enabled'=>1, 'visible'=>-2, 'notnull'=> 0, 'position'=>501),
129  //'date_validation ' =>array('type'=>'datetime', 'label'=>'DateCreation', 'enabled'=>1, 'visible'=>-2, 'position'=>502),
130  'fk_user_creat' => array('type'=>'integer:User:user/class/user.class.php', 'label'=>'UserAuthor', 'picto'=>'user', 'enabled'=>1, 'visible'=>-2, 'notnull'=> 1, 'position'=>510, 'foreignkey'=>'user.rowid', 'csslist'=>'tdoverflowmax150'),
131  'fk_user_modif' => array('type'=>'integer:User:user/class/user.class.php', 'label'=>'UserModif', 'picto'=>'user', 'enabled'=>1, 'visible'=>-2, 'notnull'=>-1, 'position'=>511, 'csslist'=>'tdoverflowmax150'),
132  //'fk_user_valid' => array('type'=>'integer:User:user/class/user.class.php', 'label'=>'UserValidation', 'enabled'=>1, 'visible'=>-1, 'position'=>512),
133  'last_main_doc' => array('type'=>'varchar(255)', 'label'=>'LastMainDoc', 'enabled'=>1, 'visible'=>0, 'notnull'=>0, 'position'=>600),
134  'import_key' => array('type'=>'varchar(14)', 'label'=>'ImportId', 'enabled'=>1, 'visible'=>-2, 'notnull'=>-1, 'index'=>0, 'position'=>1000),
135  'model_pdf' => array('type'=>'varchar(255)', 'label'=>'Model pdf', 'enabled'=>1, 'visible'=>0, 'notnull'=>-1, 'position'=>1010),
136  'status' => array('type'=>'integer', 'label'=>'Status', 'enabled'=>1, 'visible'=>1, 'notnull'=> 1, 'default'=>0, 'index'=>1, 'position'=>2000, 'arrayofkeyval'=>array(0=>'Draft', 1=>'Validated', 9=>'Canceled'), 'validate'=>1),
137  );
138 
142  public $rowid;
143 
147  public $ref;
148 
152  public $entity;
153 
157  public $label;
158 
162  public $amount;
163 
167  public $socid; // both socid and fk_soc are used
168  public $fk_soc; // both socid and fk_soc are used
169 
173  public $status;
174 
178  public $date_creation;
179 
183  public $tms;
184 
188  public $fk_user_creat;
189 
193  public $fk_user_modif;
194 
198  public $last_main_doc;
199 
203  public $import_key;
204  // END MODULEBUILDER PROPERTIES
205 
206 
207  // If this object has a subtable with lines
208 
209  // /**
210  // * @var string Name of subtable line
211  // */
212  // public $table_element_line = 'mymodule_myobjectline';
213 
214  // /**
215  // * @var string Field with ID of parent key if this object has a parent
216  // */
217  // public $fk_element = 'fk_myobject';
218 
219  // /**
220  // * @var string Name of subtable class that manage subtable lines
221  // */
222  // public $class_element_line = 'MyObjectline';
223 
224  // /**
225  // * @var array List of child tables. To test if we can delete object.
226  // */
227  // protected $childtables = array();
228 
229  // /**
230  // * @var array List of child tables. To know object to delete on cascade.
231  // * If name matches '@ClassNAme:FilePathClass;ParentFkFieldName' it will
232  // * call method deleteByParentField(parentId, ParentFkFieldName) to fetch and delete child object
233  // */
234  // protected $childtablesoncascade = array('mymodule_myobjectdet');
235 
236  // /**
237  // * @var MyObjectLine[] Array of subtable lines
238  // */
239  // public $lines = array();
240 
241 
242 
248  public function __construct(DoliDB $db)
249  {
250  global $conf, $langs;
251 
252  $this->db = $db;
253 
254  if (!getDolGlobalInt('MAIN_SHOW_TECHNICAL_ID') && isset($this->fields['rowid']) && !empty($this->fields['ref'])) {
255  $this->fields['rowid']['visible'] = 0;
256  }
257  if (!isModEnabled('multicompany') && isset($this->fields['entity'])) {
258  $this->fields['entity']['enabled'] = 0;
259  }
260 
261  // Example to show how to set values of fields definition dynamically
262  /*if ($user->rights->mymodule->myobject->read) {
263  $this->fields['myfield']['visible'] = 1;
264  $this->fields['myfield']['noteditable'] = 0;
265  }*/
266 
267  // Unset fields that are disabled
268  foreach ($this->fields as $key => $val) {
269  if (isset($val['enabled']) && empty($val['enabled'])) {
270  unset($this->fields[$key]);
271  }
272  }
273 
274  // Translate some data of arrayofkeyval
275  if (is_object($langs)) {
276  foreach ($this->fields as $key => $val) {
277  if (!empty($val['arrayofkeyval']) && is_array($val['arrayofkeyval'])) {
278  foreach ($val['arrayofkeyval'] as $key2 => $val2) {
279  $this->fields[$key]['arrayofkeyval'][$key2] = $langs->trans($val2);
280  }
281  }
282  }
283  }
284  }
285 
293  public function create(User $user, $notrigger = false)
294  {
295  $resultcreate = $this->createCommon($user, $notrigger);
296 
297  //$resultvalidate = $this->validate($user, $notrigger);
298 
299  return $resultcreate;
300  }
301 
309  public function createFromClone(User $user, $fromid)
310  {
311  global $langs, $extrafields;
312  $error = 0;
313 
314  dol_syslog(__METHOD__, LOG_DEBUG);
315 
316  $object = new self($this->db);
317 
318  $this->db->begin();
319 
320  // Load source object
321  $result = $object->fetchCommon($fromid);
322  if ($result > 0 && !empty($object->table_element_line)) {
323  $object->fetchLines();
324  }
325 
326  // get lines so they will be clone
327  //foreach($this->lines as $line)
328  // $line->fetch_optionals();
329 
330  // Reset some properties
331  unset($object->id);
332  unset($object->fk_user_creat);
333  unset($object->import_key);
334 
335  // Clear fields
336  if (property_exists($object, 'ref')) {
337  $object->ref = empty($this->fields['ref']['default']) ? "Copy_Of_".$object->ref : $this->fields['ref']['default'];
338  }
339  if (property_exists($object, 'label')) {
340  $object->label = empty($this->fields['label']['default']) ? $langs->trans("CopyOf")." ".$object->label : $this->fields['label']['default'];
341  }
342  if (property_exists($object, 'status')) {
343  $object->status = self::STATUS_DRAFT;
344  }
345  if (property_exists($object, 'date_creation')) {
346  $object->date_creation = dol_now();
347  }
348  if (property_exists($object, 'date_modification')) {
349  $object->date_modification = null;
350  }
351  // ...
352  // Clear extrafields that are unique
353  if (is_array($object->array_options) && count($object->array_options) > 0) {
354  $extrafields->fetch_name_optionals_label($this->table_element);
355  foreach ($object->array_options as $key => $option) {
356  $shortkey = preg_replace('/options_/', '', $key);
357  if (!empty($extrafields->attributes[$this->table_element]['unique'][$shortkey])) {
358  //var_dump($key);
359  //var_dump($clonedObj->array_options[$key]); exit;
360  unset($object->array_options[$key]);
361  }
362  }
363  }
364 
365  // Create clone
366  $object->context['createfromclone'] = 'createfromclone';
367  $result = $object->createCommon($user);
368  if ($result < 0) {
369  $error++;
370  $this->error = $object->error;
371  $this->errors = $object->errors;
372  }
373 
374  if (!$error) {
375  // copy internal contacts
376  if ($this->copy_linked_contact($object, 'internal') < 0) {
377  $error++;
378  }
379  }
380 
381  if (!$error) {
382  // copy external contacts if same company
383  if (!empty($object->socid) && property_exists($this, 'fk_soc') && $this->fk_soc == $object->socid) {
384  if ($this->copy_linked_contact($object, 'external') < 0) {
385  $error++;
386  }
387  }
388  }
389 
390  unset($object->context['createfromclone']);
391 
392  // End
393  if (!$error) {
394  $this->db->commit();
395  return $object;
396  } else {
397  $this->db->rollback();
398  return -1;
399  }
400  }
401 
409  public function fetch($id, $ref = null)
410  {
411  $result = $this->fetchCommon($id, $ref);
412  if ($result > 0 && !empty($this->table_element_line)) {
413  $this->fetchLines();
414  }
415  return $result;
416  }
417 
423  public function fetchLines()
424  {
425  $this->lines = array();
426 
427  $result = $this->fetchLinesCommon();
428  return $result;
429  }
430 
431 
443  public function fetchAll($sortorder = '', $sortfield = '', $limit = 0, $offset = 0, array $filter = array(), $filtermode = 'AND')
444  {
445  global $conf;
446 
447  dol_syslog(__METHOD__, LOG_DEBUG);
448 
449  $records = array();
450 
451  $sql = "SELECT ";
452  $sql .= $this->getFieldList('t');
453  $sql .= " FROM ".$this->db->prefix().$this->table_element." as t";
454  if (isset($this->ismultientitymanaged) && $this->ismultientitymanaged == 1) {
455  $sql .= " WHERE t.entity IN (".getEntity($this->element).")";
456  } else {
457  $sql .= " WHERE 1 = 1";
458  }
459  // Manage filter
460  $sqlwhere = array();
461  if (count($filter) > 0) {
462  foreach ($filter as $key => $value) {
463  if ($key == 't.rowid') {
464  $sqlwhere[] = $key." = ".((int) $value);
465  } elseif (in_array($this->fields[$key]['type'], array('date', 'datetime', 'timestamp'))) {
466  $sqlwhere[] = $key." = '".$this->db->idate($value)."'";
467  } elseif ($key == 'customsql') {
468  $sqlwhere[] = $value;
469  } elseif (strpos($value, '%') === false) {
470  $sqlwhere[] = $key." IN (".$this->db->sanitize($this->db->escape($value)).")";
471  } else {
472  $sqlwhere[] = $key." LIKE '%".$this->db->escape($value)."%'";
473  }
474  }
475  }
476  if (count($sqlwhere) > 0) {
477  $sql .= " AND (".implode(" ".$filtermode." ", $sqlwhere).")";
478  }
479 
480  if (!empty($sortfield)) {
481  $sql .= $this->db->order($sortfield, $sortorder);
482  }
483  if (!empty($limit)) {
484  $sql .= $this->db->plimit($limit, $offset);
485  }
486 
487  $resql = $this->db->query($sql);
488  if ($resql) {
489  $num = $this->db->num_rows($resql);
490  $i = 0;
491  while ($i < ($limit ? min($limit, $num) : $num)) {
492  $obj = $this->db->fetch_object($resql);
493 
494  $record = new self($this->db);
495  $record->setVarsFromFetchObj($obj);
496 
497  $records[$record->id] = $record;
498 
499  $i++;
500  }
501  $this->db->free($resql);
502 
503  return $records;
504  } else {
505  $this->errors[] = 'Error '.$this->db->lasterror();
506  dol_syslog(__METHOD__.' '.join(',', $this->errors), LOG_ERR);
507 
508  return -1;
509  }
510  }
511 
519  public function update(User $user, $notrigger = false)
520  {
521  return $this->updateCommon($user, $notrigger);
522  }
523 
531  public function delete(User $user, $notrigger = false)
532  {
533  return $this->deleteCommon($user, $notrigger);
534  //return $this->deleteCommon($user, $notrigger, 1);
535  }
536 
545  public function deleteLine(User $user, $idline, $notrigger = false)
546  {
547  if ($this->status < 0) {
548  $this->error = 'ErrorDeleteLineNotAllowedByObjectStatus';
549  return -2;
550  }
551 
552  return $this->deleteLineCommon($user, $idline, $notrigger);
553  }
554 
555 
563  public function validate($user, $notrigger = 0)
564  {
565  global $conf, $langs;
566 
567  require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
568 
569  $error = 0;
570 
571  // Protection
572  if ($this->status == self::STATUS_VALIDATED) {
573  dol_syslog(get_class($this)."::validate action abandonned: already validated", LOG_WARNING);
574  return 0;
575  }
576 
577  /* if (! ((!getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && $user->hasRight('mymodule','write'))
578  || (getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && !empty($user->rights->mymodule->myobject->myobject_advance->validate))))
579  {
580  $this->error='NotEnoughPermissions';
581  dol_syslog(get_class($this)."::valid ".$this->error, LOG_ERR);
582  return -1;
583  }*/
584 
585  $now = dol_now();
586 
587  $this->db->begin();
588 
589  // Define new ref
590  if (!$error && (preg_match('/^[\‍(]?PROV/i', $this->ref) || empty($this->ref))) { // empty should not happened, but when it occurs, the test save life
591  $num = $this->getNextNumRef();
592  } else {
593  $num = $this->ref;
594  }
595  $this->newref = $num;
596 
597  if (!empty($num)) {
598  // Validate
599  $sql = "UPDATE ".MAIN_DB_PREFIX.$this->table_element;
600  $sql .= " SET ref = '".$this->db->escape($num)."',";
601  $sql .= " status = ".self::STATUS_VALIDATED;
602  if (!empty($this->fields['date_validation'])) {
603  $sql .= ", date_validation = '".$this->db->idate($now)."'";
604  }
605  if (!empty($this->fields['fk_user_valid'])) {
606  $sql .= ", fk_user_valid = ".((int) $user->id);
607  }
608  $sql .= " WHERE rowid = ".((int) $this->id);
609 
610  dol_syslog(get_class($this)."::validate()", LOG_DEBUG);
611  $resql = $this->db->query($sql);
612  if (!$resql) {
613  dol_print_error($this->db);
614  $this->error = $this->db->lasterror();
615  $error++;
616  }
617 
618  if (!$error && !$notrigger) {
619  // Call trigger
620  $result = $this->call_trigger('MYOBJECT_VALIDATE', $user);
621  if ($result < 0) {
622  $error++;
623  }
624  // End call triggers
625  }
626  }
627 
628  if (!$error) {
629  $this->oldref = $this->ref;
630 
631  // Rename directory if dir was a temporary ref
632  if (preg_match('/^[\‍(]?PROV/i', $this->ref)) {
633  // Now we rename also files into index
634  $sql = 'UPDATE '.MAIN_DB_PREFIX."ecm_files set filename = CONCAT('".$this->db->escape($this->newref)."', SUBSTR(filename, ".(strlen($this->ref) + 1).")), filepath = 'myobject/".$this->db->escape($this->newref)."'";
635  $sql .= " WHERE filename LIKE '".$this->db->escape($this->ref)."%' AND filepath = 'myobject/".$this->db->escape($this->ref)."' and entity = ".$conf->entity;
636  $resql = $this->db->query($sql);
637  if (!$resql) {
638  $error++; $this->error = $this->db->lasterror();
639  }
640 
641  // We rename directory ($this->ref = old ref, $num = new ref) in order not to lose the attachments
642  $oldref = dol_sanitizeFileName($this->ref);
643  $newref = dol_sanitizeFileName($num);
644  $dirsource = $conf->mymodule->dir_output.'/myobject/'.$oldref;
645  $dirdest = $conf->mymodule->dir_output.'/myobject/'.$newref;
646  if (!$error && file_exists($dirsource)) {
647  dol_syslog(get_class($this)."::validate() rename dir ".$dirsource." into ".$dirdest);
648 
649  if (@rename($dirsource, $dirdest)) {
650  dol_syslog("Rename ok");
651  // Rename docs starting with $oldref with $newref
652  $listoffiles = dol_dir_list($conf->mymodule->dir_output.'/myobject/'.$newref, 'files', 1, '^'.preg_quote($oldref, '/'));
653  foreach ($listoffiles as $fileentry) {
654  $dirsource = $fileentry['name'];
655  $dirdest = preg_replace('/^'.preg_quote($oldref, '/').'/', $newref, $dirsource);
656  $dirsource = $fileentry['path'].'/'.$dirsource;
657  $dirdest = $fileentry['path'].'/'.$dirdest;
658  @rename($dirsource, $dirdest);
659  }
660  }
661  }
662  }
663  }
664 
665  // Set new ref and current status
666  if (!$error) {
667  $this->ref = $num;
668  $this->status = self::STATUS_VALIDATED;
669  }
670 
671  if (!$error) {
672  $this->db->commit();
673  return 1;
674  } else {
675  $this->db->rollback();
676  return -1;
677  }
678  }
679 
680 
688  public function setDraft($user, $notrigger = 0)
689  {
690  // Protection
691  if ($this->status <= self::STATUS_DRAFT) {
692  return 0;
693  }
694 
695  /* if (! ((!getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && $user->hasRight('mymodule','write'))
696  || (getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && $user->hasRight('mymodule','mymodule_advance','validate'))))
697  {
698  $this->error='Permission denied';
699  return -1;
700  }*/
701 
702  return $this->setStatusCommon($user, self::STATUS_DRAFT, $notrigger, 'MYOBJECT_UNVALIDATE');
703  }
704 
712  public function cancel($user, $notrigger = 0)
713  {
714  // Protection
715  if ($this->status != self::STATUS_VALIDATED) {
716  return 0;
717  }
718 
719  /* if (! ((!getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && $user->hasRight('mymodule','write'))
720  || (getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && $user->hasRight('mymodule','mymodule_advance','validate'))))
721  {
722  $this->error='Permission denied';
723  return -1;
724  }*/
725 
726  return $this->setStatusCommon($user, self::STATUS_CANCELED, $notrigger, 'MYOBJECT_CANCEL');
727  }
728 
736  public function reopen($user, $notrigger = 0)
737  {
738  // Protection
739  if ($this->status == self::STATUS_VALIDATED) {
740  return 0;
741  }
742 
743  /*if (! ((!getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && $user->hasRight('mymodule','write'))
744  || (getDolGlobalInt('MAIN_USE_ADVANCED_PERMS') && $user->hasRight('mymodule','mymodule_advance','validate'))))
745  {
746  $this->error='Permission denied';
747  return -1;
748  }*/
749 
750 
751  return $this->setStatusCommon($user, self::STATUS_VALIDATED, $notrigger, 'MYOBJECT_REOPEN');
752  }
753 
764  public function getNomUrl($withpicto = 0, $option = '', $notooltip = 0, $morecss = '', $save_lastsearch_value = -1)
765  {
766  global $conf, $langs, $hookmanager;
767 
768  if (!empty($conf->dol_no_mouse_hover)) {
769  $notooltip = 1; // Force disable tooltips
770  }
771 
772  $result = '';
773 
774  $label = img_picto('', $this->picto).' <u>'.$langs->trans("MyObject").'</u>';
775  if (isset($this->status)) {
776  $label .= ' '.$this->getLibStatut(5);
777  }
778  $label .= '<br>';
779  $label .= '<b>'.$langs->trans('Ref').':</b> '.$this->ref;
780 
781  $url = dol_buildpath('/mymodule/myobject_card.php', 1).'?id='.$this->id;
782 
783  if ($option != 'nolink') {
784  // Add param to save lastsearch_values or not
785  $add_save_lastsearch_values = ($save_lastsearch_value == 1 ? 1 : 0);
786  if ($save_lastsearch_value == -1 && preg_match('/list\.php/', $_SERVER["PHP_SELF"])) {
787  $add_save_lastsearch_values = 1;
788  }
789  if ($url && $add_save_lastsearch_values) {
790  $url .= '&save_lastsearch_values=1';
791  }
792  }
793 
794  $linkclose = '';
795  if (empty($notooltip)) {
796  if (getDolGlobalInt('MAIN_OPTIMIZEFORTEXTBROWSER')) {
797  $label = $langs->trans("ShowMyObject");
798  $linkclose .= ' alt="'.dol_escape_htmltag($label, 1).'"';
799  }
800  $linkclose .= ' title="'.dol_escape_htmltag($label, 1).'"';
801  $linkclose .= ' class="classfortooltip'.($morecss ? ' '.$morecss : '').'"';
802  } else {
803  $linkclose = ($morecss ? ' class="'.$morecss.'"' : '');
804  }
805 
806  if ($option == 'nolink' || empty($url)) {
807  $linkstart = '<span';
808  } else {
809  $linkstart = '<a href="'.$url.'"';
810  }
811  $linkstart .= $linkclose.'>';
812  if ($option == 'nolink' || empty($url)) {
813  $linkend = '</span>';
814  } else {
815  $linkend = '</a>';
816  }
817 
818  $result .= $linkstart;
819 
820  if (empty($this->showphoto_on_popup)) {
821  if ($withpicto) {
822  $result .= img_object(($notooltip ? '' : $label), ($this->picto ? $this->picto : 'generic'), ($notooltip ? (($withpicto != 2) ? 'class="paddingright"' : '') : 'class="'.(($withpicto != 2) ? 'paddingright ' : '').'classfortooltip"'), 0, 0, $notooltip ? 0 : 1);
823  }
824  } else {
825  if ($withpicto) {
826  require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
827 
828  list($class, $module) = explode('@', $this->picto);
829  $upload_dir = $conf->$module->multidir_output[$conf->entity]."/$class/".dol_sanitizeFileName($this->ref);
830  $filearray = dol_dir_list($upload_dir, "files");
831  $filename = $filearray[0]['name'];
832  if (!empty($filename)) {
833  $pospoint = strpos($filearray[0]['name'], '.');
834 
835  $pathtophoto = $class.'/'.$this->ref.'/thumbs/'.substr($filename, 0, $pospoint).'_mini'.substr($filename, $pospoint);
836  if (!getDolGlobalString(strtoupper($module.'_'.$class).'_FORMATLISTPHOTOSASUSERS')) {
837  $result .= '<div class="floatleft inline-block valignmiddle divphotoref"><div class="photoref"><img class="photo'.$module.'" alt="No photo" border="0" src="'.DOL_URL_ROOT.'/viewimage.php?modulepart='.$module.'&entity='.$conf->entity.'&file='.urlencode($pathtophoto).'"></div></div>';
838  } else {
839  $result .= '<div class="floatleft inline-block valignmiddle divphotoref"><img class="photouserphoto userphoto" alt="No photo" border="0" src="'.DOL_URL_ROOT.'/viewimage.php?modulepart='.$module.'&entity='.$conf->entity.'&file='.urlencode($pathtophoto).'"></div>';
840  }
841 
842  $result .= '</div>';
843  } else {
844  $result .= img_object(($notooltip ? '' : $label), ($this->picto ? $this->picto : 'generic'), ($notooltip ? (($withpicto != 2) ? 'class="paddingright"' : '') : 'class="'.(($withpicto != 2) ? 'paddingright ' : '').'classfortooltip"'), 0, 0, $notooltip ? 0 : 1);
845  }
846  }
847  }
848 
849  if ($withpicto != 2) {
850  $result .= $this->ref;
851  }
852 
853  $result .= $linkend;
854  //if ($withpicto != 2) $result.=(($addlabel && $this->label) ? $sep . dol_trunc($this->label, ($addlabel > 1 ? $addlabel : 0)) : '');
855 
856  global $action, $hookmanager;
857  $hookmanager->initHooks(array($this->element.'dao'));
858  $parameters = array('id'=>$this->id, 'getnomurl' => &$result);
859  $reshook = $hookmanager->executeHooks('getNomUrl', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
860  if ($reshook > 0) {
861  $result = $hookmanager->resPrint;
862  } else {
863  $result .= $hookmanager->resPrint;
864  }
865 
866  return $result;
867  }
868 
875  /*
876  public function getKanbanView($option = '')
877  {
878  $return = '<div class="box-flex-item box-flex-grow-zero">';
879  $return .= '<div class="info-box info-box-sm">';
880  $return .= '<span class="info-box-icon bg-infobox-action">';
881  $return .= img_picto('', $this->picto);
882  $return .= '</span>';
883  $return .= '<div class="info-box-content">';
884  $return .= '<span class="info-box-ref">'.(method_exists($this, 'getNomUrl') ? $this->getNomUrl() : $this->ref).'</span>';
885  if (property_exists($this, 'label')) {
886  $return .= '<br><span class="info-box-label opacitymedium">'.$this->label.'</span>';
887  }
888  if (method_exists($this, 'getLibStatut')) {
889  $return .= '<br><div class="info-box-status margintoponly">'.$this->getLibStatut(5).'</div>';
890  }
891  $return .= '</div>';
892  $return .= '</div>';
893  $return .= '</div>';
894 
895  return $return;
896  }
897  */
898 
905  public function getLabelStatus($mode = 0)
906  {
907  return $this->LibStatut($this->status, $mode);
908  }
909 
916  public function getLibStatut($mode = 0)
917  {
918  return $this->LibStatut($this->status, $mode);
919  }
920 
921  // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
929  public function LibStatut($status, $mode = 0)
930  {
931  // phpcs:enable
932  if (empty($this->labelStatus) || empty($this->labelStatusShort)) {
933  global $langs;
934  //$langs->load("mymodule@mymodule");
935  $this->labelStatus[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
936  $this->labelStatus[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Enabled');
937  $this->labelStatus[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('Disabled');
938  $this->labelStatusShort[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
939  $this->labelStatusShort[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Enabled');
940  $this->labelStatusShort[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('Disabled');
941  }
942 
943  $statusType = 'status'.$status;
944  //if ($status == self::STATUS_VALIDATED) $statusType = 'status1';
945  if ($status == self::STATUS_CANCELED) {
946  $statusType = 'status6';
947  }
948 
949  return dolGetStatus($this->labelStatus[$status], $this->labelStatusShort[$status], '', $statusType, $mode);
950  }
951 
958  public function info($id)
959  {
960  $sql = "SELECT rowid,";
961  $sql .= " date_creation as datec, tms as datem,";
962  $sql .= " fk_user_creat, fk_user_modif";
963  $sql .= " FROM ".MAIN_DB_PREFIX.$this->table_element." as t";
964  $sql .= " WHERE t.rowid = ".((int) $id);
965 
966  $result = $this->db->query($sql);
967  if ($result) {
968  if ($this->db->num_rows($result)) {
969  $obj = $this->db->fetch_object($result);
970 
971  $this->id = $obj->rowid;
972 
973  $this->user_creation_id = $obj->fk_user_creat;
974  $this->user_modification_id = $obj->fk_user_modif;
975  if (!empty($obj->fk_user_valid)) {
976  $this->user_validation_id = $obj->fk_user_valid;
977  }
978  $this->date_creation = $this->db->jdate($obj->datec);
979  $this->date_modification = empty($obj->datem) ? '' : $this->db->jdate($obj->datem);
980  if (!empty($obj->datev)) {
981  $this->date_validation = empty($obj->datev) ? '' : $this->db->jdate($obj->datev);
982  }
983  }
984 
985  $this->db->free($result);
986  } else {
987  dol_print_error($this->db);
988  }
989  }
990 
997  public function initAsSpecimen()
998  {
999  // Set here init that are not commonf fields
1000  // $this->property1 = ...
1001  // $this->property2 = ...
1002 
1003  $this->initAsSpecimenCommon();
1004  }
1005 
1011  public function getLinesArray()
1012  {
1013  $this->lines = array();
1014 
1015  $objectline = new MyObjectLine($this->db);
1016  $result = $objectline->fetchAll('ASC', 'position', 0, 0, array('customsql'=>'fk_myobject = '.((int) $this->id)));
1017 
1018  if (is_numeric($result)) {
1019  $this->error = $objectline->error;
1020  $this->errors = $objectline->errors;
1021  return $result;
1022  } else {
1023  $this->lines = $result;
1024  return $this->lines;
1025  }
1026  }
1027 
1033  public function getNextNumRef()
1034  {
1035  global $langs, $conf;
1036  $langs->load("mymodule@mymodule");
1037 
1038  if (getDolGlobalString('MYMODULE_MYOBJECT_ADDON')=='') {
1039  $conf->global->MYMODULE_MYOBJECT_ADDON = 'mod_myobject_standard';
1040  }
1041 
1042  if (getDolGlobalString('MYMODULE_MYOBJECT_ADDON')) {
1043  $mybool = false;
1044 
1045  $file = getDolGlobalString('MYMODULE_MYOBJECT_ADDON').".php";
1046  $classname = getDolGlobalString('MYMODULE_MYOBJECT_ADDON');
1047 
1048  // Include file with class
1049  $dirmodels = array_merge(array('/'), (array) $conf->modules_parts['models']);
1050  foreach ($dirmodels as $reldir) {
1051  $dir = dol_buildpath($reldir."core/modules/mymodule/");
1052 
1053  // Load file with numbering class (if found)
1054  $mybool |= @include_once $dir.$file;
1055  }
1056 
1057  if ($mybool === false) {
1058  dol_print_error('', "Failed to include file ".$file);
1059  return '';
1060  }
1061 
1062  if (class_exists($classname)) {
1063  $obj = new $classname();
1064  $numref = $obj->getNextValue($this);
1065 
1066  if ($numref != '' && $numref != '-1') {
1067  return $numref;
1068  } else {
1069  $this->error = $obj->error;
1070  //dol_print_error($this->db,get_class($this)."::getNextNumRef ".$obj->error);
1071  return "";
1072  }
1073  } else {
1074  print $langs->trans("Error")." ".$langs->trans("ClassNotFound").' '.$classname;
1075  return "";
1076  }
1077  } else {
1078  print $langs->trans("ErrorNumberingModuleNotSetup", $this->element);
1079  return "";
1080  }
1081  }
1082 
1094  public function generateDocument($modele, $outputlangs, $hidedetails = 0, $hidedesc = 0, $hideref = 0, $moreparams = null)
1095  {
1096  global $conf, $langs;
1097 
1098  $result = 0;
1099  $includedocgeneration = 0;
1100 
1101  $langs->load("mymodule@mymodule");
1102 
1103  if (!dol_strlen($modele)) {
1104  $modele = 'standard_myobject';
1105 
1106  if (!empty($this->model_pdf)) {
1107  $modele = $this->model_pdf;
1108  } elseif (getDolGlobalString('MYOBJECT_ADDON_PDF')) {
1109  $modele = getDolGlobalString('MYOBJECT_ADDON_PDF');
1110  }
1111  }
1112 
1113  $modelpath = "core/modules/mymodule/doc/";
1114 
1115  if ($includedocgeneration && !empty($modele)) {
1116  $result = $this->commonGenerateDocument($modelpath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams);
1117  }
1118 
1119  return $result;
1120  }
1121 
1129  public function doScheduledJob()
1130  {
1131  global $conf, $langs;
1132 
1133  //$conf->global->SYSLOG_FILE = 'DOL_DATA_ROOT/dolibarr_mydedicatedlofile.log';
1134 
1135  $error = 0;
1136  $this->output = '';
1137  $this->error = '';
1138 
1139  dol_syslog(__METHOD__, LOG_DEBUG);
1140 
1141  $now = dol_now();
1142 
1143  $this->db->begin();
1144 
1145  // ...
1146 
1147  $this->db->commit();
1148 
1149  return $error;
1150  }
1151 }
1152 
1153 
1154 require_once DOL_DOCUMENT_ROOT.'/core/class/commonobjectline.class.php';
1155 
1160 {
1161  // To complete with content of an object MyObjectLine
1162  // We should have a field rowid, fk_myobject and position
1163 
1167  public $isextrafieldmanaged = 0;
1168 
1174  public function __construct(DoliDB $db)
1175  {
1176  $this->db = $db;
1177  }
1178 }
$object ref
Definition: info.php:78
Parent class of all other business classes (invoices, contracts, proposals, orders,...
commonGenerateDocument($modelspath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams=null)
Common function for all objects extending CommonObject for generating documents.
deleteLineCommon(User $user, $idline, $notrigger=false)
Delete a line of object in database.
getFieldList($alias='')
Function to concat keys of fields.
fetchCommon($id, $ref=null, $morewhere='')
Load object in memory from the database.
createCommon(User $user, $notrigger=false)
Create object into database.
deleteCommon(User $user, $notrigger=false, $forcechilddeletion=0)
Delete object in database.
setStatusCommon($user, $status, $notrigger=0, $triggercode='')
Set to a status.
initAsSpecimenCommon()
Initialise object with example values Id must be 0 if object instance is a specimen.
copy_linked_contact($objFrom, $source='internal')
Copy contact from one element to current.
updateCommon(User $user, $notrigger=false)
Update object into database.
fetchLinesCommon($morewhere='')
Load object in memory from the database.
call_trigger($triggerName, $user)
Call trigger based on this instance.
Parent class for class inheritance lines of business objects This class is useless for the moment so ...
Class to manage Dolibarr database access.
Class for MyObject.
generateDocument($modele, $outputlangs, $hidedetails=0, $hidedesc=0, $hideref=0, $moreparams=null)
Create a document onto disk according to template module.
createFromClone(User $user, $fromid)
Clone an object into another one.
getLibStatut($mode=0)
Return the label of the status.
fetch($id, $ref=null)
Load object in memory from the database.
reopen($user, $notrigger=0)
Set back to validated status.
setDraft($user, $notrigger=0)
Set draft status.
getNomUrl($withpicto=0, $option='', $notooltip=0, $morecss='', $save_lastsearch_value=-1)
Return a link to the object card (with optionaly the picto)
LibStatut($status, $mode=0)
Return the status.
getNextNumRef()
Returns the reference to the following non used object depending on the active numbering module.
initAsSpecimen()
Initialise object with example values Id must be 0 if object instance is a specimen.
fetchAll($sortorder='', $sortfield='', $limit=0, $offset=0, array $filter=array(), $filtermode='AND')
Load list of objects in memory from the database.
__construct(DoliDB $db)
Constructor.
cancel($user, $notrigger=0)
Set cancel status.
fetchLines()
Load object lines in memory from the database.
update(User $user, $notrigger=false)
Update object into database.
info($id)
Load the info information in the object.
doScheduledJob()
Action executed by scheduler CAN BE A CRON TASK.
getLabelStatus($mode=0)
Return a thumb for kanban views.
create(User $user, $notrigger=false)
Create object into database.
deleteLine(User $user, $idline, $notrigger=false)
Delete a line of object in database.
validate($user, $notrigger=0)
Validate object.
getLinesArray()
Create an array of lines.
Class MyObjectLine.
__construct(DoliDB $db)
Constructor.
Class to manage Dolibarr users.
Definition: user.class.php:47
if(isModEnabled('facture') &&!empty($user->rights->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') &&!empty($user->rights->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)) $resql
Social contributions to pay.
Definition: index.php:745
dol_dir_list($path, $types="all", $recursive=0, $filter="", $excludefilter=null, $sortcriteria="name", $sortorder=SORT_ASC, $mode=0, $nohook=0, $relativename="", $donotfollowsymlinks=0, $nbsecondsold=0)
Scan a directory and return a list of files/directories.
Definition: files.lib.php:61
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_strlen($string, $stringencoding='UTF-8')
Make a strlen call.
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return dolibarr global constant int value.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
dolGetStatus($statusLabel='', $statusLabelShort='', $html='', $statusType='status0', $displayMode=0, $url='', $params=array())
Output the badge of a status.
dol_buildpath($path, $type=0, $returnemptyifnotfound=0)
Return path of url or filesystem.
if(!function_exists('utf8_encode')) if(!function_exists('utf8_decode')) getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
dol_sanitizeFileName($str, $newstr='_', $unaccent=1)
Clean a string to use it as a file name.
isModEnabled($module)
Is Dolibarr module enabled.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
$conf db
API class for accounts.
Definition: inc.php:41