dolibarr 21.0.0-alpha
recruitmentcandidature.class.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2020 Laurent Destailleur <eldy@users.sourceforge.net>
3 * Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
4 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 3 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <https://www.gnu.org/licenses/>.
18 */
19
26// Put here all includes required by your class file
27require_once DOL_DOCUMENT_ROOT.'/core/class/commonobject.class.php';
28//require_once DOL_DOCUMENT_ROOT . '/societe/class/societe.class.php';
29//require_once DOL_DOCUMENT_ROOT . '/product/class/product.class.php';
30
35{
39 public $module = 'recruitment';
40
44 public $element = 'recruitmentcandidature';
45
49 public $table_element = 'recruitment_recruitmentcandidature';
50
54 public $picto = 'recruitmentcandidature';
55
59 public $email_fields_no_propagate_in_actioncomm;
60
61
62 const STATUS_DRAFT = 0;
63 const STATUS_VALIDATED = 1;
64 //const STATUS_INTERVIEW_SCHEDULED = 2;
65 const STATUS_CONTRACT_PROPOSED = 3;
66 const STATUS_CONTRACT_SIGNED = 5;
67 const STATUS_CONTRACT_REFUSED = 6;
68 const STATUS_REFUSED = 8;
69 const STATUS_CANCELED = 9;
70
71
97 // BEGIN MODULEBUILDER PROPERTIES
101 public $fields = array(
102 'rowid' => array('type' => 'integer', 'label' => 'TechnicalID', 'enabled' => 1, 'position' => 1, 'notnull' => 1, 'visible' => 0, 'noteditable' => 1, 'index' => 1, 'comment' => "Id"),
103 'entity' => array('type' => 'integer', 'label' => 'Entity', 'enabled' => 1, 'visible' => 0, 'position' => 5, 'notnull' => 1, 'default' => '1', 'index' => 1),
104 'ref' => array('type' => 'varchar(128)', 'label' => 'Ref', 'enabled' => 1, 'position' => 10, 'notnull' => 1, 'visible' => 4, 'noteditable' => 1, 'default' => '(PROV)', 'index' => 1, 'searchall' => 1, 'showoncombobox' => 1, 'comment' => "Reference of candidature", 'csslist' => 'nowraponall'),
105 'fk_recruitmentjobposition' => array('type' => 'integer:RecruitmentJobPosition:recruitment/class/recruitmentjobposition.class.php:0:(t.status:=:1)', 'label' => 'Job', 'enabled' => 1, 'position' => 15, 'notnull' => 0, 'visible' => 1, 'index' => 1, 'picto' => 'recruitmentjobposition', 'css' => 'minwidth300 maxwidth500 widthcentpercentminusx', 'csslist' => 'minwidth100 nowraponall'),
106 'note_public' => array('type' => 'html', 'label' => 'NotePublic', 'enabled' => 1, 'position' => 61, 'notnull' => 0, 'visible' => 0,),
107 'note_private' => array('type' => 'html', 'label' => 'NotePrivate', 'enabled' => 1, 'position' => 62, 'notnull' => 0, 'visible' => 0,),
108 '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', 'csslist' => 'tdoverflowmax100'),
109 'fk_user_modif' => array('type' => 'integer:User:user/class/user.class.php', 'label' => 'UserModif', 'enabled' => 1, 'position' => 511, 'notnull' => -1, 'visible' => -2, 'csslist' => 'tdoverflowmax100'),
110 'lastname' => array('type' => 'varchar(128)', 'label' => 'Lastname', 'enabled' => 1, 'position' => 20, 'notnull' => 0, 'visible' => 1, 'csslist' => 'tdoverflowmax150'),
111 'firstname' => array('type' => 'varchar(128)', 'label' => 'Firstname', 'enabled' => 1, 'position' => 21, 'notnull' => 0, 'visible' => 1, 'csslist' => 'tdoverflowmax150'),
112 'email' => array('type' => 'email', 'label' => 'EMail', 'enabled' => 1, 'position' => 30, 'notnull' => 1, 'visible' => 1, 'picto' => 'email', 'csslist' => 'tdoverflowmax150'),
113 'phone' => array('type' => 'phone', 'label' => 'Phone', 'enabled' => 1, 'position' => 31, 'notnull' => 0, 'visible' => 1, 'picto' => 'phone', 'csslist' => 'tdoverflowmax150'),
114 'date_birth' => array('type' => 'date', 'label' => 'DateOfBirth', 'enabled' => 1, 'position' => 70, 'visible' => -1,),
115 'email_msgid' => array('type' => 'varchar(255)', 'label' => 'EmailMsgID', 'visible' => -2, 'enabled' => 1, 'position' => 540, 'notnull' => -1, 'help' => 'EmailMsgIDDesc'),
116 'email_date' => array('type' => 'datetime', 'label' => 'EmailDate', 'visible' => -2, 'enabled' => 1, 'position' => 541),
117 //'fk_recruitment_origin' => array('type'=>'integer:CRecruitmentOrigin:recruitment/class/crecruitmentorigin.class.php', 'label'=>'Origin', 'enabled'=>'1', 'position'=>45, 'visible'=>1, 'index'=>1),
118 'remuneration_requested' => array('type' => 'integer', 'label' => 'RequestedRemuneration', 'enabled' => 1, 'position' => 80, 'notnull' => 0, 'visible' => -1,),
119 'remuneration_proposed' => array('type' => 'integer', 'label' => 'ProposedRemuneration', 'enabled' => 1, 'position' => 81, 'notnull' => 0, 'visible' => -1,),
120 'description' => array('type' => 'html', 'label' => 'Description', 'enabled' => 1, 'position' => 300, 'notnull' => 0, 'visible' => 3, 'cssview' => 'wordbreak'),
121 'date_creation' => array('type' => 'datetime', 'label' => 'DateCreation', 'enabled' => 1, 'position' => 500, 'notnull' => 1, 'visible' => -4, 'csslist' => 'nowraponall'),
122 'tms' => array('type' => 'timestamp', 'label' => 'DateModification', 'enabled' => 1, 'position' => 501, 'notnull' => 0, 'visible' => -2, 'csslist' => 'nowraponall'),
123 'fk_user' => array('type' => 'integer:User:user/class/user.class.php', 'label' => 'LinkedToDolibarrUser', 'enabled' => 1, 'position' => 600, 'notnull' => 0, 'visible' => -1, 'csslist' => 'tdoverflowmax100'),
124 'import_key' => array('type' => 'varchar(14)', 'label' => 'ImportId', 'enabled' => 1, 'position' => 1000, 'notnull' => -1, 'visible' => -2,),
125 'model_pdf' => array('type' => 'varchar(255)', 'label' => 'Model pdf', 'enabled' => 1, 'position' => 1010, 'notnull' => -1, 'visible' => 0,),
126 'status' => array('type' => 'smallint', 'label' => 'Status', 'enabled' => 1, 'position' => 1000, 'notnull' => 1, 'visible' => 2, 'index' => 1, 'default' => '0', 'arrayofkeyval' => array('0' => 'Draft', '1' => 'Received', '3' => 'ContractProposed', '5' => 'ContractSigned', '8' => 'Refused', '9' => 'Canceled')),
127 );
128 public $rowid;
129 public $entity;
130 public $ref;
131 public $fk_recruitmentjobposition;
132 public $description;
133 public $fk_user_creat;
134 public $fk_user_modif;
135 public $fk_user;
136 public $lastname;
137 public $firstname;
138 public $email;
139 public $phone;
140 public $date_birth;
141 public $email_msgid;
142 public $email_date;
143 public $remuneration_requested;
144 public $remuneration_proposed;
145 public $fk_recruitment_origin;
146 public $import_key;
147 public $model_pdf;
148 public $status;
149 // END MODULEBUILDER PROPERTIES
150
151
157 public function __construct(DoliDB $db)
158 {
159 global $conf, $langs;
160
161 $this->db = $db;
162
163 $this->ismultientitymanaged = 1;
164 $this->isextrafieldmanaged = 1;
165
166 if (!getDolGlobalString('MAIN_SHOW_TECHNICAL_ID') && isset($this->fields['rowid'])) {
167 $this->fields['rowid']['visible'] = 0;
168 }
169 if (!isModEnabled('multicompany') && isset($this->fields['entity'])) {
170 $this->fields['entity']['enabled'] = 0;
171 }
172
173 // Example to show how to set values of fields definition dynamically
174 /*if ($user->rights->recruitment->recruitmentcandidature->read) {
175 $this->fields['myfield']['visible'] = 1;
176 $this->fields['myfield']['noteditable'] = 0;
177 }*/
178
179 // Unset fields that are disabled
180 foreach ($this->fields as $key => $val) {
181 if (isset($val['enabled']) && empty($val['enabled'])) {
182 unset($this->fields[$key]);
183 }
184 }
185
186 // Translate some data of arrayofkeyval
187 if (is_object($langs)) {
188 foreach ($this->fields as $key => $val) {
189 if (!empty($val['arrayofkeyval']) && is_array($val['arrayofkeyval'])) {
190 foreach ($val['arrayofkeyval'] as $key2 => $val2) {
191 $this->fields[$key]['arrayofkeyval'][$key2] = $langs->trans($val2);
192 }
193 }
194 }
195 }
196 }
197
205 public function create(User $user, $notrigger = 0)
206 {
207 return $this->createCommon($user, $notrigger);
208 }
209
217 public function createFromClone(User $user, $fromid)
218 {
219 global $langs, $extrafields;
220 $error = 0;
221
222 dol_syslog(__METHOD__, LOG_DEBUG);
223
224 $object = new self($this->db);
225
226 $this->db->begin();
227
228 // Load source object
229 $result = $object->fetchCommon($fromid);
230 if ($result > 0 && !empty($object->table_element_line)) {
231 $object->fetchLines();
232 }
233
234 // get lines so they will be clone
235 //foreach($this->lines as $line)
236 // $line->fetch_optionals();
237
238 // Reset some properties
239 unset($object->id);
240 unset($object->fk_user_creat);
241 unset($object->import_key);
242
243 // Clear fields
244 if (property_exists($object, 'ref')) {
245 $object->ref = empty($this->fields['ref']['default']) ? "Copy_Of_".$object->ref : $this->fields['ref']['default'];
246 }
247 if (property_exists($object, 'label')) {
248 $object->label = empty($this->fields['label']['default']) ? $langs->trans("CopyOf")." ".$object->label : $this->fields['label']['default'];
249 }
250 if (property_exists($object, 'status')) {
251 $object->status = self::STATUS_DRAFT;
252 }
253 if (property_exists($object, 'date_creation')) {
254 $object->date_creation = dol_now();
255 }
256 if (property_exists($object, 'date_modification')) {
257 $object->date_modification = null;
258 }
259
260 // ...
261 // Clear extrafields that are unique
262 if (is_array($object->array_options) && count($object->array_options) > 0) {
263 $extrafields->fetch_name_optionals_label($this->table_element);
264 foreach ($object->array_options as $key => $option) {
265 $shortkey = preg_replace('/options_/', '', $key);
266 if (!empty($extrafields->attributes[$this->table_element]['unique'][$shortkey])) {
267 //var_dump($key);
268 //var_dump($clonedObj->array_options[$key]); exit;
269 unset($object->array_options[$key]);
270 }
271 }
272 }
273
274 // Create clone
275 $object->context['createfromclone'] = 'createfromclone';
276 $result = $object->createCommon($user);
277 if ($result < 0) {
278 $error++;
279 $this->error = $object->error;
280 $this->errors = $object->errors;
281 }
282
283 if (!$error) {
284 // copy internal contacts
285 if ($this->copy_linked_contact($object, 'internal') < 0) {
286 $error++;
287 }
288 }
289
290 if (!$error) {
291 // copy external contacts if same company
292 if (property_exists($this, 'socid') && $this->socid == $object->socid) {
293 if ($this->copy_linked_contact($object, 'external') < 0) {
294 $error++;
295 }
296 }
297 }
298
299 unset($object->context['createfromclone']);
300
301 // End
302 if (!$error) {
303 $this->db->commit();
304 return $object;
305 } else {
306 $this->db->rollback();
307 return -1;
308 }
309 }
310
319 public function fetch($id, $ref = null, $email_msgid = '')
320 {
321 $morewhere = '';
322 if ($email_msgid) {
323 $morewhere = " AND email_msgid = '".$this->db->escape($email_msgid)."'";
324 }
325 $result = $this->fetchCommon($id, $ref, $morewhere);
326 if ($result > 0 && !empty($this->table_element_line)) {
327 $this->fetchLines();
328 }
329 return $result;
330 }
331
337 public function fetchLines()
338 {
339 $this->lines = array();
340
341 $result = $this->fetchLinesCommon();
342 return $result;
343 }
344
345
358 public function fetchAll($sortorder = '', $sortfield = '', $limit = 0, $offset = 0, $filter = '', $filtermode = 'AND')
359 {
360 dol_syslog(__METHOD__, LOG_DEBUG);
361
362 $records = array();
363
364 $sql = 'SELECT ';
365 $sql .= $this->getFieldList();
366 $sql .= ' FROM '.MAIN_DB_PREFIX.$this->table_element.' as t';
367 if (isset($this->ismultientitymanaged) && $this->ismultientitymanaged == 1) {
368 $sql .= ' WHERE t.entity IN ('.getEntity($this->element).')';
369 } else {
370 $sql .= ' WHERE 1 = 1';
371 }
372
373 // Manage filter
374 $errormessage = '';
375 $sql .= forgeSQLFromUniversalSearchCriteria($filter, $errormessage);
376 if ($errormessage) {
377 $this->errors[] = $errormessage;
378 dol_syslog(__METHOD__.' '.implode(',', $this->errors), LOG_ERR);
379 return -1;
380 }
381
382 if (!empty($sortfield)) {
383 $sql .= $this->db->order($sortfield, $sortorder);
384 }
385 if (!empty($limit)) {
386 $sql .= $this->db->plimit($limit, $offset);
387 }
388
389 $resql = $this->db->query($sql);
390 if ($resql) {
391 $num = $this->db->num_rows($resql);
392 $i = 0;
393 while ($i < ($limit ? min($limit, $num) : $num)) {
394 $obj = $this->db->fetch_object($resql);
395
396 $record = new self($this->db);
397 $record->setVarsFromFetchObj($obj);
398
399 $records[$record->id] = $record;
400
401 $i++;
402 }
403 $this->db->free($resql);
404
405 return $records;
406 } else {
407 $this->errors[] = 'Error '.$this->db->lasterror();
408 dol_syslog(__METHOD__.' '.implode(',', $this->errors), LOG_ERR);
409
410 return -1;
411 }
412 }
413
421 public function update(User $user, $notrigger = 0)
422 {
423 return $this->updateCommon($user, $notrigger);
424 }
425
433 public function delete(User $user, $notrigger = 0)
434 {
435 return $this->deleteCommon($user, $notrigger);
436 //return $this->deleteCommon($user, $notrigger, 1);
437 }
438
447 public function deleteLine(User $user, $idline, $notrigger = 0)
448 {
449 if ($this->status < 0) {
450 $this->error = 'ErrorDeleteLineNotAllowedByObjectStatus';
451 return -2;
452 }
453
454 return $this->deleteLineCommon($user, $idline, $notrigger);
455 }
456
457
465 public function validate($user, $notrigger = 0)
466 {
467 global $conf, $langs;
468
469 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
470
471 $error = 0;
472
473 // Protection
474 if ($this->status == self::STATUS_VALIDATED) {
475 dol_syslog(get_class($this)."::validate action abandoned: already validated", LOG_WARNING);
476 return 0;
477 }
478
479 /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->recruitmentcandidature->write))
480 || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->recruitmentcandidature->recruitmentcandidature_advance->validate))))
481 {
482 $this->error='NotEnoughPermissions';
483 dol_syslog(get_class($this)."::valid ".$this->error, LOG_ERR);
484 return -1;
485 }*/
486
487 $now = dol_now();
488
489 $this->db->begin();
490
491 // Define new ref
492 if (!$error && (preg_match('/^[\‍(]?PROV/i', $this->ref) || empty($this->ref))) { // empty should not happened, but when it occurs, the test save life
493 $num = $this->getNextNumRef();
494 } else {
495 $num = $this->ref;
496 }
497 $this->newref = $num;
498
499 if (!empty($num)) {
500 // Validate
501 $sql = "UPDATE ".MAIN_DB_PREFIX.$this->table_element;
502 $sql .= " SET ref = '".$this->db->escape($num)."',";
503 $sql .= " status = ".self::STATUS_VALIDATED;
504 if (!empty($this->fields['date_validation'])) {
505 $sql .= ", date_validation = '".$this->db->idate($now)."',";
506 }
507 if (!empty($this->fields['fk_user_valid'])) {
508 $sql .= ", fk_user_valid = ".$user->id;
509 }
510 $sql .= " WHERE rowid = ".((int) $this->id);
511
512 dol_syslog(get_class($this)."::validate()", LOG_DEBUG);
513 $resql = $this->db->query($sql);
514 if (!$resql) {
515 dol_print_error($this->db);
516 $this->error = $this->db->lasterror();
517 $error++;
518 }
519
520 if (!$error && !$notrigger) {
521 // Call trigger
522 $result = $this->call_trigger('RECRUITMENTCANDIDATURE_VALIDATE', $user);
523 if ($result < 0) {
524 $error++;
525 }
526 // End call triggers
527 }
528 }
529
530 if (!$error) {
531 $this->oldref = $this->ref;
532
533 // Rename directory if dir was a temporary ref
534 if (preg_match('/^[\‍(]?PROV/i', $this->ref)) {
535 // Now we rename also files into index
536 $sql = 'UPDATE '.MAIN_DB_PREFIX."ecm_files set filename = CONCAT('".$this->db->escape($this->newref)."', SUBSTR(filename, ".(strlen($this->ref) + 1).")), filepath = 'recruitmentcandidature/".$this->db->escape($this->newref)."'";
537 $sql .= " WHERE filename LIKE '".$this->db->escape($this->ref)."%' AND filepath = 'recruitmentcandidature/".$this->db->escape($this->ref)."' and entity = ".$conf->entity;
538 $resql = $this->db->query($sql);
539 if (!$resql) {
540 $error++;
541 $this->error = $this->db->lasterror();
542 }
543 $sql = 'UPDATE '.MAIN_DB_PREFIX."ecm_files set filepath = 'recruitmentcandidature/".$this->db->escape($this->newref)."'";
544 $sql .= " WHERE filepath = 'recruitmentcandidature/".$this->db->escape($this->ref)."' and entity = ".$conf->entity;
545 $resql = $this->db->query($sql);
546 if (!$resql) {
547 $error++;
548 $this->error = $this->db->lasterror();
549 }
550
551 // We rename directory ($this->ref = old ref, $num = new ref) in order not to lose the attachments
552 $oldref = dol_sanitizeFileName($this->ref);
553 $newref = dol_sanitizeFileName($num);
554 $dirsource = $conf->recruitment->dir_output.'/recruitmentcandidature/'.$oldref;
555 $dirdest = $conf->recruitment->dir_output.'/recruitmentcandidature/'.$newref;
556 if (!$error && file_exists($dirsource)) {
557 dol_syslog(get_class($this)."::validate() rename dir ".$dirsource." into ".$dirdest);
558
559 if (@rename($dirsource, $dirdest)) {
560 dol_syslog("Rename ok");
561 // Rename docs starting with $oldref with $newref
562 $listoffiles = dol_dir_list($conf->recruitment->dir_output.'/recruitmentcandidature/'.$newref, 'files', 1, '^'.preg_quote($oldref, '/'));
563 foreach ($listoffiles as $fileentry) {
564 $dirsource = $fileentry['name'];
565 $dirdest = preg_replace('/^'.preg_quote($oldref, '/').'/', $newref, $dirsource);
566 $dirsource = $fileentry['path'].'/'.$dirsource;
567 $dirdest = $fileentry['path'].'/'.$dirdest;
568 @rename($dirsource, $dirdest);
569 }
570 }
571 }
572 }
573 }
574
575 // Set new ref and current status
576 if (!$error) {
577 $this->ref = $num;
578 $this->status = self::STATUS_VALIDATED;
579 }
580
581 if (!$error) {
582 $this->db->commit();
583 return 1;
584 } else {
585 $this->db->rollback();
586 return -1;
587 }
588 }
589
590
598 public function setDraft($user, $notrigger = 0)
599 {
600 // Protection
601 if ($this->status <= self::STATUS_DRAFT) {
602 return 0;
603 }
604
605 /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->write))
606 || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->recruitment_advance->validate))))
607 {
608 $this->error='Permission denied';
609 return -1;
610 }*/
611
612 return $this->setStatusCommon($user, self::STATUS_DRAFT, $notrigger, 'RECRUITMENTCANDIDATURE_UNVALIDATE');
613 }
614
622 public function cancel($user, $notrigger = 0)
623 {
624 // Protection
625 if ($this->status != self::STATUS_VALIDATED) {
626 return 0;
627 }
628
629 /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->write))
630 || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->recruitment_advance->validate))))
631 {
632 $this->error='Permission denied';
633 return -1;
634 }*/
635
636 return $this->setStatusCommon($user, self::STATUS_CANCELED, $notrigger, 'RECRUITMENTCANDIDATURE_CLOSE');
637 }
638
646 public function reopen($user, $notrigger = 0)
647 {
648 // Protection
649 if ($this->status != self::STATUS_REFUSED && $this->status != self::STATUS_CANCELED && $this->status != self::STATUS_CONTRACT_REFUSED) {
650 return 0;
651 }
652
653 /*if (! ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->write))
654 || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->recruitment->recruitment_advance->validate))))
655 {
656 $this->error='Permission denied';
657 return -1;
658 }*/
659
660 return $this->setStatusCommon($user, self::STATUS_VALIDATED, $notrigger, 'RECRUITMENTCANDIDATURE_REOPEN');
661 }
662
672 public function getFullName($langs, $option = 0, $nameorder = -1, $maxlen = 0)
673 {
674 $lastname = $this->lastname;
675 $firstname = $this->firstname;
676 if (empty($lastname)) {
677 $lastname = (isset($this->lastname) ? $this->lastname : (isset($this->name) ? $this->name : (isset($this->nom) ? $this->nom : (isset($this->societe) ? $this->societe : (isset($this->company) ? $this->company : '')))));
678 }
679
680 $ret = '';
681
682 $ret .= dolGetFirstLastname($firstname, $lastname, $nameorder);
683
684 return dol_trunc($ret, $maxlen);
685 }
686
697 public function getNomUrl($withpicto = 0, $option = '', $notooltip = 0, $morecss = '', $save_lastsearch_value = -1)
698 {
699 global $conf, $langs, $hookmanager;
700
701 if (!empty($conf->dol_no_mouse_hover)) {
702 $notooltip = 1; // Force disable tooltips
703 }
704
705 $result = '';
706
707 $label = img_picto('', $this->picto).' <u class="paddingrightonly">'.$langs->trans("RecruitmentCandidature").'</u>';
708 if (isset($this->status)) {
709 $label .= ' '.$this->getLibStatut(5);
710 }
711 $label .= '<br>';
712 $label .= '<b>'.$langs->trans('Ref').':</b> '.$this->ref;
713 $label .= '<br><b>'.$langs->trans('Email').':</b> '.$this->email;
714 $label .= '<br><b>'.$langs->trans('Name').':</b> '.$this->getFullName($langs);
715
716 $url = dol_buildpath('/recruitment/recruitmentcandidature_card.php', 1).'?id='.$this->id;
717
718 if ($option != 'nolink') {
719 // Add param to save lastsearch_values or not
720 $add_save_lastsearch_values = ($save_lastsearch_value == 1 ? 1 : 0);
721 if ($save_lastsearch_value == -1 && isset($_SERVER["PHP_SELF"]) && preg_match('/list\.php/', $_SERVER["PHP_SELF"])) {
722 $add_save_lastsearch_values = 1;
723 }
724 if ($add_save_lastsearch_values) {
725 $url .= '&save_lastsearch_values=1';
726 }
727 }
728
729 $linkclose = '';
730 if (empty($notooltip)) {
731 if (getDolGlobalString('MAIN_OPTIMIZEFORTEXTBROWSER')) {
732 $label = $langs->trans("ShowRecruitmentCandidature");
733 $linkclose .= ' alt="'.dol_escape_htmltag($label, 1).'"';
734 }
735 $linkclose .= ' title="'.dol_escape_htmltag($label, 1).'"';
736 $linkclose .= ' class="classfortooltip'.($morecss ? ' '.$morecss : '').'"';
737 } else {
738 $linkclose = ($morecss ? ' class="'.$morecss.'"' : '');
739 }
740
741 $linkstart = '<a href="'.$url.'"';
742 $linkstart .= $linkclose.'>';
743 $linkend = '</a>';
744
745 $result .= $linkstart;
746
747 if (empty($this->showphoto_on_popup)) {
748 if ($withpicto) {
749 $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);
750 }
751 } else {
752 if ($withpicto) {
753 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
754
755 list($class, $module) = explode('@', $this->picto);
756 $upload_dir = $conf->$module->multidir_output[$conf->entity]."/$class/".dol_sanitizeFileName($this->ref);
757 $filearray = dol_dir_list($upload_dir, "files");
758 $filename = $filearray[0]['name'];
759 if (!empty($filename)) {
760 $pospoint = strpos($filearray[0]['name'], '.');
761
762 $pathtophoto = $class.'/'.$this->ref.'/thumbs/'.substr($filename, 0, $pospoint).'_mini'.substr($filename, $pospoint);
763 if (!getDolGlobalString(strtoupper($module.'_'.$class).'_FORMATLISTPHOTOSASUSERS')) {
764 $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>';
765 } else {
766 $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>';
767 }
768
769 $result .= '</div>';
770 } else {
771 $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);
772 }
773 }
774 }
775
776 if ($withpicto != 2) {
777 $result .= $this->ref;
778 }
779
780 $result .= $linkend;
781 //if ($withpicto != 2) $result.=(($addlabel && $this->label) ? $sep . dol_trunc($this->label, ($addlabel > 1 ? $addlabel : 0)) : '');
782
783 global $action, $hookmanager;
784 $hookmanager->initHooks(array('recruitmentcandidaturedao'));
785 $parameters = array('id' => $this->id, 'getnomurl' => &$result);
786 $reshook = $hookmanager->executeHooks('getNomUrl', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
787 if ($reshook > 0) {
788 $result = $hookmanager->resPrint;
789 } else {
790 $result .= $hookmanager->resPrint;
791 }
792
793 return $result;
794 }
795
802 public function getLibStatut($mode = 0)
803 {
804 return $this->LibStatut($this->status, $mode);
805 }
806
807 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
815 public function LibStatut($status, $mode = 0)
816 {
817 // phpcs:enable
818 if (empty($this->labelStatus) || empty($this->labelStatusShort)) {
819 global $langs;
820 //$langs->load("recruitment@recruitment");
821 $this->labelStatus[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
822 $this->labelStatus[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Received').' ('.$langs->transnoentitiesnoconv("InterviewToDo").')';
823 $this->labelStatus[self::STATUS_CONTRACT_PROPOSED] = $langs->transnoentitiesnoconv('ContractProposed');
824 $this->labelStatus[self::STATUS_CONTRACT_SIGNED] = $langs->transnoentitiesnoconv('ContractSigned');
825 $this->labelStatus[self::STATUS_CONTRACT_REFUSED] = $langs->transnoentitiesnoconv('ContractRefused');
826 $this->labelStatus[self::STATUS_REFUSED] = $langs->transnoentitiesnoconv('Refused');
827 $this->labelStatus[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('Canceled');
828 $this->labelStatusShort[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
829 $this->labelStatusShort[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Received');
830 $this->labelStatusShort[self::STATUS_CONTRACT_PROPOSED] = $langs->transnoentitiesnoconv('ContractProposed');
831 $this->labelStatusShort[self::STATUS_CONTRACT_SIGNED] = $langs->transnoentitiesnoconv('ContractSigned');
832 $this->labelStatusShort[self::STATUS_CONTRACT_REFUSED] = $langs->transnoentitiesnoconv('ContractRefused');
833 $this->labelStatusShort[self::STATUS_REFUSED] = $langs->transnoentitiesnoconv('Refused');
834 $this->labelStatusShort[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('Canceled');
835 }
836
837 $statusType = 'status'.$status;
838 //if ($status == self::STATUS_VALIDATED) $statusType = 'status1';
839 if ($status == self::STATUS_CANCELED) {
840 $statusType = 'status9';
841 }
842 if ($status == self::STATUS_CONTRACT_PROPOSED) {
843 $statusType = 'status4';
844 }
845 if ($status == self::STATUS_CONTRACT_SIGNED) {
846 $statusType = 'status6';
847 }
848 if ($status == self::STATUS_REFUSED) {
849 $statusType = 'status10';
850 }
851
852 return dolGetStatus($this->labelStatus[$status], $this->labelStatusShort[$status], '', $statusType, $mode);
853 }
854
861 public function info($id)
862 {
863 $sql = 'SELECT rowid, date_creation as datec, tms as datem,';
864 $sql .= ' fk_user_creat, fk_user_modif';
865 $sql .= ' FROM '.MAIN_DB_PREFIX.$this->table_element.' as t';
866 $sql .= ' WHERE t.rowid = '.((int) $id);
867 $result = $this->db->query($sql);
868 if ($result) {
869 if ($this->db->num_rows($result)) {
870 $obj = $this->db->fetch_object($result);
871
872 $this->id = $obj->rowid;
873
874 $this->user_creation_id = $obj->fk_user_creat;
875 $this->user_modification_id = $obj->fk_user_modif;
876 $this->date_creation = $this->db->jdate($obj->datec);
877 $this->date_modification = empty($obj->datem) ? '' : $this->db->jdate($obj->datem);
878 }
879
880 $this->db->free($result);
881 } else {
882 dol_print_error($this->db);
883 }
884 }
885
892 public function initAsSpecimen()
893 {
894 return $this->initAsSpecimenCommon();
895 }
896
902 public function getLinesArray()
903 {
904 $this->lines = array();
905
906 $objectline = new RecruitmentCandidatureLine($this->db);
907 $result = $objectline->fetchAll('ASC', 'position', 0, 0, '(fk_recruitmentcandidature:=:'.((int) $this->id).')');
908
909 if (is_numeric($result)) {
910 $this->error = $objectline->error;
911 $this->errors = $objectline->errors;
912 return $result;
913 } else {
914 $this->lines = $result;
915 return $this->lines;
916 }
917 }
918
924 public function getNextNumRef()
925 {
926 global $langs, $conf;
927 $langs->load("recruitment@recruitment");
928
929 if (!getDolGlobalString('RECRUITMENT_RECRUITMENTCANDIDATURE_ADDON')) {
930 $conf->global->RECRUITMENT_RECRUITMENTCANDIDATURE_ADDON = 'mod_recruitmentcandidature_standard';
931 }
932
933 if (getDolGlobalString('RECRUITMENT_RECRUITMENTCANDIDATURE_ADDON')) {
934 $mybool = false;
935
936 $file = getDolGlobalString('RECRUITMENT_RECRUITMENTCANDIDATURE_ADDON') . ".php";
937 $classname = getDolGlobalString('RECRUITMENT_RECRUITMENTCANDIDATURE_ADDON');
938
939 // Include file with class
940 $dirmodels = array_merge(array('/'), (array) $conf->modules_parts['models']);
941 foreach ($dirmodels as $reldir) {
942 $dir = dol_buildpath($reldir."core/modules/recruitment/");
943
944 // Load file with numbering class (if found)
945 $mybool = ((bool) @include_once $dir.$file) || $mybool;
946 }
947
948 if ($mybool === false) {
949 dol_print_error(null, "Failed to include file ".$file);
950 return '';
951 }
952
953 if (class_exists($classname)) {
954 $obj = new $classname();
955 $numref = $obj->getNextValue($this);
956
957 if ($numref != '' && $numref != '-1') {
958 return $numref;
959 } else {
960 $this->error = $obj->error;
961 //dol_print_error($this->db,get_class($this)."::getNextNumRef ".$obj->error);
962 return "";
963 }
964 } else {
965 print $langs->trans("Error")." ".$langs->trans("ClassNotFound").' '.$classname;
966 return "";
967 }
968 } else {
969 print $langs->trans("ErrorNumberingModuleNotSetup", $this->element);
970 return "";
971 }
972 }
973
985 public function generateDocument($modele, $outputlangs, $hidedetails = 0, $hidedesc = 0, $hideref = 0, $moreparams = null)
986 {
987 global $conf, $langs;
988
989 $result = 0;
990 $includedocgeneration = 0;
991
992 $langs->load("recruitment@recruitment");
993
994 if (!dol_strlen($modele)) {
995 if (getDolGlobalString('RECRUITMENTCANDIDATURE_ADDON_PDF')) {
996 $modele = getDolGlobalString('RECRUITMENTCANDIDATURE_ADDON_PDF');
997 } else {
998 $modele = ''; // No default value. For job application, we allow to disable all PDF generation
999 }
1000 }
1001
1002 $modelpath = "core/modules/recruitment/doc/";
1003
1004 if ($includedocgeneration && !empty($modele)) {
1005 $result = $this->commonGenerateDocument($modelpath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams);
1006 }
1007
1008 return $result;
1009 }
1010
1018 public function doScheduledJob()
1019 {
1020 global $conf, $langs;
1021
1022 //$conf->global->SYSLOG_FILE = 'DOL_DATA_ROOT/dolibarr_mydedicatedlofile.log';
1023
1024 $error = 0;
1025 $this->output = '';
1026 $this->error = '';
1027
1028 dol_syslog(__METHOD__, LOG_DEBUG);
1029
1030 $now = dol_now();
1031
1032 $this->db->begin();
1033
1034 // ...
1035
1036 $this->db->commit();
1037
1038 return $error;
1039 }
1040
1048 public function getKanbanView($option = '', $arraydata = null)
1049 {
1050 global $mysoc;
1051
1052 $selected = (empty($arraydata['selected']) ? 0 : $arraydata['selected']);
1053
1054 $return = '<div class="box-flex-item box-flex-grow-zero">';
1055 $return .= '<div class="info-box info-box-sm">';
1056 $return .= '<span class="info-box-icon bg-infobox-action">';
1057 $return .= img_picto('', $this->picto);
1058 $return .= '</span>';
1059 $return .= '<div class="info-box-content">';
1060 $return .= '<span class="info-box-ref inline-block tdoverflowmax150 valignmiddle">'.(method_exists($this, 'getNomUrl') ? $this->getNomUrl(1) : $this->ref).'</span>';
1061 if ($selected >= 0) {
1062 $return .= '<input id="cb'.$this->id.'" class="flat checkforselect fright" type="checkbox" name="toselect[]" value="'.$this->id.'"'.($selected ? ' checked="checked"' : '').'>';
1063 }
1064 if (property_exists($this, 'fk_recruitmentjobposition')) {
1065 $return .= '<br>';
1066 //$return .= '<span class="opacitymedium">';
1067 //$return .= $langs->trans('Job').'</span> : ';
1068 $return .= '<div class="info-box-label tdoverflowmax150">';
1069 $tmpjob = new RecruitmentJobPosition($this->db);
1070 $tmpjob->fetch($this->fk_recruitmentjobposition);
1071 //$return .= $this->fk_recruitmentjobposition;
1072 $return .= dolPrintHTML($tmpjob->label);
1073 $return .= '</div>';
1074 }
1075 if (property_exists($this, 'phone') && $this->phone) {
1076 $return .= '<div class="info-box-label small">'.dol_print_phone($this->phone, $mysoc->country_code, 0, 0, 'AC_TEL', '&nbsp;', 'phone').'</div>';
1077 }
1078 if (property_exists($this, 'email') && $this->email) {
1079 $return .= '<div class="info-box-label small">'.dol_print_email($this->email, 0, 0, 1, 64, 1, 1).'</div>';
1080 }
1081 if (method_exists($this, 'getLibStatut')) {
1082 $return .= '<div class="info-box-status">'.$this->getLibStatut(3).'</div>';
1083 }
1084 $return .= '</div>';
1085 $return .= '</div>';
1086 $return .= '</div>';
1087 return $return;
1088 }
1089}
1090
1091
1092require_once DOL_DOCUMENT_ROOT.'/core/class/commonobjectline.class.php';
1093
1098{
1099 // To complete with content of an object RecruitmentCandidatureLine
1100 // We should have a field rowid, fk_recruitmentcandidature and position
1101
1107 public function __construct(DoliDB $db)
1108 {
1109 $this->db = $db;
1110 }
1111}
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:58
print $langs trans("AuditedSecurityEvents").'</strong >< span class="opacitymedium"></span >< br > status
Or an array listing all the potential status of the object: array: int of the status => translated la...
Definition security.php:626
$object ref
Definition info.php:79
Parent class of all other business classes (invoices, contracts, proposals, orders,...
deleteLineCommon(User $user, $idline, $notrigger=0)
Delete a line of object in database.
commonGenerateDocument($modelspath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams=null)
Common function for all objects extending CommonObject for generating documents.
createCommon(User $user, $notrigger=0)
Create object in the database.
getFieldList($alias='', $excludefields=array())
Function to concat keys of fields.
updateCommon(User $user, $notrigger=0)
Update object into 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.
fetchLinesCommon($morewhere='', $noextrafields=0)
Load object in memory from the database.
fetchCommon($id, $ref=null, $morewhere='', $noextrafields=0)
Load object in memory from the database.
deleteCommon(User $user, $notrigger=0, $forcechilddeletion=0)
Delete object in 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 RecruitmentCandidature.
getLinesArray()
Create an array of lines.
createFromClone(User $user, $fromid)
Clone an object into another one.
cancel($user, $notrigger=0)
Set cancel status.
doScheduledJob()
Action executed by scheduler CAN BE A CRON TASK.
getKanbanView($option='', $arraydata=null)
Return clicable link of object (with eventually picto)
getNomUrl($withpicto=0, $option='', $notooltip=0, $morecss='', $save_lastsearch_value=-1)
Return a link to the object card (with optionally the picto)
getNextNumRef()
Returns the reference to the following non used object depending on the active numbering module.
reopen($user, $notrigger=0)
Set back to validated status.
initAsSpecimen()
Initialise object with example values Id must be 0 if object instance is a specimen.
getLibStatut($mode=0)
Return label of the status.
fetch($id, $ref=null, $email_msgid='')
Load object in memory from the database.
fetchLines()
Load object lines in memory from the database.
generateDocument($modele, $outputlangs, $hidedetails=0, $hidedesc=0, $hideref=0, $moreparams=null)
Create a document onto disk according to template module.
update(User $user, $notrigger=0)
Update object into database.
validate($user, $notrigger=0)
Validate object.
deleteLine(User $user, $idline, $notrigger=0)
Delete a line of object in database.
LibStatut($status, $mode=0)
Return the status.
fetchAll($sortorder='', $sortfield='', $limit=0, $offset=0, $filter='', $filtermode='AND')
Load list of objects in memory from the database.
getFullName($langs, $option=0, $nameorder=-1, $maxlen=0)
Return full name ('name+' '+lastname)
setDraft($user, $notrigger=0)
Set draft status.
create(User $user, $notrigger=0)
Create object into database.
info($id)
Load the info information in the object.
Class RecruitmentCandidatureLine.
Class for RecruitmentJobPosition.
Class to manage Dolibarr users.
dol_dir_list($utf8_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:63
img_object($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0)
Show a picto called object_picto (generic function)
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
dolPrintHTML($s, $allowiframe=0)
Return a string (that can be on several lines) ready to be output on a HTML page.
dol_strlen($string, $stringencoding='UTF-8')
Make a strlen call.
forgeSQLFromUniversalSearchCriteria($filter, &$errorstr='', $noand=0, $nopar=0, $noerror=0)
forgeSQLFromUniversalSearchCriteria
dol_now($mode='auto')
Return date for now.
dolGetFirstLastname($firstname, $lastname, $nameorder=-1)
Return firstname and lastname in correct order.
dol_buildpath($path, $type=0, $returnemptyifnotfound=0)
Return path of url or filesystem.
dol_sanitizeFileName($str, $newstr='_', $unaccent=1)
Clean a string to use it as a file name.
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
dol_trunc($string, $size=40, $trunc='right', $stringencoding='UTF-8', $nodot=0, $display=0)
Truncate a string to a particular length adding '…' if string larger than length.
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.
$conf db name
Only used if Module[ID]Name translation string is not found.
Definition repair.php:142