dolibarr 23.0.3
fichinter.class.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2002-2003 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2004-2014 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2005-2012 Regis Houssin <regis.houssin@inodbox.com>
5 * Copyright (C) 2011-2020 Juanjo Menent <jmenent@2byte.es>
6 * Copyright (C) 2015 Marcos García <marcosgdf@gmail.com>
7 * Copyright (C) 2015-2025 Charlene Benke <charlene@patas-monkey.com>
8 * Copyright (C) 2018 Nicolas ZABOURI <info@inovea-conseil.com>
9 * Copyright (C) 2018-2025 Frédéric France <frederic.france@free.fr>
10 * Copyright (C) 2023-2024 William Mead <william.mead@manchenumerique.fr>
11 * Copyright (C) 2024-2025 MDW <mdeweerd@users.noreply.github.com>
12 *
13 * This program is free software; you can redistribute it and/or modify
14 * it under the terms of the GNU General Public License as published by
15 * the Free Software Foundation; either version 3 of the License, or
16 * (at your option) any later version.
17 *
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
22 *
23 * You should have received a copy of the GNU General Public License
24 * along with this program. If not, see <https://www.gnu.org/licenses/>.
25 */
26
32require_once DOL_DOCUMENT_ROOT.'/core/class/commonobject.class.php';
33require_once DOL_DOCUMENT_ROOT.'/fichinter/class/fichinterligne.class.php';
34require_once DOL_DOCUMENT_ROOT.'/core/class/commonsignedobject.class.php';
35require_once DOL_DOCUMENT_ROOT.'/subtotals/class/commonsubtotal.class.php';
36
37
44{
45 use CommonSignedObject, CommonSubtotal;
46
51 public $TRIGGER_PREFIX = 'FICHINTER';
52
53 public $fields = array(
54 'rowid' => array('type' => 'integer', 'label' => 'TechnicalID', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 10),
55 'fk_soc' => array('type' => 'integer:Societe:societe/class/societe.class.php', 'label' => 'ThirdParty', 'enabled' => 'isModEnabled("societe")', 'visible' => -1, 'notnull' => 1, 'position' => 15),
56 'fk_projet' => array('type' => 'integer:Project:projet/class/project.class.php:1:(fk_statut:=:1)', 'label' => 'Project', 'enabled' => 'isModEnabled("project")', 'visible' => -1, 'position' => 20),
57 'fk_contrat' => array('type' => 'integer:Contrat:contrat/class/contrat.class.php', 'label' => 'Contract', 'enabled' => 'isModEnabled("contract")', 'visible' => -1, 'position' => 25),
58 'ref' => array('type' => 'varchar(30)', 'label' => 'Ref', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'showoncombobox' => 1, 'position' => 30),
59 'ref_ext' => array('type' => 'varchar(255)', 'label' => 'RefExt', 'enabled' => 1, 'visible' => 0, 'position' => 35),
60 'ref_client' => array('type' => 'varchar(255)', 'label' => 'RefCustomer', 'enabled' => 1, 'visible' => -1, 'position' => 36),
61 'entity' => array('type' => 'integer', 'label' => 'Entity', 'default' => '1', 'enabled' => 1, 'visible' => -2, 'notnull' => 1, 'position' => 40, 'index' => 1),
62 'tms' => array('type' => 'timestamp', 'label' => 'DateModification', 'enabled' => 1, 'visible' => -1, 'notnull' => 1, 'position' => 45),
63 'datec' => array('type' => 'datetime', 'label' => 'DateCreation', 'enabled' => 1, 'visible' => -1, 'position' => 50),
64 'date_valid' => array('type' => 'datetime', 'label' => 'DateValidation', 'enabled' => 1, 'visible' => -1, 'position' => 55),
65 'datei' => array('type' => 'date', 'label' => 'Datei', 'enabled' => 1, 'visible' => -1, 'position' => 60),
66 'fk_user_author' => array('type' => 'integer:User:user/class/user.class.php', 'label' => 'UserAuthor', 'enabled' => 1, 'visible' => -1, 'position' => 65),
67 'fk_user_modif' => array('type' => 'integer:User:user/class/user.class.php', 'label' => 'UserModif', 'enabled' => 1, 'visible' => -2, 'notnull' => -1, 'position' => 70),
68 'fk_user_valid' => array('type' => 'integer:User:user/class/user.class.php', 'label' => 'UserValidation', 'enabled' => 1, 'visible' => -1, 'position' => 75),
69 'dateo' => array('type' => 'date', 'label' => 'Dateo', 'enabled' => 1, 'visible' => -1, 'position' => 85),
70 'datee' => array('type' => 'date', 'label' => 'Datee', 'enabled' => 1, 'visible' => -1, 'position' => 90),
71 'datet' => array('type' => 'date', 'label' => 'Datet', 'enabled' => 1, 'visible' => -1, 'position' => 95),
72 'duree' => array('type' => 'integer', 'label' => 'Duree', 'enabled' => 1, 'visible' => -1, 'position' => 100),
73 'signed_status' => array('type' => 'smallint(6)', 'label' => 'SignedStatus', 'enabled' => 1, 'visible' => -1, 'position' => 101, 'arrayofkeyval' => array(0 => 'NoSignature', 1 => 'SignedSender', 2 => 'SignedReceiver', 3 => 'SignedReceiverOnline', 9 => 'SignedAll')),
74 'description' => array('type' => 'html', 'label' => 'Description', 'enabled' => 1, 'visible' => -1, 'position' => 105, 'showoncombobox' => 2),
75 'note_private' => array('type' => 'html', 'label' => 'NotePrivate', 'enabled' => 1, 'visible' => 0, 'position' => 110),
76 'note_public' => array('type' => 'html', 'label' => 'NotePublic', 'enabled' => 1, 'visible' => 0, 'position' => 115),
77 'model_pdf' => array('type' => 'varchar(255)', 'label' => 'PDFTemplate', 'enabled' => 1, 'visible' => 0, 'position' => 120),
78 'last_main_doc' => array('type' => 'varchar(255)', 'label' => 'LastMainDoc', 'enabled' => 1, 'visible' => -1, 'position' => 125),
79 'import_key' => array('type' => 'varchar(14)', 'label' => 'ImportId', 'enabled' => 1, 'visible' => -2, 'position' => 130),
80 'extraparams' => array('type' => 'varchar(255)', 'label' => 'Extraparams', 'enabled' => 1, 'visible' => -1, 'position' => 135),
81 'fk_statut' => array('type' => 'integer', 'label' => 'Status', 'enabled' => 1, 'visible' => -1, 'position' => 500),
82 );
83
87 public $element = 'fichinter';
88
92 public $fk_element = 'fk_fichinter';
93
97 public $table_element = 'fichinter';
98
102 public $table_element_line = 'fichinterdet';
103
107 public $class_element_line = 'FichinterLigne';
108
112 public $picto = 'intervention';
113
117 protected $table_ref_field = 'ref';
118
122 public $socid;
123
127 public $author;
128
132 public $datec;
133
137 public $datev;
141 public $dateo;
145 public $datee;
146
150 public $datet;
151
157 public $datem;
158
162 public $duration;
163
168 public $statut = 0; // 0=draft, 1=validated, 2=invoiced, 3=Terminate
169
173 public $status = 0; // 0=draft, 1=validated, 2=invoiced, 3=Terminate
174
178 public $description;
179
183 public $fk_contrat = 0;
184
188 public $fk_project;
189
194 public $ref_client;
195
199 public $extraparams = array();
200
204 public $lines = array();
205
209 const STATUS_DRAFT = 0;
210
215
219 const STATUS_BILLED = 2;
220
224 const STATUS_CLOSED = 3;
225
231 public $date_delivery;
232
237 public $delivery_date_receipt;
238
243 public $user_author_id;
244
245
251 public function __construct($db)
252 {
253 $this->db = $db;
254 }
255
261 public function loadStateBoard()
262 {
263 global $user;
264
265 $this->nb = array();
266 $clause = "WHERE";
267
268 $sql = "SELECT count(fi.rowid) as nb";
269 $sql .= " FROM ".MAIN_DB_PREFIX."fichinter as fi";
270 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."societe as s ON fi.fk_soc = s.rowid";
271 if (!$user->hasRight('societe', 'client', 'voir')) {
272 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."societe_commerciaux as sc ON s.rowid = sc.fk_soc";
273 $sql .= " WHERE sc.fk_user = ".((int) $user->id);
274 $clause = "AND";
275 }
276 $sql .= " ".$clause." fi.entity IN (".getEntity('intervention').")";
277
278 $resql = $this->db->query($sql);
279 if ($resql) {
280 while ($obj = $this->db->fetch_object($resql)) {
281 $this->nb["interventions"] = $obj->nb;
282 }
283 $this->db->free($resql);
284 return 1;
285 } else {
286 dol_print_error($this->db);
287 $this->error = $this->db->error();
288 return -1;
289 }
290 }
291
299 public function create($user, $notrigger = 0)
300 {
301 $error = 0;
302
303 dol_syslog(get_class($this)."::create ref=".$this->ref);
304
305 // Check parameters
306 if (!empty($this->ref)) { // We check that ref is not already used
307 $result = self::isExistingObject($this->element, 0, $this->ref); // Check ref is not yet used
308 if ($result > 0) {
309 $this->error = 'ErrorRefAlreadyExists';
310 dol_syslog(get_class($this)."::create ".$this->error, LOG_WARNING);
311 $this->db->rollback();
312 return -1;
313 }
314 }
315 if (!is_numeric($this->duration)) {
316 $this->duration = 0;
317 }
318 if (!empty($this->ref_client)) {
319 $this->ref_client = trim($this->ref_client);
320 }
321
322 if ($this->socid <= 0) {
323 $this->error = 'ErrorFicheinterCompanyDoesNotExist';
324 dol_syslog(get_class($this)."::create ".$this->error, LOG_ERR);
325 return -1;
326 }
327 $this->entity = setEntity($this);
328
329 $soc = new Societe($this->db);
330 $result = $soc->fetch($this->socid);
331
332 $now = dol_now();
333
334 $this->db->begin();
335
336 $sql = "INSERT INTO ".MAIN_DB_PREFIX."fichinter (";
337 $sql .= "fk_soc";
338 $sql .= ", datec";
339 $sql .= ", ref";
340 $sql .= ", ref_client";
341 $sql .= ", entity";
342 $sql .= ", fk_user_author";
343 $sql .= ", fk_user_modif";
344 $sql .= ", description";
345 $sql .= ", model_pdf";
346 $sql .= ", fk_projet";
347 $sql .= ", fk_contrat";
348 $sql .= ", fk_statut";
349 $sql .= ", signed_status";
350 $sql .= ", note_private";
351 $sql .= ", note_public";
352 $sql .= ") ";
353 $sql .= " VALUES (";
354 $sql .= $this->socid;
355 $sql .= ", '".$this->db->idate($now)."'";
356 $sql .= ", '".$this->db->escape($this->ref)."'";
357 $sql .= ", ".($this->ref_client ? "'".$this->db->escape($this->ref_client)."'" : "null");
358 $sql .= ", ".((int) $this->entity);
359 $sql .= ", ".((int) $user->id);
360 $sql .= ", ".((int) $user->id);
361 $sql .= ", ".($this->description ? "'".$this->db->escape($this->description)."'" : "null");
362 $sql .= ", '".$this->db->escape($this->model_pdf)."'";
363 $sql .= ", ".((int) $this->fk_project > 0 ? ((int) $this->fk_project) : 0);
364 $sql .= ", ".((int) $this->fk_contrat > 0 ? ((int) $this->fk_contrat) : 0);
365 $sql .= ", ".((int) $this->status);
366 $sql .= ", ".((int) $this->signed_status);
367 $sql .= ", ".($this->note_private ? "'".$this->db->escape($this->note_private)."'" : "null");
368 $sql .= ", ".($this->note_public ? "'".$this->db->escape($this->note_public)."'" : "null");
369 $sql .= ")";
370
371 dol_syslog(get_class($this)."::create", LOG_DEBUG);
372 $result = $this->db->query($sql);
373 if ($result) {
374 $this->id = $this->db->last_insert_id(MAIN_DB_PREFIX."fichinter");
375
376 if ($this->id) {
377 $this->ref = '(PROV'.$this->id.')';
378 $sql = 'UPDATE '.MAIN_DB_PREFIX."fichinter SET ref='".$this->db->escape($this->ref)."' WHERE rowid=".((int) $this->id);
379
380 dol_syslog(get_class($this)."::create", LOG_DEBUG);
381 $resql = $this->db->query($sql);
382 if (!$resql) {
383 $error++;
384 }
385 }
386
387 if (!$error) {
388 $result = $this->insertExtraFields();
389 if ($result < 0) {
390 $error++;
391 }
392 }
393
394 // Add linked object
395 if (!$error && $this->origin && $this->origin_id) {
396 $ret = $this->add_object_linked();
397 if (!$ret) {
398 dol_print_error($this->db);
399 }
400 }
401
402
403 if (!$error && !$notrigger) {
404 // Call trigger
405 $result = $this->call_trigger('FICHINTER_CREATE', $user);
406 if ($result < 0) {
407 $error++;
408 }
409 // End call triggers
410 }
411
412 if (!$error) {
413 $this->db->commit();
414 return $this->id;
415 } else {
416 $this->db->rollback();
417 $this->error = implode(',', $this->errors);
418 dol_syslog(get_class($this)."::create ".$this->error, LOG_ERR);
419 return -1;
420 }
421 } else {
422 $this->error = $this->db->error();
423 $this->db->rollback();
424 return -1;
425 }
426 }
427
435 public function update($user, $notrigger = 0)
436 {
437 global $conf;
438
439 if (!is_numeric($this->duration)) {
440 $this->duration = 0;
441 }
442 if (!dol_strlen((string) $this->fk_project)) {
443 $this->fk_project = 0;
444 }
445 if (!empty($this->ref_client)) {
446 $this->ref_client = trim($this->ref_client);
447 }
448
449 $error = 0;
450
451 $this->db->begin();
452
453 $sql = "UPDATE ".MAIN_DB_PREFIX."fichinter SET ";
454 $sql .= "description = '".$this->db->escape($this->description)."'";
455 $sql .= ", duree = ".((int) $this->duration);
456 $sql .= ", ref_client = ".($this->ref_client ? "'".$this->db->escape($this->ref_client)."'" : "null");
457 if ((int) $this->fk_project > 0) {
458 $sql .= ", fk_projet = ".((int) $this->fk_project);
459 }
460 if (isset($this->datec)) {
461 $sql .= ", datec = ".($this->datec ? "'".$this->db->idate($this->datec)."'" : "null");
462 }
463 if (isset($this->datev)) {
464 $sql .= ", date_valid = ".($this->datev ? "'".$this->db->idate($this->datev)."'" : "null");
465 }
466 if (isset($this->datet)) {
467 $sql .= ", datet = ".($this->datet ? "'".$this->db->idate($this->datet)."'" : "null");
468 }
469 $sql .= ", note_private = ".($this->note_private ? "'".$this->db->escape($this->note_private)."'" : "null");
470 $sql .= ", note_public = ".($this->note_public ? "'".$this->db->escape($this->note_public)."'" : "null");
471 $sql .= ", fk_user_modif = ".((int) $user->id);
472 $sql .= " WHERE rowid = ".((int) $this->id);
473
474 dol_syslog(get_class($this)."::update", LOG_DEBUG);
475 if ($this->db->query($sql)) {
476 $result = $this->insertExtraFields();
477 if ($result < 0) {
478 $error++;
479 }
480
481 if (!$error && !$notrigger) {
482 // Call trigger
483 $result = $this->call_trigger('FICHINTER_MODIFY', $user);
484 if ($result < 0) {
485 $error++;
486 $this->db->rollback();
487 return -1;
488 }
489 // End call triggers
490 }
491
492 $this->db->commit();
493 return 1;
494 } else {
495 $this->error = $this->db->error();
496 $this->db->rollback();
497 return -1;
498 }
499 }
500
509 public function fetch($rowid, $ref = '', $ref_ext = '')
510 {
511 $sql = "SELECT f.rowid, f.ref, f.ref_client, f.description, f.fk_soc, f.fk_statut as status, f.signed_status,";
512 $sql .= " f.datec, f.dateo, f.datee, f.datet, f.fk_user_author,";
513 $sql .= " f.date_valid as datev,";
514 $sql .= " f.tms as datem,";
515 $sql .= " f.duree, f.fk_projet as fk_project, f.note_public, f.note_private, f.model_pdf, f.last_main_doc, f.extraparams, fk_contrat, f.entity as entity";
516 $sql .= " FROM ".MAIN_DB_PREFIX."fichinter as f";
517 $sql .= " WHERE f.entity IN (".getEntity('intervention').")";
518 if ($ref) {
519 $sql .= " AND f.ref = '".$this->db->escape($ref)."'";
520 } elseif ($ref_ext) {
521 $sql .= " AND f.ref_ext = '".$this->db->escape($ref_ext)."'";
522 } else {
523 $sql .= " AND f.rowid = ".((int) $rowid);
524 }
525
526 $resql = $this->db->query($sql);
527 if ($resql) {
528 if ($this->db->num_rows($resql)) {
529 $obj = $this->db->fetch_object($resql);
530
531 $this->id = $obj->rowid;
532 $this->ref = $obj->ref;
533 $this->ref_client = $obj->ref_client;
534 $this->description = $obj->description;
535 $this->socid = $obj->fk_soc;
536 $this->status = $obj->status;
537 $this->statut = $obj->status; // deprecated
538 $this->signed_status = $obj->signed_status;
539 $this->duration = $obj->duree;
540 $this->datec = $this->db->jdate($obj->datec);
541 $this->dateo = $this->db->jdate($obj->dateo);
542 $this->datee = $this->db->jdate($obj->datee);
543 $this->datet = $this->db->jdate($obj->datet);
544 $this->datev = $this->db->jdate($obj->datev);
545 $this->datem = $this->db->jdate($obj->datem);
546 $this->fk_project = $obj->fk_project;
547 $this->note_public = $obj->note_public;
548 $this->note_private = $obj->note_private;
549 $this->model_pdf = $obj->model_pdf;
550 $this->fk_contrat = $obj->fk_contrat;
551 $this->entity = $obj->entity;
552
553 $this->user_creation_id = $obj->fk_user_author;
554
555 $this->extraparams = is_null($obj->extraparams) ? [] : (array) json_decode($obj->extraparams, true);
556
557 $this->last_main_doc = $obj->last_main_doc;
558
559 // Retrieve extrafields
560 $this->fetch_optionals();
561
562 /*
563 * Lines
564 */
565 $result = $this->fetch_lines();
566 if ($result < 0) {
567 return -3;
568 }
569 $this->db->free($resql);
570 return 1;
571 }
572
573 return 0;
574 } else {
575 $this->error = $this->db->lasterror();
576 return -1;
577 }
578 }
579
586 public function setDraft($user)
587 {
588 $error = 0;
589
590 // Protection
591 if ($this->status <= self::STATUS_DRAFT) {
592 return 0;
593 }
594
595 dol_syslog(get_class($this)."::setDraft", LOG_DEBUG);
596
597 $this->oldcopy = dol_clone($this, 2);
598
599 $this->db->begin();
600
601 $sql = "UPDATE ".MAIN_DB_PREFIX."fichinter";
602 $sql .= " SET fk_statut = ".self::STATUS_DRAFT;
603 $sql .= " WHERE rowid = ".((int) $this->id);
604
605 $resql = $this->db->query($sql);
606 if ($resql) {
607 // Call trigger
608 $result = $this->call_trigger('FICHINTER_UNVALIDATE', $user);
609 if ($result < 0) {
610 $error++;
611 }
612
613 if (!$error) {
614 $this->status = self::STATUS_DRAFT;
615 $this->statut = self::STATUS_DRAFT; // deprecated
616 $this->db->commit();
617 return 1;
618 } else {
619 $this->db->rollback();
620 return -1;
621 }
622 } else {
623 $this->db->rollback();
624 $this->error = $this->db->lasterror();
625 return -1;
626 }
627 }
628
636 public function setValid($user, $notrigger = 0)
637 {
638 global $conf;
639 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
640
641 $error = 0;
642
643 if ($this->status != self::STATUS_VALIDATED) {
644 $this->db->begin();
645
646 $now = dol_now();
647
648 // Define new ref
649 if ((preg_match('/^[\‍(]?PROV/i', $this->ref) || empty($this->ref))) { // empty should not happened, but when it occurs, the test save life
650 $num = $this->getNextNumRef($this->thirdparty);
651 } else {
652 $num = (string) $this->ref;
653 }
654 $this->newref = dol_sanitizeFileName($num);
655
656 $sql = "UPDATE ".MAIN_DB_PREFIX."fichinter";
657 $sql .= " SET fk_statut = 1";
658 $sql .= ", ref = '".$this->db->escape($num)."'";
659 $sql .= ", date_valid = '".$this->db->idate($now)."'";
660 $sql .= ", fk_user_valid = ".($user->id > 0 ? (int) $user->id : "null");
661 $sql .= " WHERE rowid = ".((int) $this->id);
662 $sql .= " AND entity = ".((int) $this->entity);
663
664 $sql .= " AND fk_statut = 0";
665
666 dol_syslog(get_class($this)."::setValid", LOG_DEBUG);
667 $resql = $this->db->query($sql);
668 if (!$resql) {
669 dol_print_error($this->db);
670 $error++;
671 }
672
673 if (!$error && !$notrigger) {
674 // Call trigger
675 $result = $this->call_trigger('FICHINTER_VALIDATE', $user);
676 if ($result < 0) {
677 $error++;
678 }
679 // End call triggers
680 }
681
682 if (!$error) {
683 $this->oldref = $this->ref;
684
685 // Rename directory if dir was a temporary ref
686 if (preg_match('/^[\‍(]?PROV/i', $this->ref)) {
687 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
688
689 // Now we rename also files into index
690 $sql = 'UPDATE '.MAIN_DB_PREFIX."ecm_files set filename = CONCAT('".$this->db->escape($this->newref)."', SUBSTR(filename, ".(strlen($this->ref) + 1).")), filepath = 'ficheinter/".$this->db->escape($this->newref)."'";
691 $sql .= " WHERE filename LIKE '".$this->db->escape($this->ref)."%' AND filepath = 'ficheinter/".$this->db->escape($this->ref)."' and entity = ".((int) $this->entity);
692 $resql = $this->db->query($sql);
693 if (!$resql) {
694 $error++;
695 $this->error = $this->db->lasterror();
696 }
697 $sql = 'UPDATE '.MAIN_DB_PREFIX."ecm_files set filepath = 'ficheinter/".$this->db->escape($this->newref)."'";
698 $sql .= " WHERE filepath = 'ficheinter/".$this->db->escape($this->ref)."' and entity = ".$conf->entity;
699 $resql = $this->db->query($sql);
700 if (!$resql) {
701 $error++;
702 $this->error = $this->db->lasterror();
703 }
704
705 // We rename directory ($this->ref = old ref, $num = new ref) in order not to lose the attachments
706 $oldref = dol_sanitizeFileName($this->ref);
707 $newref = dol_sanitizeFileName($num);
708 $dirsource = $conf->ficheinter->dir_output.'/'.$oldref;
709 $dirdest = $conf->ficheinter->dir_output.'/'.$newref;
710 if (!$error && file_exists($dirsource)) {
711 dol_syslog(get_class($this)."::setValid rename dir ".$dirsource." into ".$dirdest);
712
713 if (@rename($dirsource, $dirdest)) {
714 dol_syslog("Rename ok");
715 // Rename docs starting with $oldref with $newref
716 $listoffiles = dol_dir_list($conf->ficheinter->dir_output.'/'.$newref, 'files', 1, '^'.preg_quote($oldref, '/'));
717 foreach ($listoffiles as $fileentry) {
718 $dirsource = $fileentry['name'];
719 $dirdest = preg_replace('/^'.preg_quote($oldref, '/').'/', $newref, $dirsource);
720 $dirsource = $fileentry['path'].'/'.$dirsource;
721 $dirdest = $fileentry['path'].'/'.$dirdest;
722 @rename($dirsource, $dirdest);
723 }
724 }
725 }
726 }
727 }
728
729 // Set new ref and define current status
730 if (!$error) {
731 $this->ref = $num;
733 $this->statut = self::STATUS_VALIDATED; // deprecated
734 $this->date_validation = $now;
735 $this->db->commit();
736 return 1;
737 } else {
738 $this->db->rollback();
739 dol_syslog(get_class($this)."::setValid ".$this->error, LOG_ERR);
740 return -1;
741 }
742 }
743
744 return 0;
745 }
746
754 public function setClose($user, $notrigger = 0)
755 {
756 global $conf;
757
758 $error = 0;
759
760 if ($this->status == self::STATUS_CLOSED) {
761 return 0;
762 } else {
763 $this->db->begin();
764
765 $now = dol_now();
766
767 $sql = 'UPDATE ' . MAIN_DB_PREFIX . $this->table_element;
768 $sql .= ' SET fk_statut = ' . self::STATUS_CLOSED . ',';
769 $sql .= " datet = '" . $this->db->idate($now) . "',";
770 $sql .= " fk_user_modif = " . ((int) $user->id);
771 $sql .= " WHERE rowid = " . ((int) $this->id);
772 $sql .= " AND fk_statut > " . self::STATUS_DRAFT;
773 $sql .= " AND entity = " . ((int) $conf->entity);
774
775 if ($this->db->query($sql)) {
776 if (!$notrigger) {
777 // Call trigger
778 $result = $this->call_trigger('FICHINTER_CLOSE', $user);
779 if ($result < 0) {
780 $error++;
781 }
782 // End call triggers
783 }
784
785 if (!$error) {
787 $this->statut = self::STATUS_CLOSED; // deprecated
788 $this->db->commit();
789 return 1;
790 } else {
791 $this->db->rollback();
792 return -1;
793 }
794 } else {
795 $this->error = $this->db->lasterror();
796 $this->db->rollback();
797 return -1;
798 }
799 }
800 }
801
807 public function getAmount()
808 {
809 $amount = 0;
810
811 $this->author = new User($this->db);
812 $this->author->fetch($this->user_creation_id);
813
814 $thm = $this->author->thm;
815
816 foreach ($this->lines as $line) {
817 $amount += ($line->duration / 60 / 60 * (float) $thm);
818 }
819
820 return (float) price2num($amount, 'MT');
821 }
822
823
835 public function generateDocument($modele, $outputlangs, $hidedetails = 0, $hidedesc = 0, $hideref = 0, $moreparams = null)
836 {
837 global $conf;
838
839 $outputlangs->load("interventions");
840
841 if (!dol_strlen($modele)) {
842 $modele = 'soleil';
843
844 if (!empty($this->model_pdf)) {
845 $modele = $this->model_pdf;
846 } elseif (getDolGlobalString('FICHEINTER_ADDON_PDF')) {
847 $modele = getDolGlobalString('FICHEINTER_ADDON_PDF');
848 }
849 }
850
851 $modelpath = "core/modules/fichinter/doc/";
852
853 return $this->commonGenerateDocument($modelpath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams);
854 }
855
862 public function getLibStatut($mode = 0)
863 {
864 return $this->LibStatut((isset($this->statut) ? $this->statut : $this->status), $mode);
865 }
866
867 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
875 public function LibStatut($status, $mode = 0)
876 {
877 // phpcs:enable
878 global $langs;
879 // Init/load array of translation of status
880 if (empty($this->labelStatus) || empty($this->labelStatusShort)) {
881 $langs->load("interventions");
882 $langs->load("propal");
883
884 $this->labelStatus[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
885 $this->labelStatus[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Validated');
886 $this->labelStatus[self::STATUS_BILLED] = $langs->transnoentitiesnoconv('StatusInterInvoiced');
887 $this->labelStatus[self::STATUS_CLOSED] = $langs->transnoentitiesnoconv('Done');
888 $this->labelStatusShort[self::STATUS_DRAFT] = $langs->transnoentitiesnoconv('Draft');
889 $this->labelStatusShort[self::STATUS_VALIDATED] = $langs->transnoentitiesnoconv('Validated');
890 $this->labelStatusShort[self::STATUS_BILLED] = $langs->transnoentitiesnoconv('StatusInterInvoiced');
891 $this->labelStatusShort[self::STATUS_CLOSED] = $langs->transnoentitiesnoconv('Done');
892 }
893
894 $statuscode = 'status'.$status;
895 if ($status == self::STATUS_BILLED || $status == self::STATUS_CLOSED) {
896 $statuscode = 'status6';
897 }
898
899 $signed_label = ' (' . $this->getLibSignedStatus() . ')';
900 $status_label = $this->signed_status ? $this->labelStatus[$status] . $signed_label : $this->labelStatus[$status];
901 $status_label_short = $this->signed_status ? $this->labelStatusShort[$status] . $signed_label : $this->labelStatusShort[$status];
902
903 return dolGetStatus($status_label, $status_label_short, '', $statuscode, $mode);
904 }
905
912 public function getTooltipContentArray($params)
913 {
914 global $langs;
915
916 $langs->load('interventions');
917
918 $datas = [];
919 $datas['picto'] = img_picto('', $this->picto).' <u class="paddingrightonly">'.$langs->trans("ShowIntervention").'</u>';
920 $datas['picto'] .= ' '.$this->getLibStatut(5);
921 $datas['ref'] = '<br><b>'.$langs->trans('Ref').':</b> '.$this->ref;
922
923 return $datas;
924 }
925
936 public function getNomUrl($withpicto = 0, $option = '', $notooltip = 0, $save_lastsearch_value = -1, $morecss = '')
937 {
938 global $conf, $langs, $hookmanager;
939
940 if (!empty($conf->dol_no_mouse_hover)) {
941 $notooltip = 1; // Force disable tooltips
942 }
943
944 $result = '';
945 $params = [
946 'id' => $this->id,
947 'objecttype' => $this->element,
948 'option' => $option,
949 ];
950 $classfortooltip = 'classfortooltip';
951 $dataparams = '';
952 if (getDolGlobalInt('MAIN_ENABLE_AJAX_TOOLTIP')) {
953 $classfortooltip = 'classforajaxtooltip';
954 $dataparams = ' data-params="'.dol_escape_htmltag(json_encode($params)).'"';
955 $label = '';
956 } else {
957 $label = implode($this->getTooltipContentArray($params));
958 }
959
960 $url = DOL_URL_ROOT.'/fichinter/card.php?id='.$this->id;
961
962 if ($option !== 'nolink') {
963 // Add param to save lastsearch_values or not
964 $add_save_lastsearch_values = ($save_lastsearch_value == 1 ? 1 : 0);
965 if ($save_lastsearch_value == -1 && isset($_SERVER["PHP_SELF"]) && preg_match('/list\.php/', $_SERVER["PHP_SELF"])) {
966 $add_save_lastsearch_values = 1;
967 }
968 if ($add_save_lastsearch_values) {
969 $url .= '&save_lastsearch_values=1';
970 }
971 }
972
973 $linkclose = '';
974 if (empty($notooltip)) {
975 if (getDolGlobalString('MAIN_OPTIMIZEFORTEXTBROWSER')) {
976 $label = $langs->trans("ShowIntervention");
977 $linkclose .= ' alt="'.dolPrintHTMLForAttribute($label).'"';
978 }
979 $linkclose .= ($label ? ' title="'.dolPrintHTMLForAttribute($label).'"' : ' title="tocomplete"');
980 $linkclose .= $dataparams.' class="'.$classfortooltip.($morecss ? ' '.$morecss : '').'"';
981 } else {
982 $linkclose = ($morecss ? ' class="'.$morecss.'"' : '');
983 }
984
985 if ($option == 'nolink') {
986 $linkstart = '<span';
987 } else {
988 $linkstart = '<a href="'.$url.'"';
989 }
990 $linkstart .= $linkclose.'>';
991 if ($option == 'nolink') {
992 $linkend = '</span>';
993 } else {
994 $linkend = '</a>';
995 }
996
997 $result .= $linkstart;
998 if ($withpicto) {
999 $result .= img_object(($notooltip ? '' : $label), ($this->picto ? $this->picto : 'generic'), ($notooltip ? (($withpicto != 2) ? 'class="paddingright"' : '') : 'class="'.(($withpicto != 2) ? 'paddingright ' : '').'"'), 0, 0, $notooltip ? 0 : 1);
1000 }
1001
1002 if ($withpicto != 2) {
1003 $result .= $this->ref;
1004 }
1005
1006 $result .= $linkend;
1007
1008 global $action;
1009 $hookmanager->initHooks(array('interventiondao'));
1010 $parameters = array('id' => $this->id, 'getnomurl' => &$result);
1011 $reshook = $hookmanager->executeHooks('getNomUrl', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
1012 if ($reshook > 0) {
1013 $result = $hookmanager->resPrint;
1014 } else {
1015 $result .= $hookmanager->resPrint;
1016 }
1017
1018 return $result;
1019 }
1020
1021
1029 public function getNextNumRef($soc)
1030 {
1031 global $conf, $db, $langs;
1032 $langs->load("interventions");
1033
1034 if (getDolGlobalString('FICHEINTER_ADDON')) {
1035 $mybool = false;
1036
1037 $file = "mod_" . getDolGlobalString('FICHEINTER_ADDON').".php";
1038 $classname = "mod_" . getDolGlobalString('FICHEINTER_ADDON');
1039
1040 // Include file with class
1041 $dirmodels = array_merge(array('/'), (array) $conf->modules_parts['models']);
1042
1043 foreach ($dirmodels as $reldir) {
1044 $dir = dol_buildpath($reldir."core/modules/fichinter/");
1045
1046 // Load file with numbering class (if found)
1047 $mybool = ((bool) @include_once $dir.$file) || $mybool;
1048 }
1049
1050 if (!$mybool) {
1051 dol_print_error(null, "Failed to include file ".$file);
1052 return '';
1053 }
1054
1055 $obj = new $classname();
1056 '@phan-var-force ModeleNumRefFicheinter $obj';
1057 $numref = "";
1058 $numref = $obj->getNextValue($soc, $this);
1059
1060 if ($numref != "") {
1061 return $numref;
1062 } else {
1063 dol_print_error($db, "Fichinter::getNextNumRef ".$obj->error);
1064 return "";
1065 }
1066 } else {
1067 $langs->load("errors");
1068 print $langs->trans("Error")." ".$langs->trans("Error_FICHEINTER_ADDON_NotDefined");
1069 return "";
1070 }
1071 }
1072
1079 public function info($id)
1080 {
1081 $sql = "SELECT f.rowid,";
1082 $sql .= " f.datec,";
1083 $sql .= " f.tms as date_modification,";
1084 $sql .= " f.date_valid as datev,";
1085 $sql .= " f.fk_user_author,";
1086 $sql .= " f.fk_user_modif as fk_user_modification,";
1087 $sql .= " f.fk_user_valid";
1088 $sql .= " FROM ".MAIN_DB_PREFIX."fichinter as f";
1089 $sql .= " WHERE f.rowid = ".((int) $id);
1090
1091 $resql = $this->db->query($sql);
1092 if ($resql) {
1093 if ($this->db->num_rows($resql)) {
1094 $obj = $this->db->fetch_object($resql);
1095
1096 $this->id = $obj->rowid;
1097
1098 $this->date_creation = $this->db->jdate($obj->datec);
1099 $this->date_modification = $this->db->jdate($obj->date_modification);
1100 $this->date_validation = $this->db->jdate($obj->datev);
1101
1102 $this->user_creation_id = $obj->fk_user_author;
1103 $this->user_validation_id = $obj->fk_user_valid;
1104 $this->user_modification_id = $obj->fk_user_modification;
1105 }
1106 $this->db->free($resql);
1107 } else {
1108 dol_print_error($this->db);
1109 }
1110 }
1111
1119 public function delete(User $user, $notrigger = 0)
1120 {
1121 global $conf, $langs;
1122 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
1123
1124 $error = 0;
1125
1126 $this->db->begin();
1127
1128 if (!$notrigger) {
1129 // Call trigger
1130 $result = $this->call_trigger('FICHINTER_DELETE', $user);
1131 if ($result < 0) {
1132 $error++;
1133 $this->db->rollback();
1134 return -1;
1135 }
1136 // End call triggers
1137 }
1138
1139 // Delete linked object
1140 $res = $this->deleteObjectLinked();
1141 if ($res < 0) {
1142 $error++;
1143 }
1144
1145 // Delete linked contacts
1146 if (!$error) {
1147 $res = $this->delete_linked_contact();
1148 if ($res < 0) {
1149 $this->error = 'ErrorFailToDeleteLinkedContact';
1150 $error++;
1151 }
1152 }
1153
1154 if (!$error) {
1155 $main = MAIN_DB_PREFIX.'fichinterdet';
1156 $ef = $main."_extrafields";
1157 $sql = "DELETE FROM ".$this->db->sanitize($ef)." WHERE fk_object IN (SELECT rowid FROM ".$this->db->sanitize($main)." WHERE fk_fichinter = ".((int) $this->id).")";
1158
1159 $resql = $this->db->query($sql);
1160 if (!$resql) {
1161 $error++;
1162 }
1163 }
1164
1165 if (!$error) {
1166 $sql = "DELETE FROM ".MAIN_DB_PREFIX."fichinterdet";
1167 $sql .= " WHERE fk_fichinter = ".((int) $this->id);
1168
1169 $resql = $this->db->query($sql);
1170 if (!$resql) {
1171 $error++;
1172 }
1173 }
1174
1175 if (!$error) {
1176 // Remove extrafields
1177 $res = $this->deleteExtraFields();
1178 if ($res < 0) {
1179 $error++;
1180 }
1181 }
1182
1183 if (!$error) {
1184 // Delete object
1185 $sql = "DELETE FROM ".MAIN_DB_PREFIX."fichinter";
1186 $sql .= " WHERE rowid = ".((int) $this->id);
1187
1188 dol_syslog("Fichinter::delete", LOG_DEBUG);
1189 $resql = $this->db->query($sql);
1190 if (!$resql) {
1191 $error++;
1192 }
1193 }
1194
1195 if (!$error) {
1196 // Delete record into ECM index (Note that delete is also done when deleting files with the dol_delete_dir_recursive
1197 $this->deleteEcmFiles(0); // Deleting files physically is done later with the dol_delete_dir_recursive
1198 $this->deleteEcmFiles(1); // Deleting files physically is done later with the dol_delete_dir_recursive
1199
1200 // Remove directory with files
1201 $fichinterref = dol_sanitizeFileName($this->ref);
1202 if ($conf->ficheinter->dir_output) {
1203 $dir = $conf->ficheinter->dir_output."/".$fichinterref;
1204 $file = $conf->ficheinter->dir_output."/".$fichinterref."/".$fichinterref.".pdf";
1205 if (file_exists($file)) {
1206 dol_delete_preview($this);
1207
1208 if (!dol_delete_file($file, 0, 0, 0, $this)) { // For triggers
1209 $langs->load("errors");
1210 $this->error = $langs->trans("ErrorFailToDeleteFile", $file);
1211 return 0;
1212 }
1213 }
1214 if (file_exists($dir)) {
1215 if (!dol_delete_dir_recursive($dir)) {
1216 $langs->load("errors");
1217 $this->error = $langs->trans("ErrorFailToDeleteDir", $dir);
1218 return 0;
1219 }
1220 }
1221 }
1222 }
1223
1224 if (!$error) {
1225 $this->db->commit();
1226 return 1;
1227 } else {
1228 $this->db->rollback();
1229 return -1;
1230 }
1231 }
1232
1233 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1241 public function set_date_delivery($user, $delivery_date_receipt)
1242 {
1243 // phpcs:enable
1244 if ($user->hasRight('ficheinter', 'creer')) {
1245 $sql = "UPDATE ".MAIN_DB_PREFIX."fichinter";
1246 $sql .= " SET datei = '".$this->db->idate($delivery_date_receipt)."'";
1247 $sql .= " WHERE rowid = ".((int) $this->id);
1248 $sql .= " AND fk_statut = 0";
1249
1250 if ($this->db->query($sql)) {
1251 $this->date_delivery = $delivery_date_receipt;
1252 $this->delivery_date_receipt = $delivery_date_receipt;
1253 return 1;
1254 } else {
1255 $this->error = $this->db->error();
1256 dol_syslog("Fichinter::set_date_delivery Erreur SQL");
1257 return -1;
1258 }
1259 }
1260
1261 return 0;
1262 }
1263
1264 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1272 public function set_description($user, $description)
1273 {
1274 // phpcs:enable
1275 if ($user->hasRight('ficheinter', 'creer')) {
1276 $sql = "UPDATE ".MAIN_DB_PREFIX."fichinter ";
1277 $sql .= " SET description = '".$this->db->escape($description)."',";
1278 $sql .= " fk_user_modif = ".((int) $user->id);
1279 $sql .= " WHERE rowid = ".((int) $this->id);
1280
1281 if ($this->db->query($sql)) {
1282 $this->description = $description;
1283 return 1;
1284 } else {
1285 $this->error = $this->db->error();
1286 dol_syslog("Fichinter::set_description Erreur SQL");
1287 return -1;
1288 }
1289 }
1290
1291 return 0;
1292 }
1293
1294
1295 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1303 public function set_contrat($user, $contractid)
1304 {
1305 // phpcs:enable
1306 if ($user->hasRight('ficheinter', 'creer')) {
1307 $sql = "UPDATE ".MAIN_DB_PREFIX."fichinter ";
1308 $sql .= " SET fk_contrat = ".((int) $contractid);
1309 $sql .= " WHERE rowid = ".((int) $this->id);
1310
1311 if ($this->db->query($sql)) {
1312 $this->fk_contrat = $contractid;
1313 return 1;
1314 } else {
1315 $this->error = $this->db->error();
1316 return -1;
1317 }
1318 }
1319
1320 return -2;
1321 }
1322
1323
1324
1334 public function createFromClone(User $user, $socid = 0, $clone_contacts = false, $clone_notes = false)
1335 {
1336 global $hookmanager, $langs;
1337 $langs->load("errors");
1338
1339 $error = 0;
1340
1341 $this->db->begin();
1342
1343 // get extrafields so they will be clone
1344 foreach ($this->lines as $line) {
1345 $line->fetch_optionals();
1346 }
1347
1348 // Load source object
1349 $objFrom = clone $this;
1350
1351 // Change socid if needed
1352 if (!empty($socid) && $socid != $this->socid) {
1353 $objsoc = new Societe($this->db);
1354
1355 if ($objsoc->fetch($socid) > 0) {
1356 $this->socid = $objsoc->id;
1357 //$this->cond_reglement_id = (!empty($objsoc->cond_reglement_id) ? $objsoc->cond_reglement_id : 0);
1358 //$this->mode_reglement_id = (!empty($objsoc->mode_reglement_id) ? $objsoc->mode_reglement_id : 0);
1359 $this->fk_project = 0;
1360 $this->fk_delivery_address = 0;
1361 }
1362
1363 // TODO Change product price if multi-prices
1364 }
1365
1366 $this->id = 0;
1367 $this->ref = '';
1368 $this->status = self::STATUS_DRAFT;
1369 $this->statut = self::STATUS_DRAFT; // deprecated
1370
1371 // Clear fields
1372 $this->user_author_id = $user->id;
1373 $this->user_validation_id = 0;
1374 $this->date_creation = '';
1375 $this->date_validation = '';
1376
1377 $this->ref_client = '';
1378
1379 if (!$clone_notes) {
1380 $this->note_private = '';
1381 $this->note_public = '';
1382 }
1383
1384 // Create clone
1385 $this->context['createfromclone'] = 'createfromclone';
1386 $result = $this->create($user);
1387 if ($result < 0) {
1388 $error++;
1389 }
1390
1391 if (!$error) {
1392 // Add lines because it is not included into create function
1393 foreach ($this->lines as $line) {
1394 $this->addline($user, $this->id, $line->desc, $line->datei, $line->duration, $line->array_options);
1395 }
1396
1397 // Hook of thirdparty module
1398 if (is_object($hookmanager)) {
1399 $parameters = array('objFrom' => $objFrom);
1400 $action = '';
1401 $reshook = $hookmanager->executeHooks('createFrom', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
1402 if ($reshook < 0) {
1403 $this->setErrorsFromObject($hookmanager);
1404 $error++;
1405 }
1406 }
1407 }
1408
1409 //Duplicate contact
1410 if ($clone_contacts) {
1411 foreach (array('internal', 'external') as $source) {
1412 $tab = $objFrom->liste_contact(-1, $source);
1413 if (is_array($tab) && count($tab) > 0) {
1414 foreach ($tab as $contacttoadd) {
1415 $retAddContact = $this->add_contact(
1416 $contacttoadd['id'],
1417 $contacttoadd['code'],
1418 $contacttoadd['source']
1419 );
1420 if ($this->error == 'DB_ERROR_RECORD_ALREADY_EXISTS') {
1421 $this->error .= $langs->trans("ErrorThisContactIsAlreadyDefinedAsThisType");
1422 $error++;
1423 } elseif ($retAddContact < 0) {
1424 $error++;
1425 }
1426 }
1427 } elseif ($tab < 0) {
1428 $this->error .= $objFrom->error;
1429 $error++;
1430 }
1431 }
1432 }
1433
1434 unset($this->context['createfromclone']);
1435
1436 // End
1437 if (!$error) {
1438 $this->db->commit();
1439 return $this->id;
1440 } else {
1441 $this->db->rollback();
1442 return -1;
1443 }
1444 }
1445
1446
1461 public function addline($user, $fichinterid, $desc, $date_intervention, $duration, $array_options = [], $type = 0, $rang = -1, $special_code = 0)
1462 {
1463 dol_syslog(get_class($this)."::addline $fichinterid, $desc, $date_intervention, $duration, $type, $rang, $special_code");
1464
1465 if ($this->status == self::STATUS_DRAFT) {
1466 $this->db->begin();
1467
1468 // Insertion ligne
1469 $line = new FichinterLigne($this->db);
1470
1471 $line->fk_fichinter = $fichinterid;
1472 $line->desc = $desc;
1473 $line->date = $date_intervention;
1474 $line->datei = $date_intervention; // For backward compatibility
1475 $line->duration = $duration;
1476 $line->product_type = $type;
1477 $line->rang = $rang;
1478 $line->special_code = $special_code;
1479
1480
1481 if (is_array($array_options) && count($array_options) > 0) {
1482 $line->array_options = $array_options;
1483 }
1484
1485 $result = $line->insert($user);
1486
1487 if ($result >= 0) {
1488 $this->db->commit();
1489 return $line->id;
1490 } else {
1491 $this->error = $this->db->error();
1492 $this->db->rollback();
1493 return -1;
1494 }
1495 }
1496
1497 return 0;
1498 }
1499
1500
1508 public function initAsSpecimen()
1509 {
1510 global $langs;
1511
1512 $now = dol_now();
1513
1514 // Initialise parameters
1515 $this->id = 0;
1516 $this->ref = 'SPECIMEN';
1517 $this->ref_client = 'SPECIMEN CLIENT';
1518 $this->specimen = 1;
1519 $this->socid = 1;
1520 $this->datec = $now;
1521 $this->note_private = 'Private note';
1522 $this->note_public = 'SPECIMEN';
1523 $this->duration = 0;
1524 $this->user_creation_id = 1;
1525 $nbp = 25;
1526 $xnbp = 0;
1527 while ($xnbp < $nbp) {
1528 $line = new FichinterLigne($this->db);
1529 $line->desc = $langs->trans("Description")." ".$xnbp;
1530 $line->date = ($now - 3600 * (1 + $xnbp));
1531 $line->datei = ($now - 3600 * (1 + $xnbp)); // For backward compatibility
1532 $line->duration = 600;
1533 $line->fk_fichinter = 0;
1534 $this->lines[$xnbp] = $line;
1535 $xnbp++;
1536
1537 $this->duration += $line->duration;
1538 }
1539
1540 return 1;
1541 }
1542
1543 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
1549 public function fetch_lines()
1550 {
1551 // phpcs:enable
1552 $this->lines = array();
1553
1554 $sql = "SELECT rowid, fk_fichinter, description, duree, date, rang, extraparams";
1555 $sql .= " FROM ".MAIN_DB_PREFIX."fichinterdet";
1556 $sql .= " WHERE fk_fichinter = ".((int) $this->id);
1557 $sql .= " ORDER BY rang ASC, date ASC";
1558
1559 dol_syslog(get_class($this)."::fetch_lines", LOG_DEBUG);
1560
1561 $resql = $this->db->query($sql);
1562 if ($resql) {
1563 $num = $this->db->num_rows($resql);
1564 $i = 0;
1565 while ($i < $num) {
1566 $objp = $this->db->fetch_object($resql);
1567
1568 $line = new FichinterLigne($this->db);
1569 $line->id = $objp->rowid;
1570 $line->fk_fichinter = $objp->fk_fichinter;
1571 $line->desc = $objp->description;
1572 $line->duration = $objp->duree;
1573 //For invoicing we calculing hours
1574 $line->qty = round($objp->duree / 3600, 2);
1575 $line->date = $this->db->jdate($objp->date);
1576 $line->datei = $this->db->jdate($objp->date); // For backward compatibility
1577 $line->rang = $objp->rang;
1578 $line->product_type = 1;
1579 $line->fetch_optionals();
1580
1581 $line->extraparams = !empty($objp->extraparams) ? (array) json_decode($objp->extraparams, true) : array();
1582
1583 $this->lines[$i] = $line;
1584 $i++;
1585 }
1586 $this->db->free($resql);
1587
1588 return 1;
1589 } else {
1590 $this->error = $this->db->error();
1591 return -1;
1592 }
1593 }
1594
1603 public static function replaceThirdparty(DoliDB $dbs, $origin_id, $dest_id)
1604 {
1605 $tables = array(
1606 'fichinter'
1607 );
1608
1609 return CommonObject::commonReplaceThirdparty($dbs, $origin_id, $dest_id, $tables);
1610 }
1611
1620 public function setRefClient($user, $ref_client, $notrigger = 0)
1621 {
1622 // phpcs:enable
1623 if ($user->hasRight('ficheinter', 'creer')) {
1624 $error = 0;
1625
1626 $this->db->begin();
1627
1628 $this->oldcopy = dol_clone($this, 2);
1629
1630 $sql = "UPDATE ".MAIN_DB_PREFIX.$this->table_element." SET ref_client = ".(empty($ref_client) ? 'NULL' : "'".$this->db->escape($ref_client)."'");
1631 $sql .= " WHERE rowid = ".((int) $this->id);
1632
1633 dol_syslog(__METHOD__.' $this->id='.$this->id.', ref_client='.$ref_client, LOG_DEBUG);
1634 $resql = $this->db->query($sql);
1635 if (!$resql) {
1636 $this->errors[] = $this->db->error();
1637 $error++;
1638 }
1639
1640 if (!$error) {
1641 $this->ref_client = $ref_client;
1642 }
1643
1644 if (!$notrigger && empty($error)) {
1645 // Call trigger
1646 $result = $this->call_trigger('FICHINTER_MODIFY', $user);
1647 if ($result < 0) {
1648 $error++;
1649 }
1650 // End call triggers
1651 }
1652
1653 if (!$error) {
1654 $this->db->commit();
1655 return 1;
1656 } else {
1657 foreach ($this->errors as $errmsg) {
1658 dol_syslog(__METHOD__.' Error: '.$errmsg, LOG_ERR);
1659 $this->error .= ($this->error ? ', '.$errmsg : $errmsg);
1660 }
1661 $this->db->rollback();
1662 return -1 * $error;
1663 }
1664 } else {
1665 return -1;
1666 }
1667 }
1668
1676 public function getKanbanView($option = '', $arraydata = null)
1677 {
1678 global $langs;
1679
1680 $selected = (empty($arraydata['selected']) ? 0 : $arraydata['selected']);
1681
1682 $return = '<div class="box-flex-item box-flex-grow-zero">';
1683 $return .= '<div class="info-box info-box-sm">';
1684 $return .= '<span class="info-box-icon bg-infobox-action">';
1685 $return .= img_picto('', $this->picto);
1686 $return .= '</span>';
1687 $return .= '<div class="info-box-content">';
1688 $return .= '<span class="info-box-ref inline-block tdoverflowmax150 valignmiddle">' . $this->getNomUrl() . '</span>';
1689 if ($selected >= 0) {
1690 $return .= '<input id="cb'.$this->id.'" class="flat checkforselect fright" type="checkbox" name="toselect[]" value="'.$this->id.'"'.($selected ? ' checked="checked"' : '').'>';
1691 }
1692 if (!empty($arraydata['thirdparty'])) {
1693 $tmpthirdparty = $arraydata['thirdparty'];
1694 '@phan-var-force Societe $tmpthirdparty';
1696 $return .= '<br><span class="info-box-label">'.$tmpthirdparty->getNomUrl(1).'</span>';
1697 }
1698 if (!empty($this->duration)) {
1699 $return .= '<br><span class="info-box-label ">'.$langs->trans("Duration").' : '.convertSecondToTime($this->duration, 'allhourmin').'</span>';
1700 }
1701 $return .= '<br><div class="info-box-status">'.$this->getLibStatut(3).'</div>';
1702 $return .= '</div>';
1703 $return .= '</div>';
1704 $return .= '</div>';
1705 return $return;
1706 }
1707}
$object ref
Definition info.php:90
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...
deleteEcmFiles($mode=0)
Delete related files of object in database.
add_object_linked($origin=null, $origin_id=null, $f_user=null, $notrigger=0)
Add an object link into llx_element_element.
commonGenerateDocument($modelspath, $modele, $outputlangs, $hidedetails, $hidedesc, $hideref, $moreparams=null)
Common function for all objects extending CommonObject for generating documents.
deleteObjectLinked($sourceid=null, $sourcetype='', $targetid=null, $targettype='', $rowid=0, $f_user=null, $notrigger=0)
Delete all links between an object $this.
setErrorsFromObject($object)
setErrorsFromObject
static isExistingObject($element, $id, $ref='', $ref_ext='')
Check if an object id or ref exists If you don't need or want to instantiate the object and just need...
deleteExtraFields()
Delete all extra fields values for the current object.
static commonReplaceThirdparty(DoliDB $dbs, $origin_id, $dest_id, array $tables, $ignoreerrors=0)
Function used to replace a thirdparty id with another one.
insertExtraFields($trigger='', $userused=null)
Add/Update all extra fields values for the current object.
delete_linked_contact($source='', $code='')
Delete all links between an object $this and all its contacts in llx_element_contact.
add_contact($fk_socpeople, $type_contact, $source='external', $notrigger=0)
Add a link between element $this->element and a contact.
Class to manage Dolibarr database access.
const STATUS_BILLED
Billed.
initAsSpecimen()
Initialise an instance with random values.
createFromClone(User $user, $socid=0, $clone_contacts=false, $clone_notes=false)
Load an object from its id and create a new one in database.
getLibStatut($mode=0)
Returns the label status.
update($user, $notrigger=0)
Update an intervention.
static replaceThirdparty(DoliDB $dbs, $origin_id, $dest_id)
Function used to replace a thirdparty id with another one.
setClose($user, $notrigger=0)
Close intervention.
const STATUS_DRAFT
Draft status.
create($user, $notrigger=0)
Create an intervention into data base.
set_description($user, $description)
Define the label of the intervention.
getTooltipContentArray($params)
getTooltipContentArray
set_date_delivery($user, $delivery_date_receipt)
Defines a delivery date of the receipt of intervention.
const STATUS_VALIDATED
Validated status.
fetch($rowid, $ref='', $ref_ext='')
Fetch a intervention.
const STATUS_CLOSED
Closed.
setDraft($user)
Set status to draft.
getNextNumRef($soc)
Returns the next non used reference of intervention depending on the module numbering assets within F...
getAmount()
Returns amount based on user thm.
addline($user, $fichinterid, $desc, $date_intervention, $duration, $array_options=[], $type=0, $rang=-1, $special_code=0)
Adding a line of intervention into data base.
setRefClient($user, $ref_client, $notrigger=0)
Set customer reference number.
set_contrat($user, $contractid)
Link intervention to a contract.
LibStatut($status, $mode=0)
Returns the label of a status.
setValid($user, $notrigger=0)
Validate a intervention.
loadStateBoard()
Load indicators into this->nb for board.
getNomUrl($withpicto=0, $option='', $notooltip=0, $save_lastsearch_value=-1, $morecss='')
Return clickable name (with picto eventually)
__construct($db)
Constructor.
generateDocument($modele, $outputlangs, $hidedetails=0, $hidedesc=0, $hideref=0, $moreparams=null)
Create a document onto disk according to template module.
info($id)
Load information on object.
fetch_lines()
Load array lines ->lines.
Class to manage intervention lines.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage Dolibarr users.
print $langs trans("Ref").' m titre as m m statut as status
Or an array listing all the potential status of the object: array: int of the status => translated la...
Definition index.php:171
getLibSignedStatus(int $mode=0)
Returns the label for signed status.
convertSecondToTime($iSecond, $format='all', $lengthOfDay=86400, $lengthOfWeek=7)
Return, in clear text, value of a number of seconds in days, hours and minutes.
Definition date.lib.php:247
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_delete_file($file, $disableglob=0, $nophperrors=0, $nohook=0, $object=null, $allowdotdot=false, $indexdatabase=1, $nolog=0)
Remove a file or several files with a mask.
dol_delete_dir_recursive($dir, $count=0, $nophperrors=0, $onlysub=0, &$countdeleted=0, $indexdatabase=1, $nolog=0, $level=0)
Remove a directory $dir and its subdirectories (or only files and subdirectories)
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:64
dol_delete_preview($object)
Delete all preview files linked to object instance.
dol_now($mode='gmt')
Return date for now.
setEntity($currentobject)
Set entity id to use when to create an object.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2, $allowothertags=array())
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 '.
img_object($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $allowothertags=array())
Show a picto called object_picto (generic function)
dol_sanitizeFileName($str, $newstr='_', $unaccent=1, $includequotes=0, $allowdash=0)
Clean a string to use it as a file name.
dol_strlen($string, $stringencoding='UTF-8')
Make a strlen call.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
dolGetStatus($statusLabel='', $statusLabelShort='', $html='', $statusType='status0', $displayMode=0, $url='', $params=array())
Output the badge of a status.
dol_buildpath($path, $type=0, $returnemptyifnotfound=0)
Return path of url or filesystem.
dol_clone($srcobject, $native=2)
Create a clone of instance of object (new instance with same value for each properties) With native =...
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 a Dolibarr global constant string value.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
getEntity($element, $shared=1, $currentobject=null)
Get list of entity id to use.