dolibarr 20.0.2
holiday.class.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2011 Dimitri Mouillard <dmouillard@teclib.com>
3 * Copyright (C) 2012-2014 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2012-2016 Regis Houssin <regis.houssin@inodbox.com>
5 * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
6 * Copyright (C) 2016 Juanjo Menent <jmenent@2byte.es>
7 * Copyright (C) 2018-2024 Frédéric France <frederic.france@free.fr>
8 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 3 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program. If not, see <https://www.gnu.org/licenses/>.
22 */
23
29require_once DOL_DOCUMENT_ROOT.'/core/class/commonobject.class.php';
30
31
35class Holiday extends CommonObject
36{
40 public $element = 'holiday';
41
45 public $table_element = 'holiday';
46
50 public $fk_element = 'fk_holiday';
51
55 public $picto = 'holiday';
56
60 public $fk_user;
61
62 public $date_create = '';
63
67 public $description;
68
72 public $date_debut = '';
73
77 public $date_fin = '';
78
82 public $date_debut_gmt = '';
83
87 public $date_fin_gmt = '';
88
92 public $halfday = '';
93
98 public $statut = 0;
99
103 public $fk_validator;
104
108 public $date_valid = 0;
109
113 public $fk_user_valid;
114
118 public $date_approval;
119
123 public $fk_user_approve;
124
128 public $date_refuse = 0;
129
133 public $fk_user_refuse;
134
138 public $date_cancel = 0;
139
143 public $fk_user_cancel;
144
148 public $fk_user_create;
149
153 public $detail_refuse = '';
154
158 public $fk_type;
159
160 public $holiday = array();
161 public $events = array();
162 public $logs = array();
163
164 public $optName = '';
165 public $optValue = '';
166 public $optRowid = '';
167
171 const STATUS_DRAFT = 1;
187 const STATUS_REFUSED = 5;
188
189
195 public function __construct($db)
196 {
197 $this->db = $db;
198
199 $this->ismultientitymanaged = 0;
200 }
201
202
210 public function getNextNumRef($objsoc)
211 {
212 global $langs, $conf;
213 $langs->load("order");
214
215 if (!getDolGlobalString('HOLIDAY_ADDON')) {
216 $conf->global->HOLIDAY_ADDON = 'mod_holiday_madonna';
217 }
218
219 if (getDolGlobalString('HOLIDAY_ADDON')) {
220 $mybool = false;
221
222 $file = getDolGlobalString('HOLIDAY_ADDON') . ".php";
223 $classname = getDolGlobalString('HOLIDAY_ADDON');
224
225 // Include file with class
226 $dirmodels = array_merge(array('/'), (array) $conf->modules_parts['models']);
227 foreach ($dirmodels as $reldir) {
228 $dir = dol_buildpath($reldir."core/modules/holiday/");
229
230 // Load file with numbering class (if found)
231 $mybool = ((bool) @include_once $dir.$file) || $mybool;
232 }
233
234 if ($mybool === false) {
235 dol_print_error(null, "Failed to include file ".$file);
236 return '';
237 }
238
239 $obj = new $classname();
240 $numref = $obj->getNextValue($objsoc, $this);
241
242 if ($numref != "") {
243 return $numref;
244 } else {
245 $this->error = $obj->error;
246 //dol_print_error($this->db,get_class($this)."::getNextNumRef ".$obj->error);
247 return "";
248 }
249 } else {
250 print $langs->trans("Error")." ".$langs->trans("Error_HOLIDAY_ADDON_NotDefined");
251 return "";
252 }
253 }
254
260 public function updateBalance()
261 {
262 $this->db->begin();
263
264 // Update sold of vocations
265 $result = $this->updateSoldeCP();
266
267 // Check nb of users into table llx_holiday_users and update with empty lines
268 //if ($result > 0) $result = $this->verifNbUsers($this->countActiveUsersWithoutCP(), $this->getConfCP('nbUser'));
269
270 if ($result >= 0) {
271 $this->db->commit();
272 return 0; // for cronjob use (0 is OK, any other value is an error code)
273 } else {
274 $this->db->rollback();
275 return -1;
276 }
277 }
278
286 public function create($user, $notrigger = 0)
287 {
288 global $conf;
289 $error = 0;
290
291 $now = dol_now();
292
293 // Check parameters
294 if (empty($this->fk_user) || !is_numeric($this->fk_user) || $this->fk_user < 0) {
295 $this->error = "ErrorBadParameterFkUser";
296 return -1;
297 }
298 if (empty($this->fk_validator) || !is_numeric($this->fk_validator) || $this->fk_validator < 0) {
299 $this->error = "ErrorBadParameterFkValidator";
300 return -1;
301 }
302 if (empty($this->fk_type) || !is_numeric($this->fk_type) || $this->fk_type < 0) {
303 $this->error = "ErrorBadParameterFkType";
304 return -1;
305 }
306
307 // Insert request
308 $sql = "INSERT INTO ".MAIN_DB_PREFIX."holiday(";
309 $sql .= "ref,";
310 $sql .= "fk_user,";
311 $sql .= "date_create,";
312 $sql .= "description,";
313 $sql .= "date_debut,";
314 $sql .= "date_fin,";
315 $sql .= "halfday,";
316 $sql .= "statut,";
317 $sql .= "fk_validator,";
318 $sql .= "fk_type,";
319 $sql .= "fk_user_create,";
320 $sql .= "entity";
321 $sql .= ") VALUES (";
322 $sql .= "'(PROV)',";
323 $sql .= " ".((int) $this->fk_user).",";
324 $sql .= " '".$this->db->idate($now)."',";
325 $sql .= " '".$this->db->escape($this->description)."',";
326 $sql .= " '".$this->db->idate($this->date_debut)."',";
327 $sql .= " '".$this->db->idate($this->date_fin)."',";
328 $sql .= " ".((int) $this->halfday).",";
329 $sql .= " '1',";
330 $sql .= " ".((int) $this->fk_validator).",";
331 $sql .= " ".((int) $this->fk_type).",";
332 $sql .= " ".((int) $user->id).",";
333 $sql .= " ".((int) $conf->entity);
334 $sql .= ")";
335
336 $this->db->begin();
337
338 dol_syslog(get_class($this)."::create", LOG_DEBUG);
339 $resql = $this->db->query($sql);
340 if (!$resql) {
341 $error++;
342 $this->errors[] = "Error ".$this->db->lasterror();
343 }
344
345 if (!$error) {
346 $this->id = $this->db->last_insert_id(MAIN_DB_PREFIX."holiday");
347
348 if ($this->id) {
349 // update ref
350 $initialref = '(PROV'.$this->id.')';
351 if (!empty($this->ref)) {
352 $initialref = $this->ref;
353 }
354
355 $sql = 'UPDATE '.MAIN_DB_PREFIX."holiday SET ref='".$this->db->escape($initialref)."' WHERE rowid=".((int) $this->id);
356 if ($this->db->query($sql)) {
357 $this->ref = $initialref;
358
359 if (!$error) {
360 $result = $this->insertExtraFields();
361 if ($result < 0) {
362 $error++;
363 }
364 }
365
366 if (!$error && !$notrigger) {
367 // Call trigger
368 $result = $this->call_trigger('HOLIDAY_CREATE', $user);
369 if ($result < 0) {
370 $error++;
371 }
372 // End call triggers
373 }
374 }
375 }
376 }
377
378 // Commit or rollback
379 if ($error) {
380 foreach ($this->errors as $errmsg) {
381 dol_syslog(get_class($this)."::create ".$errmsg, LOG_ERR);
382 $this->error .= ($this->error ? ', '.$errmsg : $errmsg);
383 }
384 $this->db->rollback();
385 return -1 * $error;
386 } else {
387 $this->db->commit();
388 return $this->id;
389 }
390 }
391
392
400 public function fetch($id, $ref = '')
401 {
402 $sql = "SELECT";
403 $sql .= " cp.rowid,";
404 $sql .= " cp.ref,";
405 $sql .= " cp.fk_user,";
406 $sql .= " cp.date_create,";
407 $sql .= " cp.description,";
408 $sql .= " cp.date_debut,";
409 $sql .= " cp.date_fin,";
410 $sql .= " cp.halfday,";
411 $sql .= " cp.statut as status,";
412 $sql .= " cp.fk_validator,";
413 $sql .= " cp.date_valid,";
414 $sql .= " cp.fk_user_valid,";
415 $sql .= " cp.date_approval,";
416 $sql .= " cp.fk_user_approve,";
417 $sql .= " cp.date_refuse,";
418 $sql .= " cp.fk_user_refuse,";
419 $sql .= " cp.date_cancel,";
420 $sql .= " cp.fk_user_cancel,";
421 $sql .= " cp.detail_refuse,";
422 $sql .= " cp.note_private,";
423 $sql .= " cp.note_public,";
424 $sql .= " cp.fk_user_create,";
425 $sql .= " cp.fk_type,";
426 $sql .= " cp.entity";
427 $sql .= " FROM ".MAIN_DB_PREFIX."holiday as cp";
428 if ($id > 0) {
429 $sql .= " WHERE cp.rowid = ".((int) $id);
430 } else {
431 $sql .= " WHERE cp.ref = '".$this->db->escape($ref)."'";
432 }
433
434 dol_syslog(get_class($this)."::fetch", LOG_DEBUG);
435 $resql = $this->db->query($sql);
436 if ($resql) {
437 if ($this->db->num_rows($resql)) {
438 $obj = $this->db->fetch_object($resql);
439
440 $this->id = $obj->rowid;
441 $this->ref = ($obj->ref ? $obj->ref : $obj->rowid);
442 $this->fk_user = $obj->fk_user;
443 $this->date_create = $this->db->jdate($obj->date_create);
444 $this->description = $obj->description;
445 $this->date_debut = $this->db->jdate($obj->date_debut);
446 $this->date_fin = $this->db->jdate($obj->date_fin);
447 $this->date_debut_gmt = $this->db->jdate($obj->date_debut, 1);
448 $this->date_fin_gmt = $this->db->jdate($obj->date_fin, 1);
449 $this->halfday = $obj->halfday;
450 $this->status = $obj->status;
451 $this->statut = $obj->status; // deprecated
452 $this->fk_validator = $obj->fk_validator;
453 $this->date_valid = $this->db->jdate($obj->date_valid);
454 $this->fk_user_valid = $obj->fk_user_valid;
455 $this->user_validation_id = $obj->fk_user_valid;
456 $this->date_approval = $this->db->jdate($obj->date_approval);
457 $this->fk_user_approve = $obj->fk_user_approve;
458 $this->date_refuse = $this->db->jdate($obj->date_refuse);
459 $this->fk_user_refuse = $obj->fk_user_refuse;
460 $this->date_cancel = $this->db->jdate($obj->date_cancel);
461 $this->fk_user_cancel = $obj->fk_user_cancel;
462 $this->detail_refuse = $obj->detail_refuse;
463 $this->note_private = $obj->note_private;
464 $this->note_public = $obj->note_public;
465 $this->fk_user_create = $obj->fk_user_create;
466 $this->fk_type = $obj->fk_type;
467 $this->entity = $obj->entity;
468
469 $this->fetch_optionals();
470
471 $result = 1;
472 } else {
473 $result = 0;
474 }
475 $this->db->free($resql);
476
477 return $result;
478 } else {
479 $this->error = "Error ".$this->db->lasterror();
480 return -1;
481 }
482 }
483
492 public function fetchByUser($user_id, $order = '', $filter = '')
493 {
494 $sql = "SELECT";
495 $sql .= " cp.rowid,";
496 $sql .= " cp.ref,";
497
498 $sql .= " cp.fk_user,";
499 $sql .= " cp.fk_type,";
500 $sql .= " cp.date_create,";
501 $sql .= " cp.description,";
502 $sql .= " cp.date_debut,";
503 $sql .= " cp.date_fin,";
504 $sql .= " cp.halfday,";
505 $sql .= " cp.statut as status,";
506 $sql .= " cp.fk_validator,";
507 $sql .= " cp.date_valid,";
508 $sql .= " cp.fk_user_valid,";
509 $sql .= " cp.date_approval,";
510 $sql .= " cp.fk_user_approve,";
511 $sql .= " cp.date_refuse,";
512 $sql .= " cp.fk_user_refuse,";
513 $sql .= " cp.date_cancel,";
514 $sql .= " cp.fk_user_cancel,";
515 $sql .= " cp.detail_refuse,";
516
517 $sql .= " uu.lastname as user_lastname,";
518 $sql .= " uu.firstname as user_firstname,";
519 $sql .= " uu.login as user_login,";
520 $sql .= " uu.statut as user_status,";
521 $sql .= " uu.photo as user_photo,";
522
523 $sql .= " ua.lastname as validator_lastname,";
524 $sql .= " ua.firstname as validator_firstname,";
525 $sql .= " ua.login as validator_login,";
526 $sql .= " ua.statut as validator_status,";
527 $sql .= " ua.photo as validator_photo";
528
529 $sql .= " FROM ".MAIN_DB_PREFIX."holiday as cp, ".MAIN_DB_PREFIX."user as uu, ".MAIN_DB_PREFIX."user as ua";
530 $sql .= " WHERE cp.entity IN (".getEntity('holiday').")";
531 $sql .= " AND cp.fk_user = uu.rowid AND cp.fk_validator = ua.rowid"; // Hack pour la recherche sur le tableau
532 $sql .= " AND cp.fk_user IN (".$this->db->sanitize($user_id).")";
533
534 // Selection filter
535 if (!empty($filter)) {
536 $sql .= $filter;
537 }
538
539 // Order of display of the result
540 if (!empty($order)) {
541 $sql .= $order;
542 }
543
544 dol_syslog(get_class($this)."::fetchByUser", LOG_DEBUG);
545 $resql = $this->db->query($sql);
546
547 // If no SQL error
548 if ($resql) {
549 $i = 0;
550 $tab_result = $this->holiday;
551 $num = $this->db->num_rows($resql);
552
553 // If no registration
554 if (!$num) {
555 return 2;
556 }
557
558 // List the records and add them to the table
559 while ($i < $num) {
560 $obj = $this->db->fetch_object($resql);
561
562 $tab_result[$i]['rowid'] = $obj->rowid;
563 $tab_result[$i]['id'] = $obj->rowid;
564 $tab_result[$i]['ref'] = ($obj->ref ? $obj->ref : $obj->rowid);
565
566 $tab_result[$i]['fk_user'] = $obj->fk_user;
567 $tab_result[$i]['fk_type'] = $obj->fk_type;
568 $tab_result[$i]['date_create'] = $this->db->jdate($obj->date_create);
569 $tab_result[$i]['description'] = $obj->description;
570 $tab_result[$i]['date_debut'] = $this->db->jdate($obj->date_debut);
571 $tab_result[$i]['date_fin'] = $this->db->jdate($obj->date_fin);
572 $tab_result[$i]['date_debut_gmt'] = $this->db->jdate($obj->date_debut, 1);
573 $tab_result[$i]['date_fin_gmt'] = $this->db->jdate($obj->date_fin, 1);
574 $tab_result[$i]['halfday'] = $obj->halfday;
575 $tab_result[$i]['statut'] = $obj->status;
576 $tab_result[$i]['status'] = $obj->status;
577 $tab_result[$i]['fk_validator'] = $obj->fk_validator;
578 $tab_result[$i]['date_valid'] = $this->db->jdate($obj->date_valid);
579 $tab_result[$i]['fk_user_valid'] = $obj->fk_user_valid;
580 $tab_result[$i]['date_approval'] = $this->db->jdate($obj->date_approval);
581 $tab_result[$i]['fk_user_approve'] = $obj->fk_user_approve;
582 $tab_result[$i]['date_refuse'] = $this->db->jdate($obj->date_refuse);
583 $tab_result[$i]['fk_user_refuse'] = $obj->fk_user_refuse;
584 $tab_result[$i]['date_cancel'] = $this->db->jdate($obj->date_cancel);
585 $tab_result[$i]['fk_user_cancel'] = $obj->fk_user_cancel;
586 $tab_result[$i]['detail_refuse'] = $obj->detail_refuse;
587
588 $tab_result[$i]['user_firstname'] = $obj->user_firstname;
589 $tab_result[$i]['user_lastname'] = $obj->user_lastname;
590 $tab_result[$i]['user_login'] = $obj->user_login;
591 $tab_result[$i]['user_statut'] = $obj->user_status;
592 $tab_result[$i]['user_status'] = $obj->user_status;
593 $tab_result[$i]['user_photo'] = $obj->user_photo;
594
595 $tab_result[$i]['validator_firstname'] = $obj->validator_firstname;
596 $tab_result[$i]['validator_lastname'] = $obj->validator_lastname;
597 $tab_result[$i]['validator_login'] = $obj->validator_login;
598 $tab_result[$i]['validator_statut'] = $obj->validator_status;
599 $tab_result[$i]['validator_status'] = $obj->validator_status;
600 $tab_result[$i]['validator_photo'] = $obj->validator_photo;
601
602 $i++;
603 }
604
605 // Returns 1 with the filled array
606 $this->holiday = $tab_result;
607 return 1;
608 } else {
609 // SQL Error
610 $this->error = "Error ".$this->db->lasterror();
611 return -1;
612 }
613 }
614
622 public function fetchAll($order, $filter)
623 {
624 $sql = "SELECT";
625 $sql .= " cp.rowid,";
626 $sql .= " cp.ref,";
627 $sql .= " cp.fk_user,";
628 $sql .= " cp.fk_type,";
629 $sql .= " cp.date_create,";
630 $sql .= " cp.tms as date_modification,";
631 $sql .= " cp.description,";
632 $sql .= " cp.date_debut,";
633 $sql .= " cp.date_fin,";
634 $sql .= " cp.halfday,";
635 $sql .= " cp.statut as status,";
636 $sql .= " cp.fk_validator,";
637 $sql .= " cp.date_valid,";
638 $sql .= " cp.fk_user_valid,";
639 $sql .= " cp.date_approval,";
640 $sql .= " cp.fk_user_approve,";
641 $sql .= " cp.date_refuse,";
642 $sql .= " cp.fk_user_refuse,";
643 $sql .= " cp.date_cancel,";
644 $sql .= " cp.fk_user_cancel,";
645 $sql .= " cp.detail_refuse,";
646
647 $sql .= " uu.lastname as user_lastname,";
648 $sql .= " uu.firstname as user_firstname,";
649 $sql .= " uu.login as user_login,";
650 $sql .= " uu.statut as user_status,";
651 $sql .= " uu.photo as user_photo,";
652
653 $sql .= " ua.lastname as validator_lastname,";
654 $sql .= " ua.firstname as validator_firstname,";
655 $sql .= " ua.login as validator_login,";
656 $sql .= " ua.statut as validator_status,";
657 $sql .= " ua.photo as validator_photo";
658
659 $sql .= " FROM ".MAIN_DB_PREFIX."holiday as cp, ".MAIN_DB_PREFIX."user as uu, ".MAIN_DB_PREFIX."user as ua";
660 $sql .= " WHERE cp.entity IN (".getEntity('holiday').")";
661 $sql .= " AND cp.fk_user = uu.rowid AND cp.fk_validator = ua.rowid "; // Hack pour la recherche sur le tableau
662
663 // Selection filtering
664 if (!empty($filter)) {
665 $sql .= $filter;
666 }
667
668 // order of display
669 if (!empty($order)) {
670 $sql .= $order;
671 }
672
673 dol_syslog(get_class($this)."::fetchAll", LOG_DEBUG);
674 $resql = $this->db->query($sql);
675
676 // If no SQL error
677 if ($resql) {
678 $i = 0;
679 $tab_result = $this->holiday;
680 $num = $this->db->num_rows($resql);
681
682 // If no registration
683 if (!$num) {
684 return 2;
685 }
686
687 // List the records and add them to the table
688 while ($i < $num) {
689 $obj = $this->db->fetch_object($resql);
690
691 $tab_result[$i]['rowid'] = $obj->rowid;
692 $tab_result[$i]['id'] = $obj->rowid;
693 $tab_result[$i]['ref'] = ($obj->ref ? $obj->ref : $obj->rowid);
694
695 $tab_result[$i]['fk_user'] = $obj->fk_user;
696 $tab_result[$i]['fk_type'] = $obj->fk_type;
697 $tab_result[$i]['date_create'] = $this->db->jdate($obj->date_create);
698 $tab_result[$i]['date_modification'] = $this->db->jdate($obj->date_modification);
699 $tab_result[$i]['description'] = $obj->description;
700 $tab_result[$i]['date_debut'] = $this->db->jdate($obj->date_debut);
701 $tab_result[$i]['date_fin'] = $this->db->jdate($obj->date_fin);
702 $tab_result[$i]['date_debut_gmt'] = $this->db->jdate($obj->date_debut, 1);
703 $tab_result[$i]['date_fin_gmt'] = $this->db->jdate($obj->date_fin, 1);
704 $tab_result[$i]['halfday'] = $obj->halfday;
705 $tab_result[$i]['statut'] = $obj->status;
706 $tab_result[$i]['status'] = $obj->status;
707 $tab_result[$i]['fk_validator'] = $obj->fk_validator;
708 $tab_result[$i]['date_valid'] = $this->db->jdate($obj->date_valid);
709 $tab_result[$i]['fk_user_valid'] = $obj->fk_user_valid;
710 $tab_result[$i]['date_approval'] = $this->db->jdate($obj->date_approval);
711 $tab_result[$i]['fk_user_approve'] = $obj->fk_user_approve;
712 $tab_result[$i]['date_refuse'] = $obj->date_refuse;
713 $tab_result[$i]['fk_user_refuse'] = $obj->fk_user_refuse;
714 $tab_result[$i]['date_cancel'] = $obj->date_cancel;
715 $tab_result[$i]['fk_user_cancel'] = $obj->fk_user_cancel;
716 $tab_result[$i]['detail_refuse'] = $obj->detail_refuse;
717
718 $tab_result[$i]['user_firstname'] = $obj->user_firstname;
719 $tab_result[$i]['user_lastname'] = $obj->user_lastname;
720 $tab_result[$i]['user_login'] = $obj->user_login;
721 $tab_result[$i]['user_statut'] = $obj->user_status;
722 $tab_result[$i]['user_status'] = $obj->user_status;
723 $tab_result[$i]['user_photo'] = $obj->user_photo;
724
725 $tab_result[$i]['validator_firstname'] = $obj->validator_firstname;
726 $tab_result[$i]['validator_lastname'] = $obj->validator_lastname;
727 $tab_result[$i]['validator_login'] = $obj->validator_login;
728 $tab_result[$i]['validator_statut'] = $obj->validator_status;
729 $tab_result[$i]['validator_status'] = $obj->validator_status;
730 $tab_result[$i]['validator_photo'] = $obj->validator_photo;
731
732 $i++;
733 }
734 // Returns 1 and adds the array to the variable
735 $this->holiday = $tab_result;
736 return 1;
737 } else {
738 // SQL Error
739 $this->error = "Error ".$this->db->lasterror();
740 return -1;
741 }
742 }
743
744
752 public function validate($user = null, $notrigger = 0)
753 {
754 global $conf, $langs;
755 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
756 $error = 0;
757
758 $checkBalance = getDictionaryValue('c_holiday_types', 'block_if_negative', $this->fk_type, true);
759
760 if ($checkBalance > 0) {
761 $balance = $this->getCPforUser($this->fk_user, $this->fk_type);
762
763 if ($balance < 0) {
764 $this->error = 'LeaveRequestCreationBlockedBecauseBalanceIsNegative';
765 return -1;
766 }
767 }
768
769 // Define new ref
770 if (!$error && (preg_match('/^[\‍(]?PROV/i', $this->ref) || empty($this->ref) || $this->ref == $this->id)) {
771 $num = $this->getNextNumRef(null);
772 } else {
773 $num = $this->ref;
774 }
775 $this->newref = dol_sanitizeFileName($num);
776
777 // Update status
778 $sql = "UPDATE ".MAIN_DB_PREFIX."holiday SET";
779 $sql .= " fk_user_valid = ".((int) $user->id).",";
780 $sql .= " date_valid = '".$this->db->idate(dol_now())."',";
781 if (!empty($this->status) && is_numeric($this->status)) {
782 $sql .= " statut = ".((int) $this->status).",";
783 } else {
784 $this->error = 'Property status must be a numeric value';
785 $error++;
786 }
787 $sql .= " ref = '".$this->db->escape($num)."'";
788 $sql .= " WHERE rowid = ".((int) $this->id);
789
790 $this->db->begin();
791
792 dol_syslog(get_class($this)."::validate", LOG_DEBUG);
793 $resql = $this->db->query($sql);
794 if (!$resql) {
795 $error++;
796 $this->errors[] = "Error ".$this->db->lasterror();
797 }
798
799 if (!$error) {
800 if (!$notrigger) {
801 // Call trigger
802 $result = $this->call_trigger('HOLIDAY_VALIDATE', $user);
803 if ($result < 0) {
804 $error++;
805 }
806 // End call triggers
807 }
808 }
809
810 if (!$error) {
811 $this->oldref = $this->ref;
812
813 // Rename directory if dir was a temporary ref
814 if (preg_match('/^[\‍(]?PROV/i', $this->ref)) {
815 // Now we rename also files into index
816 $sql = 'UPDATE ' . MAIN_DB_PREFIX . "ecm_files set filename = CONCAT('" . $this->db->escape($this->newref) . "', SUBSTR(filename, " . (strlen($this->ref) + 1) . ")), filepath = 'holiday/" . $this->db->escape($this->newref) . "'";
817 $sql .= " WHERE filename LIKE '" . $this->db->escape($this->ref) . "%' AND filepath = 'holiday/" . $this->db->escape($this->ref) . "' and entity = " . ((int) $conf->entity);
818 $resql = $this->db->query($sql);
819 if (!$resql) {
820 $error++;
821 $this->error = $this->db->lasterror();
822 }
823 $sql = 'UPDATE '.MAIN_DB_PREFIX."ecm_files set filepath = 'holiday/".$this->db->escape($this->newref)."'";
824 $sql .= " WHERE filepath = 'holiday/".$this->db->escape($this->ref)."' and entity = ".$conf->entity;
825 $resql = $this->db->query($sql);
826 if (!$resql) {
827 $error++;
828 $this->error = $this->db->lasterror();
829 }
830
831 // We rename directory ($this->ref = old ref, $num = new ref) in order not to lose the attachments
832 $oldref = dol_sanitizeFileName($this->ref);
833 $newref = dol_sanitizeFileName($num);
834 $dirsource = $conf->holiday->multidir_output[$this->entity] . '/' . $oldref;
835 $dirdest = $conf->holiday->multidir_output[$this->entity] . '/' . $newref;
836 if (!$error && file_exists($dirsource)) {
837 dol_syslog(get_class($this) . "::validate rename dir " . $dirsource . " into " . $dirdest);
838 if (@rename($dirsource, $dirdest)) {
839 dol_syslog("Rename ok");
840 // Rename docs starting with $oldref with $newref
841 $listoffiles = dol_dir_list($dirdest, 'files', 1, '^' . preg_quote($oldref, '/'));
842 foreach ($listoffiles as $fileentry) {
843 $dirsource = $fileentry['name'];
844 $dirdest = preg_replace('/^' . preg_quote($oldref, '/') . '/', $newref, $dirsource);
845 $dirsource = $fileentry['path'] . '/' . $dirsource;
846 $dirdest = $fileentry['path'] . '/' . $dirdest;
847 @rename($dirsource, $dirdest);
848 }
849 }
850 }
851 }
852 }
853
854
855 // Commit or rollback
856 if ($error) {
857 foreach ($this->errors as $errmsg) {
858 dol_syslog(get_class($this)."::validate ".$errmsg, LOG_ERR);
859 $this->error .= ($this->error ? ', '.$errmsg : $errmsg);
860 }
861 $this->db->rollback();
862 return -1 * $error;
863 } else {
864 $this->db->commit();
865 return 1;
866 }
867 }
868
869
877 public function approve($user = null, $notrigger = 0)
878 {
879 $error = 0;
880
881 $checkBalance = getDictionaryValue('c_holiday_types', 'block_if_negative', $this->fk_type, true);
882
883 if ($checkBalance > 0) {
884 $balance = $this->getCPforUser($this->fk_user, $this->fk_type);
885
886 if ($balance < 0) {
887 $this->error = 'LeaveRequestCreationBlockedBecauseBalanceIsNegative';
888 return -1;
889 }
890 }
891
892 // Update request
893 $sql = "UPDATE ".MAIN_DB_PREFIX."holiday SET";
894 $sql .= " description= '".$this->db->escape($this->description)."',";
895 if (!empty($this->date_debut)) {
896 $sql .= " date_debut = '".$this->db->idate($this->date_debut)."',";
897 } else {
898 $error++;
899 }
900 if (!empty($this->date_fin)) {
901 $sql .= " date_fin = '".$this->db->idate($this->date_fin)."',";
902 } else {
903 $error++;
904 }
905 $sql .= " halfday = ".((int) $this->halfday).",";
906 if (!empty($this->status) && is_numeric($this->status)) {
907 $sql .= " statut = ".((int) $this->status).",";
908 } else {
909 $error++;
910 }
911 if (!empty($this->fk_validator)) {
912 $sql .= " fk_validator = ".((int) $this->fk_validator).",";
913 } else {
914 $error++;
915 }
916 if (!empty($this->date_valid)) {
917 $sql .= " date_valid = '".$this->db->idate($this->date_valid)."',";
918 } else {
919 $sql .= " date_valid = NULL,";
920 }
921 if (!empty($this->fk_user_valid)) {
922 $sql .= " fk_user_valid = ".((int) $this->fk_user_valid).",";
923 } else {
924 $sql .= " fk_user_valid = NULL,";
925 }
926 if (!empty($this->date_approval)) {
927 $sql .= " date_approval = '".$this->db->idate($this->date_approval)."',";
928 } else {
929 $sql .= " date_approval = NULL,";
930 }
931 if (!empty($this->fk_user_approve)) {
932 $sql .= " fk_user_approve = ".((int) $this->fk_user_approve).",";
933 } else {
934 $sql .= " fk_user_approve = NULL,";
935 }
936 if (!empty($this->date_refuse)) {
937 $sql .= " date_refuse = '".$this->db->idate($this->date_refuse)."',";
938 } else {
939 $sql .= " date_refuse = NULL,";
940 }
941 if (!empty($this->fk_user_refuse)) {
942 $sql .= " fk_user_refuse = ".((int) $this->fk_user_refuse).",";
943 } else {
944 $sql .= " fk_user_refuse = NULL,";
945 }
946 if (!empty($this->date_cancel)) {
947 $sql .= " date_cancel = '".$this->db->idate($this->date_cancel)."',";
948 } else {
949 $sql .= " date_cancel = NULL,";
950 }
951 if (!empty($this->fk_user_cancel)) {
952 $sql .= " fk_user_cancel = ".((int) $this->fk_user_cancel).",";
953 } else {
954 $sql .= " fk_user_cancel = NULL,";
955 }
956 if (!empty($this->detail_refuse)) {
957 $sql .= " detail_refuse = '".$this->db->escape($this->detail_refuse)."'";
958 } else {
959 $sql .= " detail_refuse = NULL";
960 }
961 $sql .= " WHERE rowid = ".((int) $this->id);
962
963 $this->db->begin();
964
965 dol_syslog(get_class($this)."::approve", LOG_DEBUG);
966 $resql = $this->db->query($sql);
967 if (!$resql) {
968 $error++;
969 $this->errors[] = "Error ".$this->db->lasterror();
970 }
971
972 if (!$error) {
973 if (!$notrigger) {
974 // Call trigger
975 $result = $this->call_trigger('HOLIDAY_APPROVE', $user);
976 if ($result < 0) {
977 $error++;
978 }
979 // End call triggers
980 }
981 }
982
983 // Commit or rollback
984 if ($error) {
985 foreach ($this->errors as $errmsg) {
986 dol_syslog(get_class($this)."::approve ".$errmsg, LOG_ERR);
987 $this->error .= ($this->error ? ', '.$errmsg : $errmsg);
988 }
989 $this->db->rollback();
990 return -1 * $error;
991 } else {
992 $this->db->commit();
993 return 1;
994 }
995 }
996
1004 public function update($user = null, $notrigger = 0)
1005 {
1006 global $conf, $langs;
1007 $error = 0;
1008
1009 $checkBalance = getDictionaryValue('c_holiday_types', 'block_if_negative', $this->fk_type, true);
1010
1011 if ($checkBalance > 0 && $this->status != self::STATUS_DRAFT) {
1012 $balance = $this->getCPforUser($this->fk_user, $this->fk_type);
1013
1014 if ($balance < 0) {
1015 $this->error = 'LeaveRequestCreationBlockedBecauseBalanceIsNegative';
1016 return -1;
1017 }
1018 }
1019
1020 // Update request
1021 $sql = "UPDATE ".MAIN_DB_PREFIX."holiday SET";
1022
1023 $sql .= " description= '".$this->db->escape($this->description)."',";
1024
1025 if (!empty($this->date_debut)) {
1026 $sql .= " date_debut = '".$this->db->idate($this->date_debut)."',";
1027 } else {
1028 $error++;
1029 }
1030 if (!empty($this->date_fin)) {
1031 $sql .= " date_fin = '".$this->db->idate($this->date_fin)."',";
1032 } else {
1033 $error++;
1034 }
1035 $sql .= " halfday = ".$this->halfday.",";
1036 if (!empty($this->status) && is_numeric($this->status)) {
1037 $sql .= " statut = ".$this->status.",";
1038 } else {
1039 $error++;
1040 }
1041 if (!empty($this->fk_validator)) {
1042 $sql .= " fk_validator = '".$this->db->escape($this->fk_validator)."',";
1043 } else {
1044 $error++;
1045 }
1046 if (!empty($this->date_valid)) {
1047 $sql .= " date_valid = '".$this->db->idate($this->date_valid)."',";
1048 } else {
1049 $sql .= " date_valid = NULL,";
1050 }
1051 if (!empty($this->fk_user_valid)) {
1052 $sql .= " fk_user_valid = ".((int) $this->fk_user_valid).",";
1053 } else {
1054 $sql .= " fk_user_valid = NULL,";
1055 }
1056 if (!empty($this->date_approval)) {
1057 $sql .= " date_approval = '".$this->db->idate($this->date_approval)."',";
1058 } else {
1059 $sql .= " date_approval = NULL,";
1060 }
1061 if (!empty($this->fk_user_approve)) {
1062 $sql .= " fk_user_approve = ".((int) $this->fk_user_approve).",";
1063 } else {
1064 $sql .= " fk_user_approve = NULL,";
1065 }
1066 if (!empty($this->date_refuse)) {
1067 $sql .= " date_refuse = '".$this->db->idate($this->date_refuse)."',";
1068 } else {
1069 $sql .= " date_refuse = NULL,";
1070 }
1071 if (!empty($this->fk_user_refuse)) {
1072 $sql .= " fk_user_refuse = ".((int) $this->fk_user_refuse).",";
1073 } else {
1074 $sql .= " fk_user_refuse = NULL,";
1075 }
1076 if (!empty($this->date_cancel)) {
1077 $sql .= " date_cancel = '".$this->db->idate($this->date_cancel)."',";
1078 } else {
1079 $sql .= " date_cancel = NULL,";
1080 }
1081 if (!empty($this->fk_user_cancel)) {
1082 $sql .= " fk_user_cancel = ".((int) $this->fk_user_cancel).",";
1083 } else {
1084 $sql .= " fk_user_cancel = NULL,";
1085 }
1086 if (!empty($this->detail_refuse)) {
1087 $sql .= " detail_refuse = '".$this->db->escape($this->detail_refuse)."'";
1088 } else {
1089 $sql .= " detail_refuse = NULL";
1090 }
1091
1092 $sql .= " WHERE rowid = ".((int) $this->id);
1093
1094 $this->db->begin();
1095
1096 dol_syslog(get_class($this)."::update", LOG_DEBUG);
1097 $resql = $this->db->query($sql);
1098 if (!$resql) {
1099 $error++;
1100 $this->errors[] = "Error ".$this->db->lasterror();
1101 }
1102
1103 if (!$error) {
1104 $result = $this->insertExtraFields();
1105 if ($result < 0) {
1106 $error++;
1107 }
1108 }
1109
1110 if (!$error) {
1111 if (!$notrigger) {
1112 // Call trigger
1113 $result = $this->call_trigger('HOLIDAY_MODIFY', $user);
1114 if ($result < 0) {
1115 $error++;
1116 }
1117 // End call triggers
1118 }
1119 }
1120
1121 // Commit or rollback
1122 if ($error) {
1123 foreach ($this->errors as $errmsg) {
1124 dol_syslog(get_class($this)."::update ".$errmsg, LOG_ERR);
1125 $this->error .= ($this->error ? ', '.$errmsg : $errmsg);
1126 }
1127 $this->db->rollback();
1128 return -1 * $error;
1129 } else {
1130 $this->db->commit();
1131 return 1;
1132 }
1133 }
1134
1135
1143 public function delete($user, $notrigger = 0)
1144 {
1145 global $conf, $langs;
1146 $error = 0;
1147
1148 $sql = "DELETE FROM ".MAIN_DB_PREFIX."holiday";
1149 $sql .= " WHERE rowid=".((int) $this->id);
1150
1151 $this->db->begin();
1152
1153 dol_syslog(get_class($this)."::delete", LOG_DEBUG);
1154 $resql = $this->db->query($sql);
1155 if (!$resql) {
1156 $error++;
1157 $this->errors[] = "Error ".$this->db->lasterror();
1158 }
1159
1160 if (!$error) {
1161 if (!$notrigger) {
1162 // Call trigger
1163 $result = $this->call_trigger('HOLIDAY_DELETE', $user);
1164 if ($result < 0) {
1165 $error++;
1166 }
1167 // End call triggers
1168 }
1169 }
1170
1171 // Commit or rollback
1172 if ($error) {
1173 foreach ($this->errors as $errmsg) {
1174 dol_syslog(get_class($this)."::delete ".$errmsg, LOG_ERR);
1175 $this->error .= ($this->error ? ', '.$errmsg : $errmsg);
1176 }
1177 $this->db->rollback();
1178 return -1 * $error;
1179 } else {
1180 $this->db->commit();
1181 return 1;
1182 }
1183 }
1184
1198 public function verifDateHolidayCP($fk_user, $dateStart, $dateEnd, $halfday = 0)
1199 {
1200 $this->fetchByUser($fk_user, '', '');
1201
1202 foreach ($this->holiday as $infos_CP) {
1203 if ($infos_CP['statut'] == Holiday::STATUS_CANCELED) {
1204 continue; // ignore not validated holidays
1205 }
1206 if ($infos_CP['statut'] == Holiday::STATUS_REFUSED) {
1207 continue; // ignore refused holidays
1208 }
1209 //var_dump("--");
1210 //var_dump("old: ".dol_print_date($infos_CP['date_debut'],'dayhour').' '.dol_print_date($infos_CP['date_fin'],'dayhour').' '.$infos_CP['halfday']);
1211 //var_dump("new: ".dol_print_date($dateStart,'dayhour').' '.dol_print_date($dateEnd,'dayhour').' '.$halfday);
1212
1213 if ($halfday == 0) {
1214 if ($dateStart >= $infos_CP['date_debut'] && $dateStart <= $infos_CP['date_fin']) {
1215 return false;
1216 }
1217 if ($dateEnd <= $infos_CP['date_fin'] && $dateEnd >= $infos_CP['date_debut']) {
1218 return false;
1219 }
1220 } elseif ($halfday == -1) {
1221 // new start afternoon, new end afternoon
1222 if ($dateStart >= $infos_CP['date_debut'] && $dateStart <= $infos_CP['date_fin']) {
1223 if ($dateStart < $infos_CP['date_fin'] || in_array($infos_CP['halfday'], array(0, -1))) {
1224 return false;
1225 }
1226 }
1227 if ($dateEnd <= $infos_CP['date_fin'] && $dateEnd >= $infos_CP['date_debut']) {
1228 if ($dateStart < $dateEnd) {
1229 return false;
1230 }
1231 if ($dateEnd < $infos_CP['date_fin'] || in_array($infos_CP['halfday'], array(0, -1))) {
1232 return false;
1233 }
1234 }
1235 } elseif ($halfday == 1) {
1236 // new start morning, new end morning
1237 if ($dateStart >= $infos_CP['date_debut'] && $dateStart <= $infos_CP['date_fin']) {
1238 if ($dateStart < $dateEnd) {
1239 return false;
1240 }
1241 if ($dateStart > $infos_CP['date_debut'] || in_array($infos_CP['halfday'], array(0, 1))) {
1242 return false;
1243 }
1244 }
1245 if ($dateEnd <= $infos_CP['date_fin'] && $dateEnd >= $infos_CP['date_debut']) {
1246 if ($dateEnd > $infos_CP['date_debut'] || in_array($infos_CP['halfday'], array(0, 1))) {
1247 return false;
1248 }
1249 }
1250 } elseif ($halfday == 2) {
1251 // new start afternoon, new end morning
1252 if ($dateStart >= $infos_CP['date_debut'] && $dateStart <= $infos_CP['date_fin']) {
1253 if ($dateStart < $infos_CP['date_fin'] || in_array($infos_CP['halfday'], array(0, -1))) {
1254 return false;
1255 }
1256 }
1257 if ($dateEnd <= $infos_CP['date_fin'] && $dateEnd >= $infos_CP['date_debut']) {
1258 if ($dateEnd > $infos_CP['date_debut'] || in_array($infos_CP['halfday'], array(0, 1))) {
1259 return false;
1260 }
1261 }
1262 } else {
1263 dol_print_error(null, 'Bad value of parameter halfday when calling function verifDateHolidayCP');
1264 }
1265 }
1266
1267 return true;
1268 }
1269
1270
1280 public function verifDateHolidayForTimestamp($fk_user, $timestamp, $status = '-1')
1281 {
1282 $isavailablemorning = true;
1283 $isavailableafternoon = true;
1284
1285 // Check into leave requests
1286 $sql = "SELECT cp.rowid, cp.date_debut as date_start, cp.date_fin as date_end, cp.halfday, cp.statut as status";
1287 $sql .= " FROM ".MAIN_DB_PREFIX."holiday as cp";
1288 $sql .= " WHERE cp.entity IN (".getEntity('holiday').")";
1289 $sql .= " AND cp.fk_user = ".(int) $fk_user;
1290 $sql .= " AND cp.date_debut <= '".$this->db->idate($timestamp)."' AND cp.date_fin >= '".$this->db->idate($timestamp)."'";
1291 if ($status != '-1') {
1292 $sql .= " AND cp.statut IN (".$this->db->sanitize($status).")";
1293 }
1294
1295 $resql = $this->db->query($sql);
1296 if ($resql) {
1297 $num_rows = $this->db->num_rows($resql); // Note, we can have 2 records if on is morning and the other one is afternoon
1298 if ($num_rows > 0) {
1299 $arrayofrecord = array();
1300 $i = 0;
1301 while ($i < $num_rows) {
1302 $obj = $this->db->fetch_object($resql);
1303
1304 // Note: $obj->halfday is 0:Full days, 2:Start afternoon end morning, -1:Start afternoon, 1:End morning
1305 $arrayofrecord[$obj->rowid] = array('date_start' => $this->db->jdate($obj->date_start), 'date_end' => $this->db->jdate($obj->date_end), 'halfday' => $obj->halfday, 'status' => $obj->status);
1306 $i++;
1307 }
1308
1309 // We found a record, user is on holiday by default, so is not available is true.
1310 $isavailablemorning = true;
1311 foreach ($arrayofrecord as $record) {
1312 if ($timestamp == $record['date_start'] && $record['halfday'] == 2) {
1313 continue;
1314 }
1315 if ($timestamp == $record['date_start'] && $record['halfday'] == -1) {
1316 continue;
1317 }
1318 $isavailablemorning = false;
1319 break;
1320 }
1321 $isavailableafternoon = true;
1322 foreach ($arrayofrecord as $record) {
1323 if ($timestamp == $record['date_end'] && $record['halfday'] == 2) {
1324 continue;
1325 }
1326 if ($timestamp == $record['date_end'] && $record['halfday'] == 1) {
1327 continue;
1328 }
1329 $isavailableafternoon = false;
1330 break;
1331 }
1332 }
1333 } else {
1334 dol_print_error($this->db);
1335 }
1336
1337 $result = array('morning' => $isavailablemorning, 'afternoon' => $isavailableafternoon);
1338 if (!$isavailablemorning) {
1339 $result['morning_reason'] = 'leave_request';
1340 }
1341 if (!$isavailableafternoon) {
1342 $result['afternoon_reason'] = 'leave_request';
1343 }
1344 return $result;
1345 }
1346
1354 public function getTooltipContentArray($params)
1355 {
1356 global $langs;
1357
1358 $langs->load('holiday');
1359 $nofetch = !empty($params['nofetch']);
1360
1361 $datas = array();
1362 $datas['picto'] = img_picto('', $this->picto).' <u class="paddingrightonly">'.$langs->trans("Holiday").'</u>';
1363 if (isset($this->status)) {
1364 $datas['picto'] .= ' '.$this->getLibStatut(5);
1365 }
1366 $datas['ref'] = '<br><b>'.$langs->trans('Ref').':</b> '.$this->ref;
1367 // show type for this record only in ajax to not overload lists
1368 if (!$nofetch && !empty($this->fk_type)) {
1369 $typeleaves = $this->getTypes(1, -1);
1370 if (empty($typeleaves[$this->fk_type])) {
1371 $labeltoshow = $langs->trans("TypeWasDisabledOrRemoved", $this->fk_type);
1372 } else {
1373 $labeltoshow = (($typeleaves[$this->fk_type]['code'] && $langs->trans($typeleaves[$this->fk_type]['code']) != $typeleaves[$this->fk_type]['code']) ? $langs->trans($typeleaves[$this->fk_type]['code']) : $typeleaves[$this->fk_type]['label']);
1374 }
1375 $datas['type'] = '<br><b>'.$langs->trans("Type") . ':</b> ' . $labeltoshow;
1376 }
1377 if (isset($this->halfday) && !empty($this->date_debut) && !empty($this->date_fin)) {
1378 $listhalfday = array(
1379 'morning' => $langs->trans("Morning"),
1380 "afternoon" => $langs->trans("Afternoon")
1381 );
1382 $starthalfday = ($this->halfday == -1 || $this->halfday == 2) ? 'afternoon' : 'morning';
1383 $endhalfday = ($this->halfday == 1 || $this->halfday == 2) ? 'morning' : 'afternoon';
1384 $datas['date_start'] = '<br><b>'.$langs->trans('DateDebCP') . '</b>: '. dol_print_date($this->date_debut, 'day') . '&nbsp;&nbsp;<span class="opacitymedium">'.$langs->trans($listhalfday[$starthalfday]).'</span>';
1385 $datas['date_end'] = '<br><b>'.$langs->trans('DateFinCP') . '</b>: '. dol_print_date($this->date_fin, 'day') . '&nbsp;&nbsp;<span class="opacitymedium">'.$langs->trans($listhalfday[$endhalfday]).'</span>';
1386 }
1387
1388
1389 return $datas;
1390 }
1391
1401 public function getNomUrl($withpicto = 0, $save_lastsearch_value = -1, $notooltip = 0, $morecss = '')
1402 {
1403 global $conf, $langs, $hookmanager;
1404
1405 if (!empty($conf->dol_no_mouse_hover)) {
1406 $notooltip = 1; // Force disable tooltips
1407 }
1408
1409 $result = '';
1410 $params = [
1411 'id' => $this->id,
1412 'objecttype' => $this->element,
1413 'nofetch' => 1,
1414 ];
1415 $classfortooltip = 'classfortooltip';
1416 $dataparams = '';
1417 if (getDolGlobalInt('MAIN_ENABLE_AJAX_TOOLTIP')) {
1418 $classfortooltip = 'classforajaxtooltip';
1419 $dataparams = ' data-params="'.dol_escape_htmltag(json_encode($params)).'"';
1420 $label = '';
1421 } else {
1422 $label = implode($this->getTooltipContentArray($params));
1423 }
1424
1425 $url = DOL_URL_ROOT.'/holiday/card.php?id='.$this->id;
1426
1427 //if ($option != 'nolink')
1428 //{
1429 // Add param to save lastsearch_values or not
1430 $add_save_lastsearch_values = ($save_lastsearch_value == 1 ? 1 : 0);
1431 if ($save_lastsearch_value == -1 && isset($_SERVER["PHP_SELF"]) && preg_match('/list\.php/', $_SERVER["PHP_SELF"])) {
1432 $add_save_lastsearch_values = 1;
1433 }
1434 if ($add_save_lastsearch_values) {
1435 $url .= '&save_lastsearch_values=1';
1436 }
1437 //}
1438
1439 $linkclose = '';
1440 if (empty($notooltip)) {
1441 if (getDolGlobalInt('MAIN_OPTIMIZEFORTEXTBROWSER')) {
1442 $label = $langs->trans("ShowMyObject");
1443 $linkclose .= ' alt="'.dol_escape_htmltag($label, 1).'"';
1444 }
1445 $linkclose .= ($label ? ' title="'.dol_escape_htmltag($label, 1).'"' : ' title="tocomplete"');
1446 $linkclose .= $dataparams.' class="'.$classfortooltip.($morecss ? ' '.$morecss : '').'"';
1447 } else {
1448 $linkclose = ($morecss ? ' class="'.$morecss.'"' : '');
1449 }
1450
1451 $linkstart = '<a href="'.$url.'"';
1452 $linkstart .= $linkclose.'>';
1453 $linkend = '</a>';
1454
1455 $result .= $linkstart;
1456
1457 if ($withpicto) {
1458 $result .= img_object(($notooltip ? '' : $label), ($this->picto ? $this->picto : 'generic'), ($notooltip ? (($withpicto != 2) ? 'class="paddingright"' : '') : 'class="'.(($withpicto != 2) ? 'paddingright ' : '').'"'), 0, 0, $notooltip ? 0 : 1);
1459 }
1460 if ($withpicto != 2) {
1461 $result .= $this->ref;
1462 }
1463 $result .= $linkend;
1464
1465 global $action;
1466 $hookmanager->initHooks(array($this->element . 'dao'));
1467 $parameters = array('id' => $this->id, 'getnomurl' => &$result);
1468 $reshook = $hookmanager->executeHooks('getNomUrl', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
1469 if ($reshook > 0) {
1470 $result = $hookmanager->resPrint;
1471 } else {
1472 $result .= $hookmanager->resPrint;
1473 }
1474 return $result;
1475 }
1476
1477
1484 public function getLibStatut($mode = 0)
1485 {
1486 return $this->LibStatut($this->status, $mode, $this->date_debut);
1487 }
1488
1489 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1498 public function LibStatut($status, $mode = 0, $startdate = '')
1499 {
1500 // phpcs:enable
1501 global $langs;
1502
1503 if (empty($this->labelStatus) || empty($this->labelStatusShort)) {
1504 global $langs;
1505 //$langs->load("mymodule");
1506 $this->labelStatus[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('DraftCP');
1507 $this->labelStatus[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('ToReviewCP');
1508 $this->labelStatus[self::STATUS_APPROVED] = $langs->transnoentitiesnoconv('ApprovedCP');
1509 $this->labelStatus[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('CancelCP');
1510 $this->labelStatus[self::STATUS_REFUSED] = $langs->transnoentitiesnoconv('RefuseCP');
1511 $this->labelStatusShort[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('DraftCP');
1512 $this->labelStatusShort[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('ToReviewCP');
1513 $this->labelStatusShort[self::STATUS_APPROVED] = $langs->transnoentitiesnoconv('ApprovedCP');
1514 $this->labelStatusShort[self::STATUS_CANCELED] = $langs->transnoentitiesnoconv('CancelCP');
1515 $this->labelStatusShort[self::STATUS_REFUSED] = $langs->transnoentitiesnoconv('RefuseCP');
1516 }
1517
1518 $params = array();
1519 $statusType = 'status6';
1520 if (!empty($startdate) && $startdate >= dol_now()) { // If not yet passed, we use a green "in live" color
1521 $statusType = 'status4';
1522 $params = array('tooltip' => $this->labelStatus[$status].' - '.$langs->trans("Forthcoming"));
1523 }
1524 if ($status == self::STATUS_DRAFT) {
1525 $statusType = 'status0';
1526 }
1527 if ($status == self::STATUS_VALIDATED) {
1528 $statusType = 'status1';
1529 }
1530 if ($status == self::STATUS_CANCELED) {
1531 $statusType = 'status9';
1532 }
1533 if ($status == self::STATUS_REFUSED) {
1534 $statusType = 'status9';
1535 }
1536
1537 return dolGetStatus($this->labelStatus[$status], $this->labelStatusShort[$status], '', $statusType, $mode, '', $params);
1538 }
1539
1540
1549 public function selectStatutCP($selected = 0, $htmlname = 'select_statut', $morecss = 'minwidth125')
1550 {
1551 global $langs;
1552
1553 // List of status label
1554 $name = array('DraftCP', 'ToReviewCP', 'ApprovedCP', 'CancelCP', 'RefuseCP');
1555 $nb = count($name) + 1;
1556
1557 // Select HTML
1558 $out = '<select name="'.$htmlname.'" id="'.$htmlname.'" class="flat'.($morecss ? ' '.$morecss : '').'">'."\n";
1559 $out .= '<option value="-1">&nbsp;</option>'."\n";
1560
1561 // Loop on status
1562 for ($i = 1; $i < $nb; $i++) {
1563 if ($i == $selected) {
1564 $out .= '<option value="'.$i.'" selected>'.$langs->trans($name[$i - 1]).'</option>'."\n";
1565 } else {
1566 $out .= '<option value="'.$i.'">'.$langs->trans($name[$i - 1]).'</option>'."\n";
1567 }
1568 }
1569
1570 $out .= "</select>\n";
1571
1572 $showempty = 0;
1573 $out .= ajax_combobox($htmlname, array(), 0, 0, 'resolve', ($showempty < 0 ? (string) $showempty : '-1'), $morecss);
1574
1575 return $out;
1576 }
1577
1585 public function updateConfCP($name, $value)
1586 {
1587 $sql = "UPDATE ".MAIN_DB_PREFIX."holiday_config SET";
1588 $sql .= " value = '".$this->db->escape($value)."'";
1589 $sql .= " WHERE name = '".$this->db->escape($name)."'";
1590
1591 dol_syslog(get_class($this).'::updateConfCP name='.$name, LOG_DEBUG);
1592 $result = $this->db->query($sql);
1593 if ($result) {
1594 return true;
1595 }
1596
1597 return false;
1598 }
1599
1608 public function getConfCP($name, $createifnotfound = '')
1609 {
1610 $sql = "SELECT value";
1611 $sql .= " FROM ".MAIN_DB_PREFIX."holiday_config";
1612 $sql .= " WHERE name = '".$this->db->escape($name)."'";
1613
1614 dol_syslog(get_class($this).'::getConfCP name='.$name.' createifnotfound='.$createifnotfound, LOG_DEBUG);
1615 $result = $this->db->query($sql);
1616
1617 if ($result) {
1618 $obj = $this->db->fetch_object($result);
1619 // Return value
1620 if (empty($obj)) {
1621 if ($createifnotfound) {
1622 $sql = "INSERT INTO ".MAIN_DB_PREFIX."holiday_config(name, value)";
1623 $sql .= " VALUES('".$this->db->escape($name)."', '".$this->db->escape($createifnotfound)."')";
1624 $result = $this->db->query($sql);
1625 if ($result) {
1626 return $createifnotfound;
1627 } else {
1628 $this->error = $this->db->lasterror();
1629 return -2;
1630 }
1631 } else {
1632 return '';
1633 }
1634 } else {
1635 return $obj->value;
1636 }
1637 } else {
1638 // Erreur SQL
1639 $this->error = $this->db->lasterror();
1640 return -1;
1641 }
1642 }
1643
1652 public function updateSoldeCP($userID = 0, $nbHoliday = 0, $fk_type = 0)
1653 {
1654 global $user, $langs;
1655
1656 $error = 0;
1657
1658 if (empty($userID) && empty($nbHoliday) && empty($fk_type)) {
1659 $langs->load("holiday");
1660
1661 // Si mise à jour pour tout le monde en début de mois
1662 $now = dol_now();
1663
1664 $month = date('m', $now);
1665 $newdateforlastupdate = dol_print_date($now, '%Y%m%d%H%M%S');
1666
1667 // Get month of last update
1668 $lastUpdate = $this->getConfCP('lastUpdate', $newdateforlastupdate);
1669 $monthLastUpdate = $lastUpdate[4].$lastUpdate[5];
1670 //print 'month: '.$month.' lastUpdate:'.$lastUpdate.' monthLastUpdate:'.$monthLastUpdate;exit;
1671
1672 // If month date is not same than the one of last update (the one we saved in database), then we update the timestamp and balance of each open user.
1673 if ($month != $monthLastUpdate) {
1674 $this->db->begin();
1675
1676 $users = $this->fetchUsers(false, false, ' AND u.statut > 0');
1677 $nbUser = count($users);
1678
1679 $sql = "UPDATE ".MAIN_DB_PREFIX."holiday_config SET";
1680 $sql .= " value = '".$this->db->escape($newdateforlastupdate)."'";
1681 $sql .= " WHERE name = 'lastUpdate'";
1682 $result = $this->db->query($sql);
1683
1684 $typeleaves = $this->getTypes(1, 1);
1685
1686 // Update each user counter
1687 foreach ($users as $userCounter) {
1688 $nbDaysToAdd = (isset($typeleaves[$userCounter['type']]['newbymonth']) ? $typeleaves[$userCounter['type']]['newbymonth'] : 0);
1689 if (empty($nbDaysToAdd)) {
1690 continue;
1691 }
1692
1693 dol_syslog("We update leave type id ".$userCounter['type']." for user id ".$userCounter['rowid'], LOG_DEBUG);
1694
1695 $nowHoliday = $userCounter['nb_holiday'];
1696 $newSolde = $nowHoliday + $nbDaysToAdd;
1697
1698 // We add a log for each user
1699 $this->addLogCP($user->id, $userCounter['rowid'], $langs->trans('HolidaysMonthlyUpdate'), $newSolde, $userCounter['type']);
1700
1701 $result = $this->updateSoldeCP($userCounter['rowid'], $newSolde, $userCounter['type']);
1702
1703 if ($result < 0) {
1704 $error++;
1705 break;
1706 }
1707 }
1708
1709 if (!$error) {
1710 $this->db->commit();
1711 return 1;
1712 } else {
1713 $this->db->rollback();
1714 return -1;
1715 }
1716 }
1717
1718 return 0;
1719 } else {
1720 // Mise à jour pour un utilisateur
1721 $nbHoliday = price2num($nbHoliday, 5);
1722
1723 $sql = "SELECT nb_holiday FROM ".MAIN_DB_PREFIX."holiday_users";
1724 $sql .= " WHERE fk_user = ".(int) $userID." AND fk_type = ".(int) $fk_type;
1725 $resql = $this->db->query($sql);
1726 if ($resql) {
1727 $num = $this->db->num_rows($resql);
1728
1729 if ($num > 0) {
1730 // Update for user
1731 $sql = "UPDATE ".MAIN_DB_PREFIX."holiday_users SET";
1732 $sql .= " nb_holiday = ".((float) $nbHoliday);
1733 $sql .= " WHERE fk_user = ".(int) $userID." AND fk_type = ".(int) $fk_type;
1734 $result = $this->db->query($sql);
1735 if (!$result) {
1736 $error++;
1737 $this->errors[] = $this->db->lasterror();
1738 }
1739 } else {
1740 // Insert for user
1741 $sql = "INSERT INTO ".MAIN_DB_PREFIX."holiday_users(nb_holiday, fk_user, fk_type) VALUES (";
1742 $sql .= ((float) $nbHoliday);
1743 $sql .= ", ".(int) $userID.", ".(int) $fk_type.")";
1744 $result = $this->db->query($sql);
1745 if (!$result) {
1746 $error++;
1747 $this->errors[] = $this->db->lasterror();
1748 }
1749 }
1750 } else {
1751 $this->errors[] = $this->db->lasterror();
1752 $error++;
1753 }
1754
1755 if (!$error) {
1756 return 1;
1757 } else {
1758 return -1;
1759 }
1760 }
1761 }
1762
1770 public function createCPusers($single = false, $userid = 0)
1771 {
1772 // do we have to add balance for all users ?
1773 if (!$single) {
1774 dol_syslog(get_class($this).'::createCPusers');
1775 $arrayofusers = $this->fetchUsers(false, true);
1776
1777 foreach ($arrayofusers as $users) {
1778 $sql = "INSERT INTO ".MAIN_DB_PREFIX."holiday_users";
1779 $sql .= " (fk_user, nb_holiday)";
1780 $sql .= " VALUES (".((int) $users['rowid'])."', '0')";
1781
1782 $resql = $this->db->query($sql);
1783 if (!$resql) {
1784 dol_print_error($this->db);
1785 }
1786 }
1787 } else {
1788 $sql = "INSERT INTO ".MAIN_DB_PREFIX."holiday_users";
1789 $sql .= " (fk_user, nb_holiday)";
1790 $sql .= " VALUES (".((int) $userid)."', '0')";
1791
1792 $resql = $this->db->query($sql);
1793 if (!$resql) {
1794 dol_print_error($this->db);
1795 }
1796 }
1797 }
1798
1806 public function getCPforUser($user_id, $fk_type = 0)
1807 {
1808 $sql = "SELECT nb_holiday";
1809 $sql .= " FROM ".MAIN_DB_PREFIX."holiday_users";
1810 $sql .= " WHERE fk_user = ".(int) $user_id;
1811 if ($fk_type > 0) {
1812 $sql .= " AND fk_type = ".(int) $fk_type;
1813 }
1814
1815 dol_syslog(get_class($this).'::getCPforUser user_id='.$user_id.' type_id='.$fk_type, LOG_DEBUG);
1816 $result = $this->db->query($sql);
1817 if ($result) {
1818 $obj = $this->db->fetch_object($result);
1819 //return number_format($obj->nb_holiday,2);
1820 if ($obj) {
1821 return $obj->nb_holiday;
1822 } else {
1823 return null;
1824 }
1825 } else {
1826 return null;
1827 }
1828 }
1829
1838 public function fetchUsers($stringlist = true, $type = true, $filters = '')
1839 {
1840 global $conf;
1841
1842 dol_syslog(get_class($this)."::fetchUsers", LOG_DEBUG);
1843
1844 if ($stringlist) {
1845 if ($type) {
1846 // If user of Dolibarr
1847 $sql = "SELECT";
1848 if (isModEnabled('multicompany') && getDolGlobalString('MULTICOMPANY_TRANSVERSE_MODE')) {
1849 $sql .= " DISTINCT";
1850 }
1851 $sql .= " u.rowid";
1852 $sql .= " FROM ".MAIN_DB_PREFIX."user as u";
1853
1854 if (isModEnabled('multicompany') && getDolGlobalString('MULTICOMPANY_TRANSVERSE_MODE')) {
1855 $sql .= ", ".MAIN_DB_PREFIX."usergroup_user as ug";
1856 $sql .= " WHERE ((ug.fk_user = u.rowid";
1857 $sql .= " AND ug.entity IN (".getEntity('usergroup')."))";
1858 $sql .= " OR u.entity = 0)"; // Show always superadmin
1859 } else {
1860 $sql .= " WHERE u.entity IN (".getEntity('user').")";
1861 }
1862 $sql .= " AND u.statut > 0";
1863 $sql .= " AND u.employee = 1"; // We only want employee users for holidays
1864 if ($filters) {
1865 $sql .= $filters;
1866 }
1867
1868 $resql = $this->db->query($sql);
1869
1870 // Si pas d'erreur SQL
1871 if ($resql) {
1872 $i = 0;
1873 $num = $this->db->num_rows($resql);
1874 $stringlist = '';
1875
1876 // Boucles du listage des utilisateurs
1877 while ($i < $num) {
1878 $obj = $this->db->fetch_object($resql);
1879
1880 if ($i == 0) {
1881 $stringlist .= $obj->rowid;
1882 } else {
1883 $stringlist .= ', '.$obj->rowid;
1884 }
1885
1886 $i++;
1887 }
1888 // Retoune le tableau des utilisateurs
1889 return $stringlist;
1890 } else {
1891 // Erreur SQL
1892 $this->error = "Error ".$this->db->lasterror();
1893 return -1;
1894 }
1895 } else {
1896 // We want only list of vacation balance for user ids
1897 $sql = "SELECT DISTINCT cpu.fk_user";
1898 $sql .= " FROM ".MAIN_DB_PREFIX."holiday_users as cpu, ".MAIN_DB_PREFIX."user as u";
1899 $sql .= " WHERE cpu.fk_user = u.rowid";
1900 if ($filters) {
1901 $sql .= $filters;
1902 }
1903
1904 $resql = $this->db->query($sql);
1905
1906 // Si pas d'erreur SQL
1907 if ($resql) {
1908 $i = 0;
1909 $num = $this->db->num_rows($resql);
1910 $stringlist = '';
1911
1912 // Boucles du listage des utilisateurs
1913 while ($i < $num) {
1914 $obj = $this->db->fetch_object($resql);
1915
1916 if ($i == 0) {
1917 $stringlist .= $obj->fk_user;
1918 } else {
1919 $stringlist .= ', '.$obj->fk_user;
1920 }
1921
1922 $i++;
1923 }
1924 // Retoune le tableau des utilisateurs
1925 return $stringlist;
1926 } else {
1927 // Erreur SQL
1928 $this->error = "Error ".$this->db->lasterror();
1929 return -1;
1930 }
1931 }
1932 } else {
1933 // Si faux donc return array
1934 // List for Dolibarr users
1935 if ($type) {
1936 // If we need users of Dolibarr
1937 $sql = "SELECT";
1938 if (isModEnabled('multicompany') && getDolGlobalString('MULTICOMPANY_TRANSVERSE_MODE')) {
1939 $sql .= " DISTINCT";
1940 }
1941 $sql .= " u.rowid, u.lastname, u.firstname, u.gender, u.photo, u.employee, u.statut as status, u.fk_user";
1942 $sql .= " FROM ".MAIN_DB_PREFIX."user as u";
1943
1944 if (isModEnabled('multicompany') && getDolGlobalString('MULTICOMPANY_TRANSVERSE_MODE')) {
1945 $sql .= ", ".MAIN_DB_PREFIX."usergroup_user as ug";
1946 $sql .= " WHERE ((ug.fk_user = u.rowid";
1947 $sql .= " AND ug.entity IN (".getEntity('usergroup')."))";
1948 $sql .= " OR u.entity = 0)"; // Show always superadmin
1949 } else {
1950 $sql .= " WHERE u.entity IN (".getEntity('user').")";
1951 }
1952
1953 $sql .= " AND u.statut > 0";
1954 $sql .= " AND u.employee = 1"; // We only want employee users for holidays
1955 if ($filters) {
1956 $sql .= $filters;
1957 }
1958
1959 $resql = $this->db->query($sql);
1960
1961 // Si pas d'erreur SQL
1962 if ($resql) {
1963 $i = 0;
1964 $tab_result = $this->holiday;
1965 $num = $this->db->num_rows($resql);
1966
1967 // Boucles du listage des utilisateurs
1968 while ($i < $num) {
1969 $obj = $this->db->fetch_object($resql);
1970
1971 $tab_result[$i]['rowid'] = $obj->rowid; // rowid of user
1972 $tab_result[$i]['id'] = $obj->rowid; // id of user
1973 $tab_result[$i]['name'] = $obj->lastname; // deprecated
1974 $tab_result[$i]['lastname'] = $obj->lastname;
1975 $tab_result[$i]['firstname'] = $obj->firstname;
1976 $tab_result[$i]['gender'] = $obj->gender;
1977 $tab_result[$i]['status'] = $obj->status;
1978 $tab_result[$i]['employee'] = $obj->employee;
1979 $tab_result[$i]['photo'] = $obj->photo;
1980 $tab_result[$i]['fk_user'] = $obj->fk_user; // rowid of manager
1981 //$tab_result[$i]['type'] = $obj->type;
1982 //$tab_result[$i]['nb_holiday'] = $obj->nb_holiday;
1983
1984 $i++;
1985 }
1986 // Retoune le tableau des utilisateurs
1987 return $tab_result;
1988 } else {
1989 // Erreur SQL
1990 $this->errors[] = "Error ".$this->db->lasterror();
1991 return -1;
1992 }
1993 } else {
1994 // List of vacation balance users
1995 $sql = "SELECT cpu.fk_type, cpu.nb_holiday, u.rowid, u.lastname, u.firstname, u.gender, u.photo, u.employee, u.statut as status, u.fk_user";
1996 $sql .= " FROM ".MAIN_DB_PREFIX."holiday_users as cpu, ".MAIN_DB_PREFIX."user as u";
1997 $sql .= " WHERE cpu.fk_user = u.rowid";
1998 if ($filters) {
1999 $sql .= $filters;
2000 }
2001
2002 $resql = $this->db->query($sql);
2003
2004 // Si pas d'erreur SQL
2005 if ($resql) {
2006 $i = 0;
2007 $tab_result = $this->holiday;
2008 $num = $this->db->num_rows($resql);
2009
2010 // Boucles du listage des utilisateurs
2011 while ($i < $num) {
2012 $obj = $this->db->fetch_object($resql);
2013
2014 $tab_result[$i]['rowid'] = $obj->rowid; // rowid of user
2015 $tab_result[$i]['id'] = $obj->rowid; // id of user
2016 $tab_result[$i]['name'] = $obj->lastname; // deprecated
2017 $tab_result[$i]['lastname'] = $obj->lastname;
2018 $tab_result[$i]['firstname'] = $obj->firstname;
2019 $tab_result[$i]['gender'] = $obj->gender;
2020 $tab_result[$i]['status'] = $obj->status;
2021 $tab_result[$i]['employee'] = $obj->employee;
2022 $tab_result[$i]['photo'] = $obj->photo;
2023 $tab_result[$i]['fk_user'] = $obj->fk_user; // rowid of manager
2024
2025 $tab_result[$i]['type'] = $obj->fk_type;
2026 $tab_result[$i]['nb_holiday'] = $obj->nb_holiday;
2027
2028 $i++;
2029 }
2030 // Retoune le tableau des utilisateurs
2031 return $tab_result;
2032 } else {
2033 // Erreur SQL
2034 $this->error = "Error ".$this->db->lasterror();
2035 return -1;
2036 }
2037 }
2038 }
2039 }
2040
2041
2042 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
2050 {
2051 // phpcs:enable
2052 $users_validator = array();
2053
2054 $sql = "SELECT DISTINCT ur.fk_user";
2055 $sql .= " FROM ".MAIN_DB_PREFIX."user_rights as ur, ".MAIN_DB_PREFIX."rights_def as rd";
2056 $sql .= " WHERE ur.fk_id = rd.id and rd.module = 'holiday' AND rd.perms = 'approve'"; // Permission 'Approve';
2057 $sql .= "UNION";
2058 $sql .= " SELECT DISTINCT ugu.fk_user";
2059 $sql .= " FROM ".MAIN_DB_PREFIX."usergroup_user as ugu, ".MAIN_DB_PREFIX."usergroup_rights as ur, ".MAIN_DB_PREFIX."rights_def as rd";
2060 $sql .= " WHERE ugu.fk_usergroup = ur.fk_usergroup AND ur.fk_id = rd.id and rd.module = 'holiday' AND rd.perms = 'approve'"; // Permission 'Approve';
2061 //print $sql;
2062
2063 dol_syslog(get_class($this)."::fetch_users_approver_holiday sql=".$sql);
2064 $result = $this->db->query($sql);
2065 if ($result) {
2066 $num_rows = $this->db->num_rows($result);
2067 $i = 0;
2068 while ($i < $num_rows) {
2069 $objp = $this->db->fetch_object($result);
2070 array_push($users_validator, $objp->fk_user);
2071 $i++;
2072 }
2073 return $users_validator;
2074 } else {
2075 $this->error = $this->db->lasterror();
2076 dol_syslog(get_class($this)."::fetch_users_approver_holiday Error ".$this->error, LOG_ERR);
2077 return -1;
2078 }
2079 }
2080
2081
2087 public function countActiveUsers()
2088 {
2089 $sql = "SELECT count(u.rowid) as compteur";
2090 $sql .= " FROM ".MAIN_DB_PREFIX."user as u";
2091 $sql .= " WHERE u.statut > 0";
2092
2093 $result = $this->db->query($sql);
2094 $object = $this->db->fetch_object($result);
2095
2096 return $object->compteur;
2097 }
2104 {
2105 $sql = "SELECT count(u.rowid) as compteur";
2106 $sql .= " FROM ".MAIN_DB_PREFIX."user as u LEFT OUTER JOIN ".MAIN_DB_PREFIX."holiday_users hu ON (hu.fk_user=u.rowid)";
2107 $sql .= " WHERE u.statut > 0 AND hu.fk_user IS NULL";
2108
2109 $result = $this->db->query($sql);
2110 $object = $this->db->fetch_object($result);
2111
2112 return $object->compteur;
2113 }
2114
2122 public function verifNbUsers($userDolibarrWithoutCP, $userCP)
2123 {
2124 if (empty($userCP)) {
2125 $userCP = 0;
2126 }
2127 dol_syslog(get_class($this).'::verifNbUsers userDolibarr='.$userDolibarrWithoutCP.' userCP='.$userCP);
2128 return 1;
2129 }
2130
2131
2142 public function addLogCP($fk_user_action, $fk_user_update, $label, $new_solde, $fk_type)
2143 {
2144 global $conf, $langs;
2145
2146 $error = 0;
2147
2148 $prev_solde = price2num($this->getCPforUser($fk_user_update, $fk_type), 5);
2149 $new_solde = price2num($new_solde, 5);
2150 //print "$prev_solde == $new_solde";
2151
2152 if ($prev_solde == $new_solde) {
2153 return 0;
2154 }
2155
2156 $this->db->begin();
2157
2158 // Insert request
2159 $sql = "INSERT INTO ".MAIN_DB_PREFIX."holiday_logs (";
2160 $sql .= "date_action,";
2161 $sql .= "fk_user_action,";
2162 $sql .= "fk_user_update,";
2163 $sql .= "type_action,";
2164 $sql .= "prev_solde,";
2165 $sql .= "new_solde,";
2166 $sql .= "fk_type";
2167 $sql .= ") VALUES (";
2168 $sql .= " '".$this->db->idate(dol_now())."',";
2169 $sql .= " ".((int) $fk_user_action).",";
2170 $sql .= " ".((int) $fk_user_update).",";
2171 $sql .= " '".$this->db->escape($label)."',";
2172 $sql .= " ".((float) $prev_solde).",";
2173 $sql .= " ".((float) $new_solde).",";
2174 $sql .= " ".((int) $fk_type);
2175 $sql .= ")";
2176
2177 $resql = $this->db->query($sql);
2178 if (!$resql) {
2179 $error++;
2180 $this->errors[] = "Error ".$this->db->lasterror();
2181 }
2182
2183 if (!$error) {
2184 $this->optRowid = $this->db->last_insert_id(MAIN_DB_PREFIX."holiday_logs");
2185 }
2186
2187 // Commit or rollback
2188 if ($error) {
2189 foreach ($this->errors as $errmsg) {
2190 dol_syslog(get_class($this)."::addLogCP ".$errmsg, LOG_ERR);
2191 $this->error .= ($this->error ? ', '.$errmsg : $errmsg);
2192 }
2193 $this->db->rollback();
2194 return -1 * $error;
2195 } else {
2196 $this->db->commit();
2197 return $this->optRowid;
2198 }
2199 }
2200
2208 public function fetchLog($order, $filter)
2209 {
2210 $sql = "SELECT";
2211 $sql .= " cpl.rowid,";
2212 $sql .= " cpl.date_action,";
2213 $sql .= " cpl.fk_user_action,";
2214 $sql .= " cpl.fk_user_update,";
2215 $sql .= " cpl.type_action,";
2216 $sql .= " cpl.prev_solde,";
2217 $sql .= " cpl.new_solde,";
2218 $sql .= " cpl.fk_type";
2219 $sql .= " FROM ".MAIN_DB_PREFIX."holiday_logs as cpl";
2220 $sql .= " WHERE cpl.rowid > 0"; // To avoid error with other search and criteria
2221
2222 // Filtrage de séléction
2223 if (!empty($filter)) {
2224 $sql .= " ".$filter;
2225 }
2226
2227 // Ordre d'affichage
2228 if (!empty($order)) {
2229 $sql .= " ".$order;
2230 }
2231
2232 dol_syslog(get_class($this)."::fetchLog", LOG_DEBUG);
2233 $resql = $this->db->query($sql);
2234
2235 // Si pas d'erreur SQL
2236 if ($resql) {
2237 $i = 0;
2238 $tab_result = $this->logs;
2239 $num = $this->db->num_rows($resql);
2240
2241 // Si pas d'enregistrement
2242 if (!$num) {
2243 return 2;
2244 }
2245
2246 // On liste les résultats et on les ajoutent dans le tableau
2247 while ($i < $num) {
2248 $obj = $this->db->fetch_object($resql);
2249
2250 $tab_result[$i]['rowid'] = $obj->rowid;
2251 $tab_result[$i]['id'] = $obj->rowid;
2252 $tab_result[$i]['date_action'] = $obj->date_action;
2253 $tab_result[$i]['fk_user_action'] = $obj->fk_user_action;
2254 $tab_result[$i]['fk_user_update'] = $obj->fk_user_update;
2255 $tab_result[$i]['type_action'] = $obj->type_action;
2256 $tab_result[$i]['prev_solde'] = $obj->prev_solde;
2257 $tab_result[$i]['new_solde'] = $obj->new_solde;
2258 $tab_result[$i]['fk_type'] = $obj->fk_type;
2259
2260 $i++;
2261 }
2262 // Retourne 1 et ajoute le tableau à la variable
2263 $this->logs = $tab_result;
2264 return 1;
2265 } else {
2266 // Erreur SQL
2267 $this->error = "Error ".$this->db->lasterror();
2268 return -1;
2269 }
2270 }
2271
2272
2280 public function getTypes($active = -1, $affect = -1)
2281 {
2282 global $mysoc;
2283
2284 $sql = "SELECT rowid, code, label, affect, delay, newbymonth";
2285 $sql .= " FROM ".MAIN_DB_PREFIX."c_holiday_types";
2286 $sql .= " WHERE (fk_country IS NULL OR fk_country = ".((int) $mysoc->country_id).')';
2287 $sql .= " AND entity IN (".getEntity('c_holiday_types').")";
2288 if ($active >= 0) {
2289 $sql .= " AND active = ".((int) $active);
2290 }
2291 if ($affect >= 0) {
2292 $sql .= " AND affect = ".((int) $affect);
2293 }
2294 $sql .= " ORDER BY sortorder";
2295
2296 $result = $this->db->query($sql);
2297 if ($result) {
2298 $num = $this->db->num_rows($result);
2299 if ($num) {
2300 $types = array();
2301 while ($obj = $this->db->fetch_object($result)) {
2302 $types[$obj->rowid] = array('id' => $obj->rowid, 'rowid' => $obj->rowid, 'code' => $obj->code, 'label' => $obj->label, 'affect' => $obj->affect, 'delay' => $obj->delay, 'newbymonth' => $obj->newbymonth);
2303 }
2304
2305 return $types;
2306 }
2307 } else {
2308 dol_print_error($this->db);
2309 }
2310
2311 return array();
2312 }
2313
2314
2321 public function info($id)
2322 {
2323 global $conf;
2324
2325 $sql = "SELECT f.rowid, f.statut as status,";
2326 $sql .= " f.date_create as datec,";
2327 $sql .= " f.tms as date_modification,";
2328 $sql .= " f.date_valid as datev,";
2329 $sql .= " f.date_approval as datea,";
2330 $sql .= " f.date_refuse as dater,";
2331 $sql .= " f.fk_user_create as fk_user_creation,";
2332 $sql .= " f.fk_user_modif as fk_user_modification,";
2333 $sql .= " f.fk_user_valid as fk_user_validation,";
2334 $sql .= " f.fk_user_approve as fk_user_approval_done,";
2335 $sql .= " f.fk_validator as fk_user_approval_expected,";
2336 $sql .= " f.fk_user_refuse as fk_user_refuse";
2337 $sql .= " FROM ".MAIN_DB_PREFIX."holiday as f";
2338 $sql .= " WHERE f.rowid = ".((int) $id);
2339 $sql .= " AND f.entity = ".$conf->entity;
2340
2341 $resql = $this->db->query($sql);
2342 if ($resql) {
2343 if ($this->db->num_rows($resql)) {
2344 $obj = $this->db->fetch_object($resql);
2345
2346 $this->id = $obj->rowid;
2347
2348 $this->date_creation = $this->db->jdate($obj->datec);
2349 $this->date_modification = $this->db->jdate($obj->date_modification);
2350 $this->date_validation = $this->db->jdate($obj->datev);
2351 $this->date_approval = $this->db->jdate($obj->datea);
2352
2353 $this->user_creation_id = $obj->fk_user_creation;
2354 $this->user_validation_id = $obj->fk_user_validation;
2355 $this->user_modification_id = $obj->fk_user_modification;
2356
2357 if ($obj->status == Holiday::STATUS_APPROVED || $obj->status == Holiday::STATUS_CANCELED) {
2358 if ($obj->fk_user_approval_done) {
2359 $this->fk_user_approve = $obj->fk_user_approval_done;
2360 }
2361 }
2362 }
2363 $this->db->free($resql);
2364 } else {
2365 dol_print_error($this->db);
2366 }
2367 }
2368
2369
2377 public function initAsSpecimen()
2378 {
2379 global $user, $langs;
2380
2381 // Initialise parameters
2382 $this->id = 0;
2383 $this->specimen = 1;
2384
2385 $this->fk_user = $user->id;
2386 $this->description = 'SPECIMEN description';
2387 $this->date_debut = dol_now();
2388 $this->date_fin = dol_now() + (24 * 3600);
2389 $this->date_valid = dol_now();
2390 $this->fk_validator = $user->id;
2391 $this->halfday = 0;
2392 $this->fk_type = 1;
2394
2395 return 1;
2396 }
2397
2403 public function loadStateBoard()
2404 {
2405 global $user;
2406
2407 $this->nb = array();
2408
2409 $sql = "SELECT count(h.rowid) as nb";
2410 $sql .= " FROM ".MAIN_DB_PREFIX."holiday as h";
2411 $sql .= " WHERE h.statut > 1";
2412 $sql .= " AND h.entity IN (".getEntity('holiday').")";
2413 if (!$user->hasRight('expensereport', 'readall')) {
2414 $userchildids = $user->getAllChildIds(1);
2415 $sql .= " AND (h.fk_user IN (".$this->db->sanitize(implode(',', $userchildids)).")";
2416 $sql .= " OR h.fk_validator IN (".$this->db->sanitize(implode(',', $userchildids))."))";
2417 }
2418
2419 $resql = $this->db->query($sql);
2420 if ($resql) {
2421 while ($obj = $this->db->fetch_object($resql)) {
2422 $this->nb["holidays"] = $obj->nb;
2423 }
2424 $this->db->free($resql);
2425 return 1;
2426 } else {
2427 dol_print_error($this->db);
2428 $this->error = $this->db->error();
2429 return -1;
2430 }
2431 }
2432
2433 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
2440 public function load_board($user)
2441 {
2442 // phpcs:enable
2443 global $conf, $langs;
2444
2445 if ($user->socid) {
2446 return -1; // protection pour eviter appel par utilisateur externe
2447 }
2448
2449 $now = dol_now();
2450
2451 $sql = "SELECT h.rowid, h.date_debut";
2452 $sql .= " FROM ".MAIN_DB_PREFIX."holiday as h";
2453 $sql .= " WHERE h.statut = 2";
2454 $sql .= " AND h.entity IN (".getEntity('holiday').")";
2455 if (!$user->hasRight('expensereport', 'read_all')) {
2456 $userchildids = $user->getAllChildIds(1);
2457 $sql .= " AND (h.fk_user IN (".$this->db->sanitize(implode(',', $userchildids)).")";
2458 $sql .= " OR h.fk_validator IN (".$this->db->sanitize(implode(',', $userchildids))."))";
2459 }
2460
2461 $resql = $this->db->query($sql);
2462 if ($resql) {
2463 $langs->load("members");
2464
2465 $response = new WorkboardResponse();
2466 $response->warning_delay = $conf->holiday->approve->warning_delay / 60 / 60 / 24;
2467 $response->label = $langs->trans("HolidaysToApprove");
2468 $response->labelShort = $langs->trans("ToApprove");
2469 $response->url = DOL_URL_ROOT.'/holiday/list.php?search_status=2&amp;mainmenu=hrm&amp;leftmenu=holiday';
2470 $response->img = img_object('', "holiday");
2471
2472 while ($obj = $this->db->fetch_object($resql)) {
2473 $response->nbtodo++;
2474
2475 if ($this->db->jdate($obj->date_debut) < ($now - $conf->holiday->approve->warning_delay)) {
2476 $response->nbtodolate++;
2477 }
2478 }
2479
2480 return $response;
2481 } else {
2482 dol_print_error($this->db);
2483 $this->error = $this->db->error();
2484 return -1;
2485 }
2486 }
2494 public function getKanbanView($option = '', $arraydata = null)
2495 {
2496 global $langs;
2497
2498 $selected = (empty($arraydata['selected']) ? 0 : $arraydata['selected']);
2499
2500 $return = '<div class="box-flex-item box-flex-grow-zero">';
2501 $return .= '<div class="info-box info-box-sm">';
2502 $return .= '<span class="info-box-icon bg-infobox-action">';
2503 $return .= img_picto('', $this->picto);
2504 $return .= '</span>';
2505 $return .= '<div class="info-box-content">';
2506 $return .= '<span class="info-box-ref inline-block tdoverflowmax150 valignmiddle">'.$arraydata['user']->getNomUrl(-1).'</span>';
2507 if ($selected >= 0) {
2508 $return .= '<input id="cb'.$this->id.'" class="flat checkforselect fright" type="checkbox" name="toselect[]" value="'.$this->id.'"'.($selected ? ' checked="checked"' : '').'>';
2509 }
2510 if (property_exists($this, 'fk_type')) {
2511 $return .= '<br>';
2512 //$return .= '<span class="opacitymedium">'.$langs->trans("Type").'</span> : ';
2513 $return .= '<div class="info_box-label tdoverflowmax100" title="'.dol_escape_htmltag($arraydata['labeltype']).'">'.dol_escape_htmltag($arraydata['labeltype']).'</div>';
2514 }
2515 if (property_exists($this, 'date_debut') && property_exists($this, 'date_fin')) {
2516 $return .= '<span class="info-box-label small">'.dol_print_date($this->date_debut, 'day').'</span>';
2517 $return .= ' <span class="opacitymedium small">'.$langs->trans("To").'</span> ';
2518 $return .= '<span class="info-box-label small">'.dol_print_date($this->date_fin, 'day').'</span>';
2519 if (!empty($arraydata['nbopenedday'])) {
2520 $return .= ' ('.$arraydata['nbopenedday'].')';
2521 }
2522 }
2523 if (method_exists($this, 'getLibStatut')) {
2524 $return .= '<div class="info-box-status">'.$this->getLibStatut(3).'</div>';
2525 }
2526 $return .= '</div>';
2527 $return .= '</div>';
2528 $return .= '</div>';
2529 return $return;
2530 }
2531}
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:637
ajax_combobox($htmlname, $events=array(), $minLengthToAutocomplete=0, $forcefocus=0, $widthTypeOfAutocomplete='resolve', $idforemptyvalue='-1', $morecss='')
Convert a html select field into an ajax combobox.
Definition ajax.lib.php:456
$object ref
Definition info.php:79
Parent class of all other business classes (invoices, contracts, proposals, orders,...
fetch_optionals($rowid=null, $optionsArray=null)
Function to get extra fields of an object into $this->array_options This method is in most cases call...
insertExtraFields($trigger='', $userused=null)
Add/Update all extra fields values for the current object.
call_trigger($triggerName, $user)
Call trigger based on this instance.
Class of the module paid holiday.
getTypes($active=-1, $affect=-1)
Return array with list of types.
getNomUrl($withpicto=0, $save_lastsearch_value=-1, $notooltip=0, $morecss='')
Return clicable name (with picto eventually)
verifDateHolidayCP($fk_user, $dateStart, $dateEnd, $halfday=0)
Check if a user is on holiday (partially or completely) into a period.
validate($user=null, $notrigger=0)
Validate leave request.
info($id)
Load information on object.
updateBalance()
Update balance of vacations and check table of users for holidays is complete.
updateConfCP($name, $value)
Met à jour une option du module Holiday Payés.
const STATUS_VALIDATED
Validated status.
const STATUS_DRAFT
Draft status.
fetch($id, $ref='')
Load object in memory from database.
addLogCP($fk_user_action, $fk_user_update, $label, $new_solde, $fk_type)
addLogCP
verifNbUsers($userDolibarrWithoutCP, $userCP)
Compare le nombre d'utilisateur actif de Dolibarr à celui des utilisateurs des congés payés.
verifDateHolidayForTimestamp($fk_user, $timestamp, $status='-1')
Check that a user is not on holiday for a particular timestamp.
approve($user=null, $notrigger=0)
Approve leave request.
getNextNumRef($objsoc)
Returns the reference to the following non used Order depending on the active numbering module define...
const STATUS_REFUSED
Refused.
getConfCP($name, $createifnotfound='')
Return value of a conf parameter for leave module TODO Move this into llx_const table.
load_board($user)
Load indicators for dashboard (this->nbtodo and this->nbtodolate)
initAsSpecimen()
Initialise an instance with random values.
create($user, $notrigger=0)
Créer un congés payés dans la base de données.
selectStatutCP($selected=0, $htmlname='select_statut', $morecss='minwidth125')
Show select with list of leave status.
countActiveUsersWithoutCP()
Compte le nombre d'utilisateur actifs dans Dolibarr sans CP.
updateSoldeCP($userID=0, $nbHoliday=0, $fk_type=0)
Met à jour le timestamp de la dernière mise à jour du solde des CP.
fetchLog($order, $filter)
Liste le log des congés payés.
update($user=null, $notrigger=0)
Update database.
getCPforUser($user_id, $fk_type=0)
Return the balance of annual leave of a user.
fetch_users_approver_holiday()
Return list of people with permission to validate leave requests.
__construct($db)
Constructor.
loadStateBoard()
Load this->nb for dashboard.
getLibStatut($mode=0)
Returns the label status.
createCPusers($single=false, $userid=0)
Create entries for each user at setup step.
fetchAll($order, $filter)
List all holidays of all users.
const STATUS_CANCELED
Canceled.
countActiveUsers()
Compte le nombre d'utilisateur actifs dans Dolibarr.
fetchByUser($user_id, $order='', $filter='')
List holidays for a particular user or list of users.
const STATUS_APPROVED
Approved.
getTooltipContentArray($params)
getTooltipContentArray
fetchUsers($stringlist=true, $type=true, $filters='')
Get list of Users or list of vacation balance.
getKanbanView($option='', $arraydata=null)
Return clicable link of object (with eventually picto)
LibStatut($status, $mode=0, $startdate='')
Returns the label of a status.
print $script_file $mode $langs defaultlang(is_numeric($duration_value) ? " delay=". $duration_value :"").(is_numeric($duration_value2) ? " after cd cd cd description as description
Only used if Module[ID]Desc translation string is not found.
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)
price2num($amount, $rounding='', $option=0)
Function that return a number with universal decimal format (decimal separator is '.
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs=null, $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
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...
getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
getDictionaryValue($tablename, $field, $id, $checkentity=false, $rowidfield='rowid')
Return the value of a filed into a dictionary for the record $id.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Returns text escaped for inclusion in HTML alt or title or value tags, or into values of HTML input f...
publicphonebutton2 phonegreen basiclayout basiclayout TotalHT VATCode TotalVAT TotalLT1 TotalLT2 TotalTTC TotalHT clearboth nowraponall TAKEPOS_SHOW_SUBPRICE right right right takeposterminal SELECT e e e e e statut
Definition invoice.php:2010