dolibarr  16.0.1
skill.class.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2017 Laurent Destailleur <eldy@users.sourceforge.net>
3  * Copyright (C) 2021 Gauthier VERDOL <gauthier.verdol@atm-consulting.fr>
4  * Copyright (C) 2021 Greg Rastklan <greg.rastklan@atm-consulting.fr>
5  * Copyright (C) 2021 Jean-Pascal BOUDET <jean-pascal.boudet@atm-consulting.fr>
6  * Copyright (C) 2021 Grégory BLEMAND <gregory.blemand@atm-consulting.fr>
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 3 of the License, or
11  * (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program. If not, see <https://www.gnu.org/licenses/>.
20  */
21 
28 // Put here all includes required by your class file
29 require_once DOL_DOCUMENT_ROOT.'/core/class/commonobject.class.php';
30 //require_once DOL_DOCUMENT_ROOT . '/societe/class/societe.class.php';
31 //require_once DOL_DOCUMENT_ROOT . '/product/class/product.class.php';
32 
36 class Skill extends CommonObject
37 {
41  public $module = 'hrm';
42 
46  public $element = 'skill';
47 
51  public $table_element = 'hrm_skill';
52 
53 
57  public $table_element_line = 'skilldet';
58 
63  public $ismultientitymanaged = 0;
64 
68  public $isextrafieldmanaged = 1;
69 
73  public $picto = 'shapes';
74 
75 
76  const STATUS_DRAFT = 0;
77  const STATUS_VALIDATED = 1;
78  const STATUS_CANCELED = 9;
79  const DEFAULT_MAX_RANK_PER_SKILL = 3;
80 
107  // BEGIN MODULEBUILDER PROPERTIES
111  public $fields=array(
112  'rowid' => array('type'=>'integer', 'label'=>'TechnicalID', 'enabled'=>'1', 'position'=>1, 'notnull'=>1, 'visible'=>0, 'noteditable'=>'1', 'index'=>1, 'css'=>'left', 'comment'=>"Id"),
113  'label' => array('type'=>'varchar(255)', 'label'=>'Label', 'enabled'=>'1', 'position'=>30, 'notnull'=>1, 'visible'=>1, 'searchall'=>1, 'css'=>'minwidth300', 'cssview'=>'wordbreak', 'showoncombobox'=>'2',),
114  'description' => array('type'=>'text', 'label'=>'Description', 'enabled'=>'1', 'position'=>60, 'notnull'=>0, 'visible'=>3,),
115  'date_creation' => array('type'=>'datetime', 'label'=>'DateCreation', 'enabled'=>'1', 'position'=>500, 'notnull'=>1, 'visible'=>-2,),
116  'tms' => array('type'=>'timestamp', 'label'=>'DateModification', 'enabled'=>'1', 'position'=>501, 'notnull'=>0, 'visible'=>-2,),
117  'fk_user_creat' => array('type'=>'integer:User:user/class/user.class.php', 'label'=>'UserAuthor', 'enabled'=>'1', 'position'=>510, 'notnull'=>1, 'visible'=>-2, 'foreignkey'=>'user.rowid',),
118  'fk_user_modif' => array('type'=>'integer:User:user/class/user.class.php', 'label'=>'UserModif', 'enabled'=>'1', 'position'=>511, 'notnull'=>-1, 'visible'=>-2,),
119  'required_level' => array('type'=>'integer', 'label'=>'requiredLevel', 'enabled'=>'1', 'position'=>50, 'notnull'=>1, 'visible'=>0,),
120  'date_validite' => array('type'=>'integer', 'label'=>'date_validite', 'enabled'=>'1', 'position'=>52, 'notnull'=>1, 'visible'=>0,),
121  'temps_theorique' => array('type'=>'double(24,8)', 'label'=>'temps_theorique', 'enabled'=>'1', 'position'=>54, 'notnull'=>1, 'visible'=>0,),
122  'skill_type' => array('type'=>'integer', 'label'=>'SkillType', 'enabled'=>'1', 'position'=>55, 'notnull'=>1, 'visible'=>1, 'index'=>1, 'css'=>'minwidth200', 'arrayofkeyval'=>array('0'=>'TypeKnowHow', '1'=>'TypeHowToBe', '9'=>'TypeKnowledge'), 'default'=>0),
123  'note_public' => array('type'=>'html', 'label'=>'NotePublic', 'enabled'=>'1', 'position'=>70, 'notnull'=>0, 'visible'=>0,),
124  'note_private' => array('type'=>'html', 'label'=>'NotePrivate', 'enabled'=>'1', 'position'=>71, 'notnull'=>0, 'visible'=>0,),
125  );
126  public $rowid;
127  public $label;
128  public $description;
129  public $date_creation;
130  public $tms;
131  public $fk_user_creat;
132  public $fk_user_modif;
133  public $required_level;
134  public $date_validite;
135  public $temps_theorique;
136  public $skill_type;
137  public $note_public;
138  public $note_private;
139  // END MODULEBUILDER PROPERTIES
140 
141 
142  // If this object has a subtable with lines
143 
144  // /**
145  // * @var string Name of subtable line
146  // */
147  // public $table_element_line = 'hrm_skillline';
148 
149  // /**
150  // * @var string Field with ID of parent key if this object has a parent
151  // */
152  public $fk_element = 'fk_skill';
153 
154  // /**
155  // * @var string Name of subtable class that manage subtable lines
156  // */
157  // public $class_element_line = 'Skillline';
158 
159  // /**
160  // * @var array List of child tables. To test if we can delete object.
161  // */
162  protected $childtables = array('hrm_skillrank', 'hrm_evaluationdet');
163 
164  // /**
165  // * @var array List of child tables. To know object to delete on cascade.
166  // * If name matches '@ClassNAme:FilePathClass;ParentFkFieldName' it will
167  // * call method deleteByParentField(parentId, ParentFkFieldName) to fetch and delete child object
168  // */
169  protected $childtablesoncascade = array('hrm_skilldet');
170 
171  // /**
172  // * @var SkillLine[] Array of subtable lines
173  // */
174  // public $lines = array();
175 
176 
177 
183  public function __construct(DoliDB $db)
184  {
185  global $conf, $langs;
186 
187  $this->db = $db;
188 
189  if (empty($conf->global->MAIN_SHOW_TECHNICAL_ID) && isset($this->fields['rowid'])) {
190  $this->fields['rowid']['visible'] = 0;
191  }
192  if (empty($conf->multicompany->enabled) && isset($this->fields['entity'])) {
193  $this->fields['entity']['enabled'] = 0;
194  }
195 
196  // Example to show how to set values of fields definition dynamically
197  /*if ($user->rights->hrm->skill->read) {
198  $this->fields['myfield']['visible'] = 1;
199  $this->fields['myfield']['noteditable'] = 0;
200  }*/
201 
202  // Unset fields that are disabled
203  foreach ($this->fields as $key => $val) {
204  if (isset($val['enabled']) && empty($val['enabled'])) {
205  unset($this->fields[$key]);
206  }
207  }
208 
209  // Translate some data of arrayofkeyval
210  if (is_object($langs)) {
211  foreach ($this->fields as $key => $val) {
212  if (!empty($val['arrayofkeyval']) && is_array($val['arrayofkeyval'])) {
213  foreach ($val['arrayofkeyval'] as $key2 => $val2) {
214  $this->fields[$key]['arrayofkeyval'][$key2] = $langs->trans($val2);
215  }
216  }
217  }
218  }
219  }
220 
228  public function create(User $user, $notrigger = false)
229  {
230  global $langs,$conf;
231 
232  $resultcreate = $this->createCommon($user, $notrigger);
233 
234 
235  if ($resultcreate > 0) {
236  // skillDet create
237  $this->createSkills();
238  }
239 
240  return $resultcreate;
241  }
242 
249  public function createSkills($i = 1)
250  {
251  global $conf, $user, $langs;
252 
253  $MaxNumberSkill = isset($conf->global->HRM_MAXRANK) ? $conf->global->HRM_MAXRANK : self::DEFAULT_MAX_RANK_PER_SKILL;
254  $defaultSkillDesc = !empty($conf->global->HRM_DEFAULT_SKILL_DESCRIPTION) ? $conf->global->HRM_DEFAULT_SKILL_DESCRIPTION : $langs->trans("NoDescription");
255 
256  $error = 0;
257 
258  require_once __DIR__ . '/skilldet.class.php';
259 
260  $this->db->begin();
261 
262  // Create level of skills
263  for ($i; $i <= $MaxNumberSkill ; $i++) {
264  $skilldet = new Skilldet($this->db);
265  $skilldet->description = $defaultSkillDesc . " " . $i;
266  $skilldet->rankorder = $i;
267  $skilldet->fk_skill = $this->id;
268 
269  $result = $skilldet->create($user);
270  if ($result <= 0) {
271  $error++;
272  }
273  }
274 
275  if (! $error) {
276  $this->db->commit();
277 
278  setEventMessage($langs->trans('SkillCreated'), $i);
279  return 1;
280  } else {
281  $this->db->rollback();
282  return -1;
283  }
284  }
285 
293  public function createFromClone(User $user, $fromid)
294  {
295  global $langs, $extrafields;
296  $error = 0;
297 
298  dol_syslog(__METHOD__, LOG_DEBUG);
299 
300  $object = new self($this->db);
301 
302  $this->db->begin();
303 
304  // Load source object
305  $result = $object->fetchCommon($fromid);
306  if ($result > 0 && !empty($object->table_element_line)) {
307  $object->fetchLines();
308  }
309 
310  // get lines so they will be clone
311  //foreach($this->lines as $line)
312  // $line->fetch_optionals();
313 
314  // Reset some properties
315  unset($object->id);
316  unset($object->fk_user_creat);
317  unset($object->import_key);
318 
319  // Clear fields
320  if (property_exists($object, 'ref')) {
321  $object->ref = empty($this->fields['ref']['default']) ? "Copy_Of_".$object->ref : $this->fields['ref']['default'];
322  }
323  if (property_exists($object, 'label')) {
324  $object->label = empty($this->fields['label']['default']) ? $langs->trans("CopyOf")." ".$object->label : $this->fields['label']['default'];
325  }
326  if (property_exists($object, 'status')) {
327  $object->status = self::STATUS_DRAFT;
328  }
329  if (property_exists($object, 'date_creation')) {
330  $object->date_creation = dol_now();
331  }
332  if (property_exists($object, 'date_modification')) {
333  $object->date_modification = null;
334  }
335  // ...
336  // Clear extrafields that are unique
337  if (is_array($object->array_options) && count($object->array_options) > 0) {
338  $extrafields->fetch_name_optionals_label($this->table_element);
339  foreach ($object->array_options as $key => $option) {
340  $shortkey = preg_replace('/options_/', '', $key);
341  if (!empty($extrafields->attributes[$this->table_element]['unique'][$shortkey])) {
342  //var_dump($key); var_dump($clonedObj->array_options[$key]); exit;
343  unset($object->array_options[$key]);
344  }
345  }
346  }
347 
348  // Create clone
349  $object->context['createfromclone'] = 'createfromclone';
350  $result = $object->createCommon($user);
351  if ($result < 0) {
352  $error++;
353  $this->error = $object->error;
354  $this->errors = $object->errors;
355  }
356 
357  if (!$error) {
358  // copy internal contacts
359  if ($this->copy_linked_contact($object, 'internal') < 0) {
360  $error++;
361  }
362  }
363 
364  if (!$error) {
365  // copy external contacts if same company
366  if (property_exists($this, 'fk_soc') && $this->fk_soc == $object->socid) {
367  if ($this->copy_linked_contact($object, 'external') < 0) {
368  $error++;
369  }
370  }
371  }
372 
373  unset($object->context['createfromclone']);
374 
375  // End
376  if (!$error) {
377  $this->db->commit();
378  return $object;
379  } else {
380  $this->db->rollback();
381  return -1;
382  }
383  }
384 
392  public function fetch($id, $ref = null)
393  {
394  $result = $this->fetchCommon($id, $ref);
395  if ($result > 0 && !empty($this->table_element_line)) {
396  $this->fetchLines();
397  }
398  return $result;
399  }
400 
406  public function fetchLines()
407  {
408  $this->lines = array();
409  require_once __DIR__ . '/skilldet.class.php';
410  $skilldet = new Skilldet($this->db);
411  $this->lines = $skilldet->fetchAll('ASC', '', '', '', array('fk_skill' => $this->id), '');
412 
413  if (is_array($this->lines)) {
414  return (count($this->lines) > 0) ? $this->lines : array();
415  } elseif ($this->lines < 0) {
416  $this->errors = array_merge($this->errors, $skilldet->errors);
417  $this->error = $skilldet->error;
418  return $this->lines;
419  }
420  }
421 
422 
434  public function fetchAll($sortorder = '', $sortfield = '', $limit = 0, $offset = 0, array $filter = array(), $filtermode = 'AND')
435  {
436  global $conf;
437 
438  dol_syslog(__METHOD__, LOG_DEBUG);
439 
440  $records = array();
441 
442  $sql = 'SELECT ';
443  $sql .= $this->getFieldList('t');
444  $sql .= ' FROM '.MAIN_DB_PREFIX.$this->table_element.' as t';
445  if (isset($this->ismultientitymanaged) && $this->ismultientitymanaged == 1) {
446  $sql .= ' WHERE t.entity IN ('.getEntity($this->table_element).')';
447  } else {
448  $sql .= ' WHERE 1 = 1';
449  }
450  // Manage filter
451  $sqlwhere = array();
452  if (count($filter) > 0) {
453  foreach ($filter as $key => $value) {
454  if ($key == 't.rowid') {
455  $sqlwhere[] = $key.'='.$value;
456  } elseif (in_array($this->fields[$key]['type'], array('date', 'datetime', 'timestamp'))) {
457  $sqlwhere[] = $key.' = \''.$this->db->idate($value).'\'';
458  } elseif ($key == 'customsql') {
459  $sqlwhere[] = $value;
460  } elseif (strpos($value, '%') === false) {
461  $sqlwhere[] = $key.' IN ('.$this->db->sanitize($this->db->escape($value)).')';
462  } else {
463  $sqlwhere[] = $key.' LIKE \'%'.$this->db->escape($value).'%\'';
464  }
465  }
466  }
467  if (count($sqlwhere) > 0) {
468  $sql .= " AND (".implode(" ".$filtermode." ", $sqlwhere).")";
469  }
470 
471  if (!empty($sortfield)) {
472  $sql .= $this->db->order($sortfield, $sortorder);
473  }
474  if (!empty($limit)) {
475  $sql .= ' '.$this->db->plimit($limit, $offset);
476  }
477 
478  $resql = $this->db->query($sql);
479  if ($resql) {
480  $num = $this->db->num_rows($resql);
481  $i = 0;
482  while ($i < ($limit ? min($limit, $num) : $num)) {
483  $obj = $this->db->fetch_object($resql);
484 
485  $record = new self($this->db);
486  $record->setVarsFromFetchObj($obj);
487 
488  $records[$record->id] = $record;
489 
490  $i++;
491  }
492  $this->db->free($resql);
493 
494  return $records;
495  } else {
496  $this->errors[] = 'Error '.$this->db->lasterror();
497  dol_syslog(__METHOD__.' '.join(',', $this->errors), LOG_ERR);
498 
499  return -1;
500  }
501  }
502 
510  public function update(User $user, $notrigger = false)
511  {
512  return $this->updateCommon($user, $notrigger);
513  }
514 
522  public function delete(User $user, $notrigger = false)
523  {
524  return $this->deleteCommon($user, $notrigger);;
525  }
526 
535  public function deleteLine(User $user, $idline, $notrigger = false)
536  {
537  if ($this->status < 0) {
538  $this->error = 'ErrorDeleteLineNotAllowedByObjectStatus';
539  return -2;
540  }
541 
542  return $this->deleteLineCommon($user, $idline, $notrigger);
543  }
544 
545 
553  public function validate($user, $notrigger = 0)
554  {
555  global $conf, $langs;
556 
557  require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
558 
559  $error = 0;
560 
561  // Protection
562  if ($this->status == self::STATUS_VALIDATED) {
563  dol_syslog(get_class($this)."::validate action abandonned: already validated", LOG_WARNING);
564  return 0;
565  }
566 
567  /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->skill->write))
568  || (! empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->skill->skill_advance->validate))))
569  {
570  $this->error='NotEnoughPermissions';
571  dol_syslog(get_class($this)."::valid ".$this->error, LOG_ERR);
572  return -1;
573  }*/
574 
575  $now = dol_now();
576 
577  $this->db->begin();
578 
579  // Define new ref
580  if (!$error && (preg_match('/^[\(]?PROV/i', $this->ref) || empty($this->ref))) { // empty should not happened, but when it occurs, the test save life
581  $num = $this->getNextNumRef();
582  } else {
583  $num = $this->ref;
584  }
585  $this->newref = $num;
586 
587  if (!empty($num)) {
588  // Validate
589  $sql = "UPDATE ".MAIN_DB_PREFIX.$this->table_element;
590  $sql .= " SET ref = '".$this->db->escape($num)."',";
591  $sql .= " status = ".self::STATUS_VALIDATED;
592  if (!empty($this->fields['date_validation'])) {
593  $sql .= ", date_validation = '".$this->db->idate($now)."'";
594  }
595  if (!empty($this->fields['fk_user_valid'])) {
596  $sql .= ", fk_user_valid = ".((int) $user->id);
597  }
598  $sql .= " WHERE rowid = ".((int) $this->id);
599 
600  dol_syslog(get_class($this)."::validate()", LOG_DEBUG);
601  $resql = $this->db->query($sql);
602  if (!$resql) {
603  dol_print_error($this->db);
604  $this->error = $this->db->lasterror();
605  $error++;
606  }
607 
608  if (!$error && !$notrigger) {
609  // Call trigger
610  $result = $this->call_trigger('SKILL_VALIDATE', $user);
611  if ($result < 0) {
612  $error++;
613  }
614  // End call triggers
615  }
616  }
617 
618  if (!$error) {
619  $this->oldref = $this->ref;
620 
621  // Rename directory if dir was a temporary ref
622  if (preg_match('/^[\(]?PROV/i', $this->ref)) {
623  // Now we rename also files into index
624  $sql = 'UPDATE '.MAIN_DB_PREFIX."ecm_files set filename = CONCAT('".$this->db->escape($this->newref)."', SUBSTR(filename, ".(strlen($this->ref) + 1).")), filepath = 'skill/".$this->db->escape($this->newref)."'";
625  $sql .= " WHERE filename LIKE '".$this->db->escape($this->ref)."%' AND filepath = 'skill/".$this->db->escape($this->ref)."' and entity = ".$conf->entity;
626  $resql = $this->db->query($sql);
627  if (!$resql) {
628  $error++; $this->error = $this->db->lasterror();
629  }
630 
631  // We rename directory ($this->ref = old ref, $num = new ref) in order not to lose the attachments
632  $oldref = dol_sanitizeFileName($this->ref);
633  $newref = dol_sanitizeFileName($num);
634  $dirsource = $conf->hrm->dir_output.'/skill/'.$oldref;
635  $dirdest = $conf->hrm->dir_output.'/skill/'.$newref;
636  if (!$error && file_exists($dirsource)) {
637  dol_syslog(get_class($this)."::validate() rename dir ".$dirsource." into ".$dirdest);
638 
639  if (@rename($dirsource, $dirdest)) {
640  dol_syslog("Rename ok");
641  // Rename docs starting with $oldref with $newref
642  $listoffiles = dol_dir_list($conf->hrm->dir_output.'/skill/'.$newref, 'files', 1, '^'.preg_quote($oldref, '/'));
643  foreach ($listoffiles as $fileentry) {
644  $dirsource = $fileentry['name'];
645  $dirdest = preg_replace('/^'.preg_quote($oldref, '/').'/', $newref, $dirsource);
646  $dirsource = $fileentry['path'].'/'.$dirsource;
647  $dirdest = $fileentry['path'].'/'.$dirdest;
648  @rename($dirsource, $dirdest);
649  }
650  }
651  }
652  }
653  }
654 
655  // Set new ref and current status
656  if (!$error) {
657  $this->ref = $num;
658  $this->status = self::STATUS_VALIDATED;
659  }
660 
661  if (!$error) {
662  $this->db->commit();
663  return 1;
664  } else {
665  $this->db->rollback();
666  return -1;
667  }
668  }
669 
670 
678  public function setDraft($user, $notrigger = 0)
679  {
680  // Protection
681  if ($this->status <= self::STATUS_DRAFT) {
682  return 0;
683  }
684 
685  /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->write))
686  || (! empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->hrm_advance->validate))))
687  {
688  $this->error='Permission denied';
689  return -1;
690  }*/
691 
692  return $this->setStatusCommon($user, self::STATUS_DRAFT, $notrigger, 'SKILL_UNVALIDATE');
693  }
694 
702  public function cancel($user, $notrigger = 0)
703  {
704  // Protection
705  if ($this->status != self::STATUS_VALIDATED) {
706  return 0;
707  }
708 
709  /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->write))
710  || (! empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->hrm_advance->validate))))
711  {
712  $this->error='Permission denied';
713  return -1;
714  }*/
715 
716  return $this->setStatusCommon($user, self::STATUS_CANCELED, $notrigger, 'SKILL_CANCEL');
717  }
718 
726  public function reopen($user, $notrigger = 0)
727  {
728  // Protection
729  if ($this->status != self::STATUS_CANCELED) {
730  return 0;
731  }
732 
733  /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->write))
734  || (! empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ! empty($user->rights->hrm->hrm_advance->validate))))
735  {
736  $this->error='Permission denied';
737  return -1;
738  }*/
739 
740  return $this->setStatusCommon($user, self::STATUS_VALIDATED, $notrigger, 'SKILL_REOPEN');
741  }
742 
763  public function getNomUrl($withpicto = 0, $option = '', $notooltip = 0, $morecss = '', $save_lastsearch_value = -1)
764  {
765  global $conf, $langs, $hookmanager;
766 
767  if (!empty($conf->dol_no_mouse_hover)) {
768  $notooltip = 1; // Force disable tooltips
769  }
770 
771  $result = '';
772 
773  $label = img_picto('', $this->picto).' <u>'.$langs->trans("Skill").'</u>';
774  if (isset($this->status)) {
775  $label .= ' '.$this->getLibStatut(5);
776  }
777  $label .= '<br>';
778  $label .= '<b>'.$langs->trans('Label').':</b> '.$this->label;
779 
780  $url = dol_buildpath('/hrm/skill_card.php', 1).'?id='.$this->id;
781 
782  if ($option != 'nolink') {
783  // Add param to save lastsearch_values or not
784  $add_save_lastsearch_values = ($save_lastsearch_value == 1 ? 1 : 0);
785  if ($save_lastsearch_value == -1 && preg_match('/list\.php/', $_SERVER["PHP_SELF"])) {
786  $add_save_lastsearch_values = 1;
787  }
788  if ($add_save_lastsearch_values) {
789  $url .= '&save_lastsearch_values=1';
790  }
791  }
792 
793  $linkclose = '';
794  if (empty($notooltip)) {
795  if (!empty($conf->global->MAIN_OPTIMIZEFORTEXTBROWSER)) {
796  $label = $langs->trans("ShowSkill");
797  $linkclose .= ' alt="'.dol_escape_htmltag($label, 1).'"';
798  }
799  $linkclose .= ' title="'.dol_escape_htmltag($label, 1).'"';
800  $linkclose .= ' class="classfortooltip'.($morecss ? ' '.$morecss : '').'"';
801  } else {
802  $linkclose = ($morecss ? ' class="'.$morecss.'"' : '');
803  }
804 
805  if ($option == 'nolink') {
806  $linkstart = '<span';
807  } else {
808  $linkstart = '<a href="'.$url.'"';
809  }
810  $linkstart .= $linkclose.'>';
811  if ($option == 'nolink') {
812  $linkend = '</span>';
813  } else {
814  $linkend = '</a>';
815  }
816 
817  $result .= $linkstart;
818 
819  if (empty($this->showphoto_on_popup)) {
820  if ($withpicto) {
821  $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);
822  }
823  } else {
824  if ($withpicto) {
825  require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
826 
827  list($class, $module) = explode('@', $this->picto);
828  $upload_dir = $conf->$module->multidir_output[$conf->entity]."/$class/".dol_sanitizeFileName($this->ref);
829  $filearray = dol_dir_list($upload_dir, "files");
830  $filename = $filearray[0]['name'];
831  if (!empty($filename)) {
832  $pospoint = strpos($filearray[0]['name'], '.');
833 
834  $pathtophoto = $class.'/'.$this->ref.'/thumbs/'.substr($filename, 0, $pospoint).'_mini'.substr($filename, $pospoint);
835  if (empty($conf->global->{strtoupper($module.'_'.$class).'_FORMATLISTPHOTOSASUSERS'})) {
836  $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>';
837  } else {
838  $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>';
839  }
840 
841  $result .= '</div>';
842  } else {
843  $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);
844  }
845  }
846  }
847 
848  if ($withpicto != 2) {
849  $result .= $this->label;
850  }
851 
852  $result .= $linkend;
853  //if ($withpicto != 2) $result.=(($addlabel && $this->label) ? $sep . dol_trunc($this->label, ($addlabel > 1 ? $addlabel : 0)) : '');
854 
855  global $action, $hookmanager;
856  $hookmanager->initHooks(array('skilldao'));
857  $parameters = array('id'=>$this->id, 'getnomurl' => &$result);
858  $reshook = $hookmanager->executeHooks('getNomUrl', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
859  if ($reshook > 0) {
860  $result = $hookmanager->resPrint;
861  } else {
862  $result .= $hookmanager->resPrint;
863  }
864 
865  return $result;
866  }
867 
874  public function getLibStatut($mode = 0)
875  {
876  return $this->LibStatut($this->status, $mode);
877  }
878 
879  // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
887  public function LibStatut($status, $mode = 0)
888  {
889  // phpcs:enable
890  if (empty($this->labelStatus) || empty($this->labelStatusShort)) {
891  global $langs;
892  //$langs->load("hrm");
893  $this->labelStatus[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
894  $this->labelStatus[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Enabled');
895  $this->labelStatus[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('Disabled');
896  $this->labelStatusShort[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
897  $this->labelStatusShort[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Enabled');
898  $this->labelStatusShort[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('Disabled');
899  }
900 
901  $statusType = 'status'.$status;
902  //if ($status == self::STATUS_VALIDATED) $statusType = 'status1';
903  if ($status == self::STATUS_CANCELED) {
904  $statusType = 'status6';
905  }
906 
907  return dolGetStatus($this->labelStatus[$status], $this->labelStatusShort[$status], '', $statusType, $mode);
908  }
909 
916  public function info($id)
917  {
918  $sql = 'SELECT rowid, date_creation as datec, tms as datem,';
919  $sql .= ' fk_user_creat, fk_user_modif';
920  $sql .= ' FROM '.MAIN_DB_PREFIX.$this->table_element.' as t';
921  $sql .= ' WHERE t.rowid = '.((int) $id);
922  $result = $this->db->query($sql);
923  if ($result) {
924  if ($this->db->num_rows($result)) {
925  $obj = $this->db->fetch_object($result);
926  $this->id = $obj->rowid;
927 
928  $this->user_creation_id = $obj->fk_user_creat;
929  $this->user_modification_id = $obj->fk_user_modif;
930  $this->date_creation = $this->db->jdate($obj->datec);
931  $this->date_modification = empty($obj->datem) ? '' : $this->db->jdate($obj->datem);
932  }
933 
934  $this->db->free($result);
935  } else {
936  dol_print_error($this->db);
937  }
938  }
939 
946  public function initAsSpecimen()
947  {
948  // Set here init that are not commonf fields
949  // $this->property1 = ...
950  // $this->property2 = ...
951 
952  $this->initAsSpecimenCommon();
953  }
954 
960  public function getLinesArray()
961  {
962  $this->lines = array();
963 
964  $objectline = new Skilldet($this->db);
965  $result = $objectline->fetchAll('ASC', 'rankorder', 0, 0, array('customsql'=>'fk_skill = '.$this->id));
966 
967  if (is_numeric($result)) {
968  $this->error = $this->error;
969  $this->errors = $this->errors;
970  return $result;
971  } else {
972  $this->lines = $result;
973  return $this->lines;
974  }
975  }
976 
982  public function getNextNumRef()
983  {
984  global $langs, $conf;
985  $langs->load("hrm");
986 
987  if (empty($conf->global->hrm_SKILL_ADDON)) {
988  $conf->global->hrm_SKILL_ADDON = 'mod_skill_standard';
989  }
990 
991  if (!empty($conf->global->hrm_SKILL_ADDON)) {
992  $mybool = false;
993 
994  $file = $conf->global->hrm_SKILL_ADDON.".php";
995  $classname = $conf->global->hrm_SKILL_ADDON;
996 
997  // Include file with class
998  $dirmodels = array_merge(array('/'), (array) $conf->modules_parts['models']);
999  foreach ($dirmodels as $reldir) {
1000  $dir = dol_buildpath($reldir."core/modules/hrm/");
1001 
1002  // Load file with numbering class (if found)
1003  $mybool |= @include_once $dir.$file;
1004  }
1005 
1006  if ($mybool === false) {
1007  dol_print_error('', "Failed to include file ".$file);
1008  return '';
1009  }
1010 
1011  if (class_exists($classname)) {
1012  $obj = new $classname();
1013  $numref = $obj->getNextValue($this);
1014 
1015  if ($numref != '' && $numref != '-1') {
1016  return $numref;
1017  } else {
1018  $this->error = $obj->error;
1019  //dol_print_error($this->db,get_class($this)."::getNextNumRef ".$obj->error);
1020  return "";
1021  }
1022  } else {
1023  print $langs->trans("Error")." ".$langs->trans("ClassNotFound").' '.$classname;
1024  return "";
1025  }
1026  } else {
1027  print $langs->trans("ErrorNumberingModuleNotSetup", $this->element);
1028  return "";
1029  }
1030  }
1031 
1043  public function generateDocument($modele, $outputlangs, $hidedetails = 0, $hidedesc = 0, $hideref = 0, $moreparams = null)
1044  {
1045  global $conf, $langs;
1046 
1047  $result = 0;
1048  $includedocgeneration = 0;
1049 
1050  $langs->load("hrm");
1051 
1052  if (!dol_strlen($modele)) {
1053  $modele = 'standard_skill';
1054 
1055  if (!empty($this->model_pdf)) {
1056  $modele = $this->model_pdf;
1057  } elseif (!empty($conf->global->SKILL_ADDON_PDF)) {
1058  $modele = $conf->global->SKILL_ADDON_PDF;
1059  }
1060  }
1061 
1062  $modelpath = "core/modules/hrm/doc/";
1063 
1064  if ($includedocgeneration && !empty($modele)) {
1065  $result = $this->commonGenerateDocument($modelpath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams);
1066  }
1067 
1068  return $result;
1069  }
1070 
1078  public function doScheduledJob()
1079  {
1080  global $conf, $langs;
1081 
1082  //$conf->global->SYSLOG_FILE = 'DOL_DATA_ROOT/dolibarr_mydedicatedlofile.log';
1083 
1084  $error = 0;
1085  $this->output = '';
1086  $this->error = '';
1087 
1088  dol_syslog(__METHOD__, LOG_DEBUG);
1089 
1090  $now = dol_now();
1091 
1092  $this->db->begin();
1093 
1094  // ...
1095 
1096  $this->db->commit();
1097 
1098  return $error;
1099  }
1100 
1105  public static function typeCodeToLabel($code)
1106  {
1107  global $langs;
1108  $result = '';
1109  switch ($code) {
1110  case 0 : $result = $langs->trans("TypeKnowHow"); break; //"Savoir Faire"
1111  case 1 : $result = $langs->trans("TypeHowToBe"); break; // "Savoir être"
1112  case 9 : $result = $langs->trans("TypeKnowledge"); break; //"Savoir"
1113  }
1114  return $result;
1115  }
1116 }
setDraft($user, $notrigger=0)
Set draft status.
createFromClone(User $user, $fromid)
Clone an object into another one.
fetchAll($sortorder= '', $sortfield= '', $limit=0, $offset=0, array $filter=array(), $filtermode= 'AND')
Load list of objects in memory from the database.
deleteCommon(User $user, $notrigger=false, $forcechilddeletion=0)
Delete object in database.
getLinesArray()
Create an array of lines.
doScheduledJob()
Action executed by scheduler CAN BE A CRON TASK.
$conf db
API class for accounts.
Definition: inc.php:41
dol_now($mode= 'auto')
Return date for now.
Class to manage Dolibarr users.
Definition: user.class.php:44
Class to manage Dolibarr database access.
reopen($user, $notrigger=0)
Set back to validated status.
setEventMessage($mesgs, $style= 'mesgs')
Set event message in dol_events session object.
createSkills($i=1)
createSkills
createCommon(User $user, $notrigger=false)
Create object into database.
fetchLines()
Load object lines in memory from the database.
validate($user, $notrigger=0)
Validate object.
dol_buildpath($path, $type=0, $returnemptyifnotfound=0)
Return path of url or filesystem.
getLibStatut($mode=0)
Return the label of the status.
Class for Skill.
Definition: skill.class.php:36
dol_strlen($string, $stringencoding= 'UTF-8')
Make a strlen call.
getFieldList($alias= '')
Function to concat keys of fields.
initAsSpecimen()
Initialise object with example values Id must be 0 if object instance is a specimen.
img_picto($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt= '', $morecss= '', $marginleftonlyshort=2)
Show picto whatever it&#39;s its name (generic function)
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename= '', $restricttologhandler= '', $logcontext=null)
Write log message into outputs.
deleteLine(User $user, $idline, $notrigger=false)
Delete a line of object in database.
img_object($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0)
Show a picto called object_picto (generic function)
updateCommon(User $user, $notrigger=false)
Update object into database.
dol_sanitizeFileName($str, $newstr= '_', $unaccent=1)
Clean a string to use it as a file name.
dol_dir_list($path, $types="all", $recursive=0, $filter="", $excludefilter=null, $sortcriteria="name", $sortorder=SORT_ASC, $mode=0, $nohook=0, $relativename="", $donotfollowsymlinks=0)
Scan a directory and return a list of files/directories.
Definition: files.lib.php:60
Class for Skilldet.
getNomUrl($withpicto=0, $option= '', $notooltip=0, $morecss= '', $save_lastsearch_value=-1)
Return a link to the object card (with optionaly the picto)
__construct(DoliDB $db)
Constructor.
if(isModEnabled('facture')&&!empty($user->rights->facture->lire)) if((isModEnabled('fournisseur')&&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD)&&$user->rights->fournisseur->facture->lire)||(isModEnabled('supplier_invoice')&&$user->rights->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->rights->commande->lire &&empty($conf->global->WORKFLOW_DISABLE_CREATE_INVOICE_FROM_ORDER)) $resql
Social contributions to pay.
Definition: index.php:742
create(User $user, $notrigger=false)
Create object into database.
info($id)
Load the info information in the object.
deleteLineCommon(User $user, $idline, $notrigger=false)
Delete a line of object in database.
copy_linked_contact($objFrom, $source= 'internal')
Copy contact from one element to current.
LibStatut($status, $mode=0)
Return the status.
call_trigger($triggerName, $user)
Call trigger based on this instance.
update(User $user, $notrigger=false)
Update object into database.
$object ref
Definition: info.php:77
dol_print_error($db= '', $error= '', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
setStatusCommon($user, $status, $notrigger=0, $triggercode= '')
Set to a status.
dolGetStatus($statusLabel= '', $statusLabelShort= '', $html= '', $statusType= 'status0', $displayMode=0, $url= '', $params=array())
Output the badge of a status.
cancel($user, $notrigger=0)
Set cancel status.
fetch($id, $ref=null)
Load object in memory from the database.
static typeCodeToLabel($code)
generateDocument($modele, $outputlangs, $hidedetails=0, $hidedesc=0, $hideref=0, $moreparams=null)
Create a document onto disk according to template module.
getNextNumRef()
Returns the reference to the following non used object depending on the active numbering module...
Parent class of all other business classes (invoices, contracts, proposals, orders, ...)
fetchCommon($id, $ref=null, $morewhere= '')
Load object in memory from the database.