dolibarr 21.0.0-alpha
doc_generic_project_odt.modules.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2010-2012 Laurent Destailleur <eldy@users.sourceforge.net>
3 * Copyright (C) 2012 Juanjo Menent <jmenent@2byte.es>
4 * Copyright (C) 2013 Florian Henry <florian.henry@ope-concept.pro>
5 * Copyright (C) 2016-2023 Charlene Benke <charlene@patas-monkey.com>
6 * Copyright (C) 2018-2024 Frédéric France <frederic.france@free.fr>
7 * Copyright (C) 2023 Gauthier VERDOL <gauthier.verdol@atm-consulting.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 * or see https://www.gnu.org/
23 */
24
31require_once DOL_DOCUMENT_ROOT.'/core/modules/project/modules_project.php';
32require_once DOL_DOCUMENT_ROOT.'/projet/class/project.class.php';
33require_once DOL_DOCUMENT_ROOT.'/projet/class/task.class.php';
34require_once DOL_DOCUMENT_ROOT.'/contact/class/contact.class.php';
35require_once DOL_DOCUMENT_ROOT.'/user/class/user.class.php';
36require_once DOL_DOCUMENT_ROOT.'/societe/class/societe.class.php';
37require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
38require_once DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php';
39require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
40require_once DOL_DOCUMENT_ROOT.'/core/lib/doc.lib.php';
41require_once DOL_DOCUMENT_ROOT.'/core/lib/date.lib.php';
42if (isModEnabled("propal")) {
43 require_once DOL_DOCUMENT_ROOT.'/comm/propal/class/propal.class.php';
44}
45if (isModEnabled('invoice')) {
46 require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
47}
48if (isModEnabled('invoice')) {
49 require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture-rec.class.php';
50}
51if (isModEnabled('order')) {
52 require_once DOL_DOCUMENT_ROOT.'/commande/class/commande.class.php';
53}
54if (isModEnabled("supplier_invoice")) {
55 require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.facture.class.php';
56}
57if (isModEnabled("supplier_order")) {
58 require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.commande.class.php';
59}
60if (isModEnabled('contract')) {
61 require_once DOL_DOCUMENT_ROOT.'/contrat/class/contrat.class.php';
62}
63if (isModEnabled('intervention')) {
64 require_once DOL_DOCUMENT_ROOT.'/fichinter/class/fichinter.class.php';
65}
66if (isModEnabled('deplacement')) {
67 require_once DOL_DOCUMENT_ROOT.'/compta/deplacement/class/deplacement.class.php';
68}
69if (isModEnabled('agenda')) {
70 require_once DOL_DOCUMENT_ROOT.'/comm/action/class/actioncomm.class.php';
71}
72if (isModEnabled('shipping')) {
73 require_once DOL_DOCUMENT_ROOT.'/expedition/class/expedition.class.php';
74}
75
80{
85 public $version = 'dolibarr';
86
87
93 public function __construct($db)
94 {
95 global $langs, $mysoc;
96
97 // Load traductions files required by page
98 $langs->loadLangs(array("companies", "main"));
99
100 $this->db = $db;
101 $this->name = "ODT templates";
102 $this->description = $langs->trans("DocumentModelOdt");
103 $this->scandir = 'PROJECT_ADDON_PDF_ODT_PATH'; // Name of constant that is used to save list of directories to scan
104
105 // Page size for A4 format
106 $this->type = 'odt';
107 $this->page_largeur = 0;
108 $this->page_hauteur = 0;
109 $this->format = array($this->page_largeur, $this->page_hauteur);
110 $this->marge_gauche = 0;
111 $this->marge_droite = 0;
112 $this->marge_haute = 0;
113 $this->marge_basse = 0;
114
115 $this->option_logo = 1; // Display logo
116 $this->option_tva = 0; // Manage the vat option COMMANDE_TVAOPTION
117 $this->option_modereg = 0; // Display payment mode
118 $this->option_condreg = 0; // Display payment terms
119 $this->option_multilang = 1; // Available in several languages
120 $this->option_escompte = 0; // Displays if there has been a discount
121 $this->option_credit_note = 0; // Support credit notes
122 $this->option_freetext = 1; // Support add of a personalised text
123 $this->option_draft_watermark = 0; // Support add of a watermark on drafts
124
125 if ($mysoc === null) {
126 dol_syslog(get_class($this).'::__construct() Global $mysoc should not be null.'. getCallerInfoString(), LOG_ERR);
127 return;
128 }
129
130 // Get source company
131 $this->emetteur = $mysoc;
132 if (!$this->emetteur->country_code) {
133 $this->emetteur->country_code = substr($langs->defaultlang, -2); // Par default, si n'etait pas defini
134 }
135 }
136
137 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
146 public function get_substitutionarray_object($object, $outputlangs, $array_key = 'object')
147 {
148 // phpcs:enable
149 if (!$object instanceof Project) {
150 dol_syslog("Expected Project object, got ".gettype($object), LOG_ERR);
151 return array();
152 }
153
154 $resarray = array(
155 $array_key.'_id' => $object->id,
156 $array_key.'_ref' => $object->ref,
157 $array_key.'_title' => $object->title,
158 $array_key.'_description' => $object->description,
159 $array_key.'_date_creation' => dol_print_date($object->date_c, 'day'),
160 $array_key.'_date_modification' => dol_print_date($object->date_m, 'day'),
161 $array_key.'_date_start' => dol_print_date($object->date_start, 'day'),
162 $array_key.'_date_end' => dol_print_date($object->date_end, 'day'),
163 $array_key.'_note_private' => $object->note_private,
164 $array_key.'_note_public' => $object->note_public,
165 $array_key.'_public' => $object->public,
166 $array_key.'_statut' => $object->getLibStatut()
167 );
168
169 require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
170 $extrafields = new ExtraFields($this->db);
171 $extrafields->fetch_name_optionals_label($object->table_element, true);
172 $object->fetch_optionals();
173
174 $resarray = $this->fill_substitutionarray_with_extrafields($object, $resarray, $extrafields, $array_key, $outputlangs);
175
176 return $resarray;
177 }
178
179 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
188 public function get_substitutionarray_tasks(Task $task, $outputlangs)
189 {
190 // phpcs:enable
191 $resarray = array(
192 'task_ref' => $task->ref,
193 'task_fk_project' => $task->fk_project,
194 'task_projectref' => $task->projectref,
195 'task_projectlabel' => $task->projectlabel,
196 'task_label' => $task->label,
197 'task_description' => $task->description,
198 'task_fk_parent' => $task->fk_task_parent,
199 'task_duration' => $task->duration,
200 'task_duration_hour' => convertSecondToTime($task->duration, 'all'),
201 'task_planned_workload' => $task->planned_workload,
202 'task_planned_workload_hour' => convertSecondToTime($task->planned_workload, 'all'),
203 'task_progress' => $task->progress,
204 'task_public' => $task->public,
205 'task_date_start' => dol_print_date($task->date_start, 'day'),
206 'task_date_end' => dol_print_date($task->date_end, 'day'),
207 'task_note_private' => $task->note_private,
208 'task_note_public' => $task->note_public
209 );
210
211 require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
212 $extrafields = new ExtraFields($this->db);
213 $extrafields->fetch_name_optionals_label($task->table_element, true);
214 $task->fetch_optionals();
215
216 $resarray = $this->fill_substitutionarray_with_extrafields($task, $resarray, $extrafields, 'task', $outputlangs);
217
218 return $resarray;
219 }
220
221 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
229 public function get_substitutionarray_project_contacts($contact, $outputlangs)
230 {
231 // phpcs:enable
232 $pc = 'projcontacts_'; // prefix to avoid typos
233
234 $ret = array(
235 $pc.'id' => $contact['id'],
236 $pc.'rowid' => $contact['rowid'],
237 $pc.'role' => $contact['libelle'],
238 $pc.'lastname' => $contact['lastname'],
239 $pc.'firstname' => $contact['firstname'],
240 $pc.'civility' => $contact['civility'],
241 $pc.'fullcivname' => $contact['fullname'],
242 $pc.'socname' => $contact['socname'],
243 $pc.'email' => $contact['email']
244 );
245
246 if ($contact['source'] == 'external') {
247 $ret[$pc.'isInternal'] = ''; // not internal
248
249 $ct = new Contact($this->db);
250 $ct->fetch($contact['id']);
251 $ret[$pc.'phone_pro'] = $ct->phone_pro;
252 $ret[$pc.'phone_perso'] = $ct->phone_perso;
253 $ret[$pc.'phone_mobile'] = $ct->phone_mobile;
254
255 // fetch external user extrafields
256 require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
257 $extrafields = new ExtraFields($this->db);
258 $extrafields->fetch_name_optionals_label($ct->table_element, true);
259 $extrafields_num = $ct->fetch_optionals();
260 //dol_syslog(get_class($this)."::get_substitutionarray_project_contacts: ===== Number of Extrafields found: ".$extrafields_num, LOG_DEBUG);
261 foreach ($ct->array_options as $efkey => $efval) {
262 dol_syslog(get_class($this)."::get_substitutionarray_project_contacts: +++++ Extrafield ".$efkey." => ".$efval, LOG_DEBUG);
263 $ret[$pc.$efkey] = $efval; // add nothing else because it already comes as 'options_XX'
264 }
265 } elseif ($contact['source'] == 'internal') {
266 $ret[$pc.'isInternal'] = '1'; // this is an internal user
267
268 $ct = new User($this->db);
269 $ct->fetch($contact['id']);
270 $ret[$pc.'phone_pro'] = $ct->office_phone;
271 $ret[$pc.'phone_perso'] = '';
272 $ret[$pc.'phone_mobile'] = $ct->user_mobile;
273 // do internal users have extrafields ?
274 }
275 return $ret;
276 }
277
278 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
286 public function get_substitutionarray_project_file($file, $outputlangs)
287 {
288 // phpcs:enable
289 return array(
290 'projfile_name' => $file['name'],
291 'projfile_date' => dol_print_date($file['date'], 'day'),
292 'projfile_size' => $file['size']
293 );
294 }
295
296 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
304 public function get_substitutionarray_project_reference($refdetail, $outputlangs)
305 {
306 // phpcs:enable
307 global $conf;
308
309 return array(
310 'projref_type' => $refdetail['type'],
311 'projref_ref' => $refdetail['ref'],
312 'projref_date' => dol_print_date($refdetail['date'], 'day'),
313 'projref_socname' => $refdetail['socname'],
314 'projref_amountht' => price($refdetail['amountht'], 0, $outputlangs),
315 'projref_amountttc' => price($refdetail['amountttc'], 0, $outputlangs),
316 'projref_status' => $refdetail['status']
317 );
318 }
319
320 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
328 public function get_substitutionarray_tasksressource($taskresource, $outputlangs)
329 {
330 // phpcs:enable
331
332 //dol_syslog(get_class($this).'::get_substitutionarray_tasksressource taskressource='.var_export($taskressource,true),LOG_DEBUG);
333 return array(
334 'taskressource_rowid' => $taskresource['rowid'],
335 'taskressource_role' => $taskresource['libelle'],
336 'taskressource_lastname' => $taskresource['lastname'],
337 'taskressource_firstname' => $taskresource['firstname'],
338 'taskressource_fullcivname' => $taskresource['fullname'],
339 'taskressource_socname' => $taskresource['socname'],
340 'taskressource_email' => $taskresource['email']
341 );
342 }
343
344 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
352 public function get_substitutionarray_taskstime($tasktime, $outputlangs)
353 {
354 // phpcs:enable
355 return array(
356 'tasktime_rowid' => $tasktime['rowid'],
357 'tasktime_task_date' => dol_print_date($tasktime['task_date'], 'day'),
358 'tasktime_task_duration_sec' => $tasktime['task_duration'],
359 'tasktime_task_duration' => convertSecondToTime($tasktime['task_duration'], 'all'),
360 'tasktime_note' => $tasktime['note'],
361 'tasktime_fk_user' => $tasktime['fk_user'],
362 'tasktime_user_name' => $tasktime['name'],
363 'tasktime_user_first' => $tasktime['firstname'],
364 'tasktime_fullcivname' => $tasktime['fullcivname'],
365 'tasktime_amountht' => $tasktime['amountht'],
366 'tasktime_amountttc' => $tasktime['amountttc'],
367 'tasktime_thm' => $tasktime['thm'],
368 );
369 }
370
371 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
379 public function get_substitutionarray_task_file($file, $outputlangs)
380 {
381 // phpcs:enable
382 return array(
383 'tasksfile_name' => $file['name'],
384 'tasksfile_date' => dol_print_date($file['date'], 'day'),
385 'tasksfile_size' => $file['size']
386 );
387 }
388
389
396 public function info($langs)
397 {
398 global $conf, $langs;
399
400 // Load translation files required by the page
401 $langs->loadLangs(array("companies", "errors"));
402
403 $form = new Form($this->db);
404
405 $texte = $this->description.".<br>\n";
406 $texte .= '<form action="'.$_SERVER["PHP_SELF"].'" method="POST" enctype="multipart/form-data">';
407 $texte .= '<input type="hidden" name="token" value="'.newToken().'">';
408 $texte .= '<input type="hidden" name="page_y" value="">';
409 $texte .= '<input type="hidden" name="action" value="setModuleOptions">';
410 $texte .= '<input type="hidden" name="param1" value="PROJECT_ADDON_PDF_ODT_PATH">';
411 $texte .= '<table class="nobordernopadding centpercent">';
412
413 // List of directories area
414 $texte .= '<tr><td>';
415 $texttitle = $langs->trans("ListOfDirectories");
416 $listofdir = explode(',', preg_replace('/[\r\n]+/', ',', trim(getDolGlobalString('PROJECT_ADDON_PDF_ODT_PATH'))));
417 $listoffiles = array();
418 foreach ($listofdir as $key => $tmpdir) {
419 $tmpdir = trim($tmpdir);
420 $tmpdir = preg_replace('/DOL_DATA_ROOT/', DOL_DATA_ROOT, $tmpdir);
421 if (!$tmpdir) {
422 unset($listofdir[$key]);
423 continue;
424 }
425 if (!is_dir($tmpdir)) {
426 $texttitle .= img_warning($langs->trans("ErrorDirNotFound", $tmpdir), '');
427 } else {
428 $tmpfiles = dol_dir_list($tmpdir, 'files', 0, '\.(ods|odt)');
429 if (count($tmpfiles)) {
430 $listoffiles = array_merge($listoffiles, $tmpfiles);
431 }
432 }
433 }
434 $texthelp = $langs->trans("ListOfDirectoriesForModelGenODT");
435 $texthelp .= '<br><br><span class="opacitymedium">'.$langs->trans("ExampleOfDirectoriesForModelGen").'</span>';
436 // Add list of substitution keys
437 $texthelp .= '<br>'.$langs->trans("FollowingSubstitutionKeysCanBeUsed").'<br>';
438 $texthelp .= $langs->transnoentitiesnoconv("FullListOnOnlineDocumentation"); // This contains an url, we don't modify it
439
440 $texte .= $form->textwithpicto($texttitle, $texthelp, 1, 'help', '', 1, 3, $this->name);
441 $texte .= '<div><div style="display: inline-block; min-width: 100px; vertical-align: middle;">';
442 $texte .= '<textarea class="flat" cols="60" name="value1">';
443 $texte .= getDolGlobalString('PROJECT_ADDON_PDF_ODT_PATH');
444 $texte .= '</textarea>';
445 $texte .= '</div><div style="display: inline-block; vertical-align: middle;">';
446 $texte .= '<input type="submit" class="button button-edit reposition smallpaddingimp" name="modify" value="'.dol_escape_htmltag($langs->trans("Modify")).'">';
447 $texte .= '<br></div></div>';
448
449 // Scan directories
450 $nbofiles = count($listoffiles);
451 if (getDolGlobalString('PROJECT_ADDON_PDF_ODT_PATH')) {
452 $texte .= $langs->trans("NumberOfModelFilesFound").': <b>';
453 //$texte.=$nbofiles?'<a id="a_'.get_class($this).'" href="#">':'';
454 $texte .= $nbofiles;
455 //$texte.=$nbofiles?'</a>':'';
456 $texte .= '</b>';
457 }
458
459 if ($nbofiles) {
460 $texte .= '<div id="div_'.get_class($this).'" class="hiddenx">';
461 // Show list of found files
462 foreach ($listoffiles as $file) {
463 $texte .= '- '.$file['name'].' <a href="'.DOL_URL_ROOT.'/document.php?modulepart=doctemplates&file=projects/'.urlencode(basename($file['name'])).'">'.img_picto('', 'listlight').'</a>';
464 $texte .= ' &nbsp; <a class="reposition" href="'.$_SERVER["PHP_SELF"].'?modulepart=doctemplates&keyforuploaddir=PROJECT_ADDON_PDF_ODT_PATH&action=deletefile&token='.newToken().'&file='.urlencode(basename($file['name'])).'">'.img_picto('', 'delete').'</a>';
465 $texte .= '<br>';
466 }
467 $texte .= '</div>';
468 }
469 // Add input to upload a new template file.
470 $texte .= '<div>'.$langs->trans("UploadNewTemplate");
471 $maxfilesizearray = getMaxFileSizeArray();
472 $maxmin = $maxfilesizearray['maxmin'];
473 if ($maxmin > 0) {
474 $texte .= '<input type="hidden" name="MAX_FILE_SIZE" value="'.($maxmin * 1024).'">'; // MAX_FILE_SIZE must precede the field type=file
475 }
476 $texte .= ' <input type="file" name="uploadfile">';
477 $texte .= '<input type="hidden" value="PROJECT_ADDON_PDF_ODT_PATH" name="keyforuploaddir">';
478 $texte .= '<input type="submit" class="button smallpaddingimp reposition" value="'.dol_escape_htmltag($langs->trans("Upload")).'" name="upload">';
479 $texte .= '</div>';
480 $texte .= '</td>';
481
482 $texte .= '</tr>';
483
484 $texte .= '</table>';
485 $texte .= '</form>';
486
487 return $texte;
488 }
489
490 // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps
499 public function write_file($object, $outputlangs, $srctemplatepath = '')
500 {
501 // phpcs:enable
502 global $user, $langs, $conf, $mysoc, $hookmanager;
503
504 if (empty($srctemplatepath)) {
505 dol_syslog("doc_generic_odt::write_file parameter srctemplatepath empty", LOG_WARNING);
506 return -1;
507 }
508
509 // Add odtgeneration hook
510 if (!is_object($hookmanager)) {
511 include_once DOL_DOCUMENT_ROOT.'/core/class/hookmanager.class.php';
512 $hookmanager = new HookManager($this->db);
513 }
514 $hookmanager->initHooks(array('odtgeneration'));
515 global $action;
516
517 if (!is_object($outputlangs)) {
518 $outputlangs = $langs;
519 }
520 $sav_charset_output = $outputlangs->charset_output;
521 $outputlangs->charset_output = 'UTF-8';
522
523 // Load translation files required by the page
524 $outputlangs->loadLangs(array("main", "dict", "companies", "projects"));
525
526 if ($conf->project->dir_output) {
527 // If $object is id instead of object
528 if (!is_object($object)) {
529 $id = $object;
530 $object = new Project($this->db);
531 $result = $object->fetch($id);
532 if ($result < 0) {
533 dol_print_error($this->db, $object->error);
534 return -1;
535 }
536 }
537
538 $object->fetch_thirdparty();
539
540 $dir = $conf->project->dir_output;
541 $objectref = dol_sanitizeFileName($object->ref);
542 if (!preg_match('/specimen/i', $objectref)) {
543 $dir .= "/".$objectref;
544 }
545 $file = $dir."/".$objectref.".odt";
546
547 if (!file_exists($dir)) {
548 if (dol_mkdir($dir) < 0) {
549 $this->error = $langs->transnoentities("ErrorCanNotCreateDir", $dir);
550 return -1;
551 }
552 }
553
554 if (file_exists($dir)) {
555 //print "srctemplatepath=".$srctemplatepath; // Src filename
556 $newfile = basename($srctemplatepath);
557 $newfiletmp = preg_replace('/\.od[ts]/i', '', $newfile);
558 $newfiletmp = preg_replace('/template_/i', '', $newfiletmp);
559 $newfiletmp = preg_replace('/modele_/i', '', $newfiletmp);
560 $newfiletmp = $objectref . '_' . $newfiletmp;
561 //$file=$dir.'/'.$newfiletmp.'.'.dol_print_date(dol_now(),'%Y%m%d%H%M%S').'.odt';
562 // Get extension (ods or odt)
563 $newfileformat = substr($newfile, strrpos($newfile, '.') + 1);
564 if (getDolGlobalString('MAIN_DOC_USE_TIMING')) {
565 $format = getDolGlobalString('MAIN_DOC_USE_TIMING');
566 if ($format == '1') {
567 $format = '%Y%m%d%H%M%S';
568 }
569 $filename = $newfiletmp . '-' . dol_print_date(dol_now(), $format) . '.' . $newfileformat;
570 } else {
571 $filename = $newfiletmp . '.' . $newfileformat;
572 }
573 $file = $dir . '/' . $filename;
574 //print "newdir=".$dir;
575 //print "newfile=".$newfile;
576 //print "file=".$file;
577 //print "conf->societe->dir_temp=".$conf->societe->dir_temp;
578
579 dol_mkdir($conf->project->dir_temp);
580 if (!is_writable($conf->project->dir_temp)) {
581 $this->error = $langs->transnoentities("ErrorFailedToWriteInTempDirectory", $conf->project->dir_temp);
582 dol_syslog('Error in write_file: ' . $this->error, LOG_ERR);
583 return -1;
584 }
585
586 // If PROJECTLEADER contact defined on project, we use it
587 $usecontact = false;
588 $arrayidcontact = $object->getIdContact('external', 'PROJECTLEADER');
589 if (count($arrayidcontact) > 0) {
590 $usecontact = true;
591 $result = $object->fetch_contact($arrayidcontact[0]);
592 }
593
594 // Recipient name
595 $contactobject = null;
596 if (!empty($usecontact)) {
597 // if we have a PROJECTLEADER contact and we don't use it as recipient we store the contact object for later use
598 $contactobject = $object->contact;
599 }
600
601 $socobject = $object->thirdparty;
602
603 // Make substitution
604 $substitutionarray = array(
605 '__FROM_NAME__' => $this->emetteur->name,
606 '__FROM_EMAIL__' => $this->emetteur->email,
607 );
608 complete_substitutions_array($substitutionarray, $langs, $object);
609 // Call the ODTSubstitution hook
610 $parameters = array('file' => $file, 'object' => $object, 'outputlangs' => $outputlangs, 'substitutionarray' => &$substitutionarray);
611 $reshook = $hookmanager->executeHooks('ODTSubstitution', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
612
613 // Open and load template
614 require_once ODTPHP_PATH.'odf.php';
615 try {
616 $odfHandler = new Odf(
617 $srctemplatepath,
618 array(
619 'PATH_TO_TMP' => $conf->project->dir_temp,
620 'ZIP_PROXY' => getDolGlobalString('MAIN_ODF_ZIP_PROXY', 'PclZipProxy'), // PhpZipProxy or PclZipProxy. Got "bad compression method" error when using PhpZipProxy.
621 'DELIMITER_LEFT' => '{',
622 'DELIMITER_RIGHT' => '}'
623 )
624 );
625 } catch (Exception $e) {
626 $this->error = $e->getMessage();
627 dol_syslog($e->getMessage(), LOG_INFO);
628 return -1;
629 }
630 // After construction $odfHandler->contentXml contains content and
631 // [!-- BEGIN row.lines --]*[!-- END row.lines --] has been replaced by
632 // [!-- BEGIN lines --]*[!-- END lines --]
633
634 // Define substitution array
635 $substitutionarray = getCommonSubstitutionArray($outputlangs, 0, null, $object);
636 $array_object_from_properties = $this->get_substitutionarray_each_var_object($object, $outputlangs);
637 $array_objet = $this->get_substitutionarray_object($object, $outputlangs);
638 $array_user = $this->get_substitutionarray_user($user, $outputlangs);
639 $array_soc = $this->get_substitutionarray_mysoc($mysoc, $outputlangs);
640 $array_thirdparty = $this->get_substitutionarray_thirdparty($socobject, $outputlangs);
641 $array_other = $this->get_substitutionarray_other($outputlangs);
642 // retrieve contact information for use in object as contact_xxx tags
643 $array_project_contact = array();
644 if ($usecontact && is_object($contactobject)) {
645 $array_project_contact = $this->get_substitutionarray_contact($contactobject, $outputlangs, 'contact');
646 }
647
648 $tmparray = array_merge($substitutionarray, $array_object_from_properties, $array_user, $array_soc, $array_thirdparty, $array_objet, $array_other, $array_project_contact);
649 complete_substitutions_array($tmparray, $outputlangs, $object);
650
651 // Call the ODTSubstitution hook
652 $parameters = array('odfHandler' => &$odfHandler, 'file' => $file, 'object' => $object, 'outputlangs' => $outputlangs, 'substitutionarray' => &$tmparray);
653 $reshook = $hookmanager->executeHooks('ODTSubstitution', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
654
655 foreach ($tmparray as $key => $value) {
656 try {
657 if (preg_match('/logo$/', $key)) { // Image
658 if (file_exists($value)) {
659 $odfHandler->setImage($key, $value);
660 } else {
661 $odfHandler->setVars($key, 'ErrorFileNotFound', true, 'UTF-8');
662 }
663 } else { // Text
664 $odfHandler->setVars($key, $value, true, 'UTF-8');
665 }
666 } catch (OdfException $e) {
667 dol_syslog($e->getMessage(), LOG_INFO);
668 }
669 }
670
671 // Replace tags of lines for tasks
672 try {
673 $listlines = $odfHandler->setSegment('tasks');
674
675 $taskstatic = new Task($this->db);
676
677 // Security check
678 $socid = 0;
679 if (!empty($object->fk_soc)) {
680 $socid = $object->fk_soc;
681 }
682
683 $tasksarray = $taskstatic->getTasksArray(null, null, $object->id, $socid, 0);
684
685
686 foreach ($tasksarray as $task) {
687 $tmparray = $this->get_substitutionarray_tasks($task, $outputlangs);
688 //complete_substitutions_array($tmparray, $outputlangs, $object, $task, "completesubstitutionarray_lines");
689 foreach ($tmparray as $key => $val) {
690 try {
691 $listlines->setVars($key, $val, true, 'UTF-8');
692 } catch (SegmentException $e) {
693 dol_syslog($e->getMessage(), LOG_INFO);
694 }
695 }
696
697 $taskobj = new Task($this->db);
698 $taskobj->fetch($task->id);
699
700 // Replace tags of lines for contacts task
701 $sourcearray = array('internal', 'external');
702 $contact_arrray = array();
703 foreach ($sourcearray as $source) {
704 $contact_temp = $taskobj->liste_contact(-1, $source);
705 if ((is_array($contact_temp) && count($contact_temp) > 0)) {
706 $contact_arrray = array_merge($contact_arrray, $contact_temp);
707 }
708 }
709 if ((is_array($contact_arrray) && count($contact_arrray) > 0)) {
710 $listlinestaskres = $listlines->__get('tasksressources');
711
712 foreach ($contact_arrray as $contact) {
713 if ($contact['source'] == 'internal') {
714 $objectdetail = new User($this->db);
715 $objectdetail->fetch($contact['id']);
716 $contact['socname'] = $mysoc->name;
717 } elseif ($contact['source'] == 'external') {
718 $objectdetail = new Contact($this->db);
719 $objectdetail->fetch($contact['id']);
720
721 $soc = new Societe($this->db);
722 $soc->fetch($contact['socid']);
723 $contact['socname'] = $soc->name;
724 } else {
725 dol_syslog(get_class().'::'.__METHOD__.' Unexpected contact source:'.$contact['source'], LOG_ERR);
726 continue;
727 }
728 $contact['fullname'] = $objectdetail->getFullName($outputlangs, 1);
729
730 $tmparray = $this->get_substitutionarray_tasksressource($contact, $outputlangs);
731
732 foreach ($tmparray as $key => $val) {
733 try {
734 $listlinestaskres->setVars($key, $val, true, 'UTF-8');
735 } catch (SegmentException $e) {
736 dol_syslog($e->getMessage(), LOG_INFO);
737 }
738 }
739 $listlinestaskres->merge();
740 }
741 }
742
743 //Time resources
744 $sql = "SELECT t.rowid, t.element_date as task_date, t.element_duration as task_duration, t.fk_user, t.note";
745 $sql .= ", u.lastname, u.firstname, t.thm";
746 $sql .= " FROM ".MAIN_DB_PREFIX."element_time as t";
747 $sql .= " , ".MAIN_DB_PREFIX."user as u";
748 $sql .= " WHERE t.fk_element =".((int) $task->id);
749 $sql .= " AND t.elementtype = 'task'";
750 $sql .= " AND t.fk_user = u.rowid";
751 $sql .= " ORDER BY t.element_date DESC";
752
753 $resql = $this->db->query($sql);
754 if ($resql) {
755 $num = $this->db->num_rows($resql);
756 $i = 0;
757 $tasks = array();
758 $row = array();
759 $listlinestasktime = $listlines->__get('taskstimes');
760 if (empty($num)) {
761 $row['rowid'] = 0;
762 $row['task_date'] = 0;
763 $row['task_duration'] = 0;
764 //$row['$tasktime'] = '';
765 $row['note'] = '';
766 $row['fk_user'] = 0;
767 $row['name'] = '';
768 $row['firstname'] = '';
769 $row['fullcivname'] = '';
770 $row['amountht'] = 0;
771 $row['amountttc'] = 0;
772 $row['thm'] = 0;
773 $tmparray = $this->get_substitutionarray_taskstime($row, $outputlangs);
774 foreach ($tmparray as $key => $val) {
775 try {
776 $listlinestasktime->setVars($key, $val, true, 'UTF-8');
777 } catch (SegmentException $e) {
778 dol_syslog($e->getMessage(), LOG_INFO);
779 }
780 }
781 $listlinestasktime->merge();
782 }
783 while ($i < $num) {
784 $row = $this->db->fetch_array($resql);
785 if (!empty($row['fk_user'])) {
786 $objectdetail = new User($this->db);
787 $objectdetail->fetch($row['fk_user']);
788 $row['fullcivname'] = $objectdetail->getFullName($outputlangs, 1);
789 } else {
790 $row['fullcivname'] = '';
791 }
792
793 if (!empty($row['thm'])) {
794 $row['amountht'] = ($row['task_duration'] / 3600) * $row['thm'];
795 $defaultvat = get_default_tva($mysoc, $mysoc);
796 $row['amountttc'] = price2num($row['amountht'] * (1 + ($defaultvat / 100)), 'MT');
797 } else {
798 $row['amountht'] = 0;
799 $row['amountttc'] = 0;
800 $row['thm'] = 0;
801 }
802
803 $tmparray = $this->get_substitutionarray_taskstime($row, $outputlangs);
804
805 foreach ($tmparray as $key => $val) {
806 try {
807 $listlinestasktime->setVars($key, $val, true, 'UTF-8');
808 } catch (SegmentException $e) {
809 dol_syslog($e->getMessage(), LOG_INFO);
810 }
811 }
812 $listlinestasktime->merge();
813 $i++;
814 }
815 $this->db->free($resql);
816 }
817
818
819 // Replace tags of project files
820 $listtasksfiles = $listlines->__get('tasksfiles');
821
822 $upload_dir = $conf->project->dir_output.'/'.dol_sanitizeFileName($object->ref).'/'.dol_sanitizeFileName($task->ref);
823 $filearray = dol_dir_list($upload_dir, "files", 0, '', '(\.meta|_preview.*\.png)$', 'name', SORT_ASC, 1);
824
825
826 foreach ($filearray as $filedetail) {
827 $tmparray = $this->get_substitutionarray_task_file($filedetail, $outputlangs);
828 //dol_syslog(get_class($this).'::main $tmparray'.var_export($tmparray,true));
829 foreach ($tmparray as $key => $val) {
830 try {
831 $listtasksfiles->setVars($key, $val, true, 'UTF-8');
832 } catch (SegmentException $e) {
833 dol_syslog($e->getMessage(), LOG_INFO);
834 }
835 }
836 $listtasksfiles->merge();
837 }
838 $listlines->merge();
839 }
840 $odfHandler->mergeSegment($listlines);
841 } catch (OdfException $e) {
842 $ExceptionTrace = $e->getTrace();
843 // no segment defined on ODT is not an error
844 if ($ExceptionTrace[0]['function'] != 'setSegment') {
845 $this->error = $e->getMessage();
846 dol_syslog($this->error, LOG_WARNING);
847 return -1;
848 }
849 }
850
851 // Replace tags of project files
852 try {
853 $listlines = $odfHandler->setSegment('projectfiles');
854
855 $upload_dir = $conf->project->dir_output.'/'.dol_sanitizeFileName($object->ref);
856 $filearray = dol_dir_list($upload_dir, "files", 0, '', '(\.meta|_preview.*\.png)$', 'name', SORT_ASC, 1);
857
858 foreach ($filearray as $filedetail) {
859 //dol_syslog(get_class($this).'::main $filedetail'.var_export($filedetail,true));
860 $tmparray = $this->get_substitutionarray_project_file($filedetail, $outputlangs);
861
862 foreach ($tmparray as $key => $val) {
863 try {
864 $listlines->setVars($key, $val, true, 'UTF-8');
865 } catch (SegmentException $e) {
866 dol_syslog($e->getMessage(), LOG_INFO);
867 }
868 }
869 $listlines->merge();
870 }
871 $odfHandler->mergeSegment($listlines);
872 } catch (OdfException $e) {
873 $this->error = $e->getMessage();
874 dol_syslog($this->error, LOG_WARNING);
875 return -1;
876 }
877
878 // Replace tags of lines for contacts
879 $sourcearray = array('internal', 'external');
880 $contact_arrray = array();
881 foreach ($sourcearray as $source) {
882 $contact_temp = $object->liste_contact(-1, $source);
883 if ((is_array($contact_temp) && count($contact_temp) > 0)) {
884 $contact_arrray = array_merge($contact_arrray, $contact_temp);
885 }
886 }
887 if ((is_array($contact_arrray) && count($contact_arrray) > 0)) {
888 try {
889 $listlines = $odfHandler->setSegment('projectcontacts');
890
891 foreach ($contact_arrray as $contact) {
892 if ($contact['source'] == 'internal') {
893 $objectdetail = new User($this->db);
894 $objectdetail->fetch($contact['id']);
895 $contact['socname'] = $mysoc->name;
896 } elseif ($contact['source'] == 'external') {
897 $objectdetail = new Contact($this->db);
898 $objectdetail->fetch($contact['id']);
899
900 $soc = new Societe($this->db);
901 $soc->fetch($contact['socid']);
902 $contact['socname'] = $soc->name;
903 }
904 $contact['fullname'] = $objectdetail->getFullName($outputlangs, 1);
905
906 $tmparray = $this->get_substitutionarray_project_contacts($contact, $outputlangs);
907 foreach ($tmparray as $key => $val) {
908 try {
909 $listlines->setVars($key, $val, true, 'UTF-8');
910 } catch (SegmentException $e) {
911 dol_syslog($e->getMessage(), LOG_INFO);
912 }
913 }
914 $listlines->merge();
915 }
916 $odfHandler->mergeSegment($listlines);
917 } catch (OdfException $e) {
918 $this->error = $e->getMessage();
919 dol_syslog($this->error, LOG_WARNING);
920 return -1;
921 }
922 }
923
924 //List of referent
925
926 $listofreferent = array(
927 'propal' => array(
928 'title' => "ListProposalsAssociatedProject",
929 'class' => 'Propal',
930 'table' => 'propal',
931 'test' => isModEnabled('propal') && $user->hasRight('propal', 'lire')
932 ),
933 'order' => array(
934 'title' => "ListOrdersAssociatedProject",
935 'class' => 'Commande',
936 'table' => 'commande',
937 'test' => isModEnabled('order') && $user->hasRight('commande', 'lire')
938 ),
939 'invoice' => array(
940 'title' => "ListInvoicesAssociatedProject",
941 'class' => 'Facture',
942 'table' => 'facture',
943 'test' => isModEnabled('invoice') && $user->hasRight('facture', 'lire')
944 ),
945 'invoice_predefined' => array(
946 'title' => "ListPredefinedInvoicesAssociatedProject",
947 'class' => 'FactureRec',
948 'table' => 'facture_rec',
949 'test' => isModEnabled('invoice') && $user->hasRight('facture', 'lire')
950 ),
951 'proposal_supplier' => array(
952 'title' => "ListSupplierProposalsAssociatedProject",
953 'class' => 'SupplierProposal',
954 'table' => 'supplier_proposal',
955 'test' => isModEnabled('supplier_proposal') && $user->hasRight('supplier_proposal', 'lire')
956 ),
957 'order_supplier' => array(
958 'title' => "ListSupplierOrdersAssociatedProject",
959 'table' => 'commande_fournisseur',
960 'class' => 'CommandeFournisseur',
961 'test' => (isModEnabled("fournisseur") && !getDolGlobalString('MAIN_USE_NEW_SUPPLIERMOD') && $user->hasRight('fournisseur', 'commande', 'lire')) || (isModEnabled("supplier_order") && $user->hasRight('supplier_order', 'lire'))
962 ),
963 'invoice_supplier' => array(
964 'title' => "ListSupplierInvoicesAssociatedProject",
965 'table' => 'facture_fourn',
966 'class' => 'FactureFournisseur',
967 'test' => (isModEnabled("fournisseur") && !getDolGlobalString('MAIN_USE_NEW_SUPPLIERMOD') && $user->hasRight('fournisseur', 'facture', 'lire')) || (isModEnabled("supplier_invoice") && $user->hasRight('supplier_invoice', 'lire'))
968 ),
969 'contract' => array(
970 'title' => "ListContractAssociatedProject",
971 'class' => 'Contrat',
972 'table' => 'contrat',
973 'test' => isModEnabled('contract') && $user->hasRight('contrat', 'lire')
974 ),
975 'intervention' => array(
976 'title' => "ListFichinterAssociatedProject",
977 'class' => 'Fichinter',
978 'table' => 'fichinter',
979 'disableamount' => 1,
980 'test' => isModEnabled('intervention') && $user->hasRight('ficheinter', 'lire')
981 ),
982 'shipping' => array(
983 'title' => "ListShippingAssociatedProject",
984 'class' => 'Expedition',
985 'table' => 'expedition',
986 'disableamount' => 1,
987 'test' => isModEnabled('shipping') && $user->hasRight('expedition', 'lire')
988 ),
989 'trip' => array(
990 'title' => "ListTripAssociatedProject",
991 'class' => 'Deplacement',
992 'table' => 'deplacement',
993 'disableamount' => 1,
994 'test' => isModEnabled('deplacement') && $user->hasRight('deplacement', 'lire')
995 ),
996 'expensereport' => array(
997 'title' => "ListExpenseReportsAssociatedProject",
998 'class' => 'ExpenseReportLine',
999 'table' => 'expensereport_det',
1000 'test' => isModEnabled('expensereport') && $user->hasRight('expensereport', 'lire')
1001 ),
1002 'donation' => array(
1003 'title' => "ListDonationsAssociatedProject",
1004 'class' => 'Don',
1005 'table' => 'don',
1006 'test' => isModEnabled('don') && $user->hasRight('don', 'lire')
1007 ),
1008 'loan' => array(
1009 'title' => "ListLoanAssociatedProject",
1010 'class' => 'Loan',
1011 'table' => 'loan',
1012 'test' => isModEnabled('loan') && $user->hasRight('loan', 'read')
1013 ),
1014 'chargesociales' => array(
1015 'title' => "ListSocialContributionAssociatedProject",
1016 'class' => 'ChargeSociales',
1017 'table' => 'chargesociales',
1018 'urlnew' => DOL_URL_ROOT.'/compta/sociales/card.php?action=create&projectid='.$object->id,
1019 'test' => isModEnabled('tax') && $user->hasRight('tax', 'charges', 'lire')
1020 ),
1021 'stock_mouvement' => array(
1022 'title' => "ListMouvementStockProject",
1023 'class' => 'MouvementStock',
1024 'table' => 'stock_mouvement',
1025 'test' => (isModEnabled('stock') && $user->hasRight('stock', 'mouvement', 'lire') && getDolGlobalString('STOCK_MOVEMENT_INTO_PROJECT_OVERVIEW'))
1026 ),
1027 'agenda' => array(
1028 'title' => "ListActionsAssociatedProject",
1029 'class' => 'ActionComm',
1030 'table' => 'actioncomm',
1031 'disableamount' => 1,
1032 'test' => isModEnabled('agenda') && $user->hasRight('agenda', 'allactions', 'lire')
1033 ),
1034 );
1035
1036 // Insert list of objects into the project
1037 try {
1038 $listlines = $odfHandler->setSegment('projectrefs');
1039
1040 foreach ($listofreferent as $keyref => $valueref) {
1041 $title = $valueref['title'];
1042 $tablename = $valueref['table'];
1043 $classname = $valueref['class'];
1044 $qualified = $valueref['test'];
1045 if ($qualified) {
1046 $elementarray = $object->get_element_list($keyref, $tablename);
1047 if (count($elementarray) > 0 && is_array($elementarray)) {
1048 $total_ht = 0;
1049 $total_ttc = 0;
1050 $num = count($elementarray);
1051 for ($i = 0; $i < $num; $i++) {
1052 $ref_array = array();
1053 $ref_array['type'] = (string) $langs->trans($classname);
1054
1055 $element = new $classname($this->db);
1056 $element->fetch($elementarray[$i]);
1057 $element->fetch_thirdparty();
1058
1059 //Ref object
1060 $ref_array['ref'] = $element->ref;
1061
1062 //Date object
1063 $dateref = $element->date;
1064 if (empty($dateref)) {
1065 $dateref = $element->datep;
1066 }
1067 if (empty($dateref)) {
1068 $dateref = $element->date_contrat;
1069 }
1070 $ref_array['date'] = (string) $dateref;
1071
1072 //Soc object
1073 if (is_object($element->thirdparty)) {
1074 $ref_array['socname'] = $element->thirdparty->name;
1075 } else {
1076 $ref_array['socname'] = '';
1077 }
1078
1079 //Amount object
1080 if (empty($valueref['disableamount'])) {
1081 if (!empty($element->total_ht)) {
1082 $ref_array['amountht'] = $element->total_ht;
1083 $ref_array['amountttc'] = $element->total_ttc;
1084 } else {
1085 $ref_array['amountht'] = 0;
1086 $ref_array['amountttc'] = 0;
1087 }
1088 } else {
1089 $ref_array['amountht'] = '';
1090 $ref_array['amountttc'] = '';
1091 }
1092
1093 $ref_array['status'] = $element->getLibStatut(0);
1094
1095 $tmparray = $this->get_substitutionarray_project_reference($ref_array, $outputlangs);
1096
1097 foreach ($tmparray as $key => $val) {
1098 try {
1099 $listlines->setVars($key, $val, true, 'UTF-8');
1100 } catch (SegmentException $e) {
1101 dol_syslog($e->getMessage(), LOG_INFO);
1102 }
1103 }
1104 $listlines->merge();
1105 }
1106 }
1107 }
1108 $odfHandler->mergeSegment($listlines);
1109 }
1110 } catch (OdfExceptionSegmentNotFound $e) {
1111 // Do nothing
1112 } catch (OdfException $e) {
1113 $this->error = $e->getMessage();
1114 dol_syslog($this->error, LOG_WARNING);
1115 return -1;
1116 }
1117
1118 // Replace labels translated
1119 $tmparray = $outputlangs->get_translations_for_substitutions();
1120 foreach ($tmparray as $key => $value) {
1121 try {
1122 $odfHandler->setVars($key, $value, true, 'UTF-8');
1123 } catch (OdfException $e) {
1124 dol_syslog($e->getMessage(), LOG_INFO);
1125 }
1126 }
1127
1128 // Call the beforeODTSave hook
1129 $parameters = array('odfHandler' => &$odfHandler, 'file' => $file, 'object' => $object, 'outputlangs' => $outputlangs, 'substitutionarray' => &$tmparray);
1130 $reshook = $hookmanager->executeHooks('beforeODTSave', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
1131
1132
1133 // Write new file
1134 if (getDolGlobalString('MAIN_ODT_AS_PDF')) {
1135 try {
1136 $odfHandler->exportAsAttachedPDF($file);
1137 } catch (Exception $e) {
1138 $this->error = $e->getMessage();
1139 return -1;
1140 }
1141 } else {
1142 try {
1143 $odfHandler->saveToDisk($file);
1144 } catch (Exception $e) {
1145 $this->error = $e->getMessage();
1146 dol_syslog($e->getMessage(), LOG_INFO);
1147 return -1;
1148 }
1149 }
1150 $parameters = array('odfHandler' => &$odfHandler, 'file' => $file, 'object' => $object, 'outputlangs' => $outputlangs, 'substitutionarray' => &$tmparray);
1151 $reshook = $hookmanager->executeHooks('afterODTCreation', $parameters, $this, $action); // Note that $action and $object may have been modified by some hooks
1152
1153 dolChmod($file);
1154
1155 $odfHandler = null; // Destroy object
1156
1157 $this->result = array('fullpath' => $file);
1158
1159 return 1; // Success
1160 } else {
1161 $this->error = $langs->transnoentities("ErrorCanNotCreateDir", $dir);
1162 return -1;
1163 }
1164 }
1165
1166 return -1;
1167 }
1168}
$id
Definition account.php:39
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:58
get_substitutionarray_each_var_object(&$object, $outputlangs, $recursive=1)
Define array with couple substitution key => substitution value.
get_substitutionarray_mysoc($mysoc, $outputlangs)
Define array with couple substitution key => substitution value.
get_substitutionarray_contact($object, $outputlangs, $array_key='object')
Define array with couple substitution key => substitution value.
get_substitutionarray_other($outputlangs)
Define array with couple substitution key => substitution value.
fill_substitutionarray_with_extrafields($object, $array_to_fill, $extrafields, $array_key, $outputlangs)
Fill array with couple extrafield key => extrafield value Note that vars into substitutions array are...
get_substitutionarray_thirdparty($object, $outputlangs, $array_key='company')
Define array with couple substitution key => substitution value For example {company_name}...
get_substitutionarray_user($user, $outputlangs)
Define array with couple substitution key => substitution value.
Class to manage contact/addresses.
Class to manage standard extra fields.
Class to manage generation of HTML components Only common components must be here.
Class to manage hooks.
Parent class for projects models.
Class to manage projects.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage tasks.
Class to manage Dolibarr users.
Class to build documents using ODF templates generator.
get_substitutionarray_tasks(Task $task, $outputlangs)
Define array with couple substitution key => substitution value.
get_substitutionarray_task_file($file, $outputlangs)
Define array with couple substitution key => substitution value.
get_substitutionarray_project_file($file, $outputlangs)
Define array with couple substitution key => substitution value.
get_substitutionarray_tasksressource($taskresource, $outputlangs)
Define array with couple substitution key => substitution value.
get_substitutionarray_taskstime($tasktime, $outputlangs)
Define array with couple substitution key => substitution value.
write_file($object, $outputlangs, $srctemplatepath='')
Function to build a document on disk using the generic odt module.
get_substitutionarray_project_contacts($contact, $outputlangs)
Define array with couple substitution key => substitution value.
get_substitutionarray_object($object, $outputlangs, $array_key='object')
Define array with couple substitution key => substitution value.
get_substitutionarray_project_reference($refdetail, $outputlangs)
Define array with couple substitution key => substitution value.
info($langs)
Return description of a module.
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:242
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_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
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 '.
getCallerInfoString()
Get caller info as a string that can be appended to a log message.
price($amount, $form=0, $outlangs='', $trunc=1, $rounding=-1, $forcerounding=-1, $currency_code='')
Function to format a value into an amount for visual output Function used into PDF and HTML pages.
dolChmod($filepath, $newmask='')
Change mod of a file.
dol_now($mode='auto')
Return date for now.
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).
newToken()
Return the value of token currently saved into session with name 'newtoken'.
complete_substitutions_array(&$substitutionarray, $outputlangs, $object=null, $parameters=null, $callfunc="completesubstitutionarray")
Complete the $substitutionarray with more entries coming from external module that had set the "subst...
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...
getCommonSubstitutionArray($outputlangs, $onlykey=0, $exclude=null, $object=null, $include=null)
Return array of possible common substitutions.
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
get_default_tva(Societe $thirdparty_seller, Societe $thirdparty_buyer, $idprod=0, $idprodfournprice=0)
Function that return vat rate of a product line (according to seller, buyer and product vat rate) VAT...
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
dol_mkdir($dir, $dataroot='', $newmask='')
Creation of a directory (this can create recursive subdir)
if(preg_match('/crypted:/i', $dolibarr_main_db_pass)||!empty($dolibarr_main_db_encrypted_pass)) $conf db type
Definition repair.php:137
$conf db name
Only used if Module[ID]Name translation string is not found.
Definition repair.php:140
getMaxFileSizeArray()
Return the max allowed for file upload.