diff --git a/htdocs/compta/bank/annuel.php b/htdocs/compta/bank/annuel.php index 610cf17498c..177855c9302 100644 --- a/htdocs/compta/bank/annuel.php +++ b/htdocs/compta/bank/annuel.php @@ -39,6 +39,9 @@ $HEIGHT = DolGraph::getDefaultGraphSizeForStats('height', 160); $id = GETPOST('account') ?GETPOST('account', 'alpha') : GETPOST('id'); $ref = GETPOST('ref'); +// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context +$hookmanager->initHooks(array('bankannualreport', 'globalcard')); + // Security check $fieldvalue = (!empty($id) ? $id : (!empty($ref) ? $ref : '')); $fieldtype = (!empty($ref) ? 'ref' : 'rowid'); diff --git a/htdocs/compta/bank/document.php b/htdocs/compta/bank/document.php index 595d627609b..0960b984c04 100644 --- a/htdocs/compta/bank/document.php +++ b/htdocs/compta/bank/document.php @@ -38,6 +38,9 @@ $ref = GETPOST('ref', 'alpha'); $action = GETPOST('action', 'aZ09'); $confirm = GETPOST('confirm', 'alpha'); +// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context +$hookmanager->initHooks(array('bankaccountdocuments', 'globalcard')); + // Security check if ($user->socid) { $action = ''; diff --git a/htdocs/compta/bank/graph.php b/htdocs/compta/bank/graph.php index a3fd0b0b15b..c11e13f1e71 100644 --- a/htdocs/compta/bank/graph.php +++ b/htdocs/compta/bank/graph.php @@ -35,6 +35,9 @@ $langs->loadLangs(array('banks', 'categories')); $WIDTH = DolGraph::getDefaultGraphSizeForStats('width', 768); $HEIGHT = DolGraph::getDefaultGraphSizeForStats('height', 200); +// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context +$hookmanager->initHooks(array('bankstats', 'globalcard')); + // Security check if (GETPOST('account') || GETPOST('ref')) { $id = GETPOST('account') ? GETPOST('account') : GETPOST('ref'); diff --git a/htdocs/compta/bank/releve.php b/htdocs/compta/bank/releve.php index 8f5e7f29069..2e532984d99 100644 --- a/htdocs/compta/bank/releve.php +++ b/htdocs/compta/bank/releve.php @@ -62,6 +62,9 @@ $newbankreceipt = GETPOST('newbankreceipt', 'alpha'); $rel = GETPOST("rel", 'alphanohtml'); $backtopage = GETPOST('backtopage', 'alpha'); +// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context +$hookmanager->initHooks(array('bankaccountstatement', 'globalcard')); + // Security check $fieldid = (!empty($ref) ? $ref : $id); $fieldname = (!empty($ref) ? 'ref' : 'rowid'); diff --git a/htdocs/compta/facture/class/facture.class.php b/htdocs/compta/facture/class/facture.class.php index 7cc4be35f70..87d28de8756 100644 --- a/htdocs/compta/facture/class/facture.class.php +++ b/htdocs/compta/facture/class/facture.class.php @@ -171,6 +171,8 @@ class Facture extends CommonInvoice public $total_ttc; public $revenuestamp; + public $resteapayer; + /** * ! Closing after partial payment: discount_vat, badcustomer or badsupplier, bankcharge, other * ! Closing when no payment: replaced, abandoned diff --git a/htdocs/core/class/commonobject.class.php b/htdocs/core/class/commonobject.class.php index 23e35abfc13..80011c8e885 100644 --- a/htdocs/core/class/commonobject.class.php +++ b/htdocs/core/class/commonobject.class.php @@ -6270,7 +6270,7 @@ abstract class CommonObject case 'date': case 'datetime': // If data is a string instead of a timestamp, we convert it - if (!is_int($this->array_options[$key])) { + if (!is_numeric($this->array_options[$key]) || $this->array_options[$key] != intval($this->array_options[$key])) { $this->array_options[$key] = strtotime($this->array_options[$key]); } $new_array_options[$key] = $this->db->idate($this->array_options[$key]); diff --git a/htdocs/core/db/DoliDB.class.php b/htdocs/core/db/DoliDB.class.php index 16b2fd956fe..e2659e224a4 100644 --- a/htdocs/core/db/DoliDB.class.php +++ b/htdocs/core/db/DoliDB.class.php @@ -107,6 +107,25 @@ abstract class DoliDB implements Database return ''; } + + /** + * Format a SQL REGEXP + * + * @param string $subject string tested + * @param string $pattern SQL pattern to match + * @param string $sqlstring whether or not the string being tested is an SQL expression + * @return string SQL string + */ + public function regexpsql($subject, $pattern, $sqlstring = false) + { + if ($sqlstring) { + return "(". $subject ." REGEXP '" . $pattern . "')"; + } + + return "('". $subject ."' REGEXP '" . $pattern . "')"; + } + + /** * Convert (by PHP) a GM Timestamp date into a string date with PHP server TZ to insert into a date field. * Function to use to build INSERT, UPDATE or WHERE predica diff --git a/htdocs/core/db/pgsql.class.php b/htdocs/core/db/pgsql.class.php index 0515a043fd1..a67feeffe64 100644 --- a/htdocs/core/db/pgsql.class.php +++ b/htdocs/core/db/pgsql.class.php @@ -757,6 +757,24 @@ class DoliDBPgsql extends DoliDB return '(CASE WHEN '.$test.' THEN '.$resok.' ELSE '.$resko.' END)'; } + /** + * Format a SQL REGEXP + * + * @param string $subject string tested + * @param string $pattern SQL pattern to match + * @param string $sqlstring whether or not the string being tested is an SQL expression + * @return string SQL string + */ + public function regexpsql($subject, $pattern, $sqlstring = false) + { + if ($sqlstring) { + return "(". $subject ." ~ '" . $pattern . "')"; + } + + return "('". $subject ."' ~ '" . $pattern . "')"; + } + + /** * Renvoie le code erreur generique de l'operation precedente. * diff --git a/htdocs/core/lib/functions2.lib.php b/htdocs/core/lib/functions2.lib.php index 8003c414dcb..0168bb55db3 100644 --- a/htdocs/core/lib/functions2.lib.php +++ b/htdocs/core/lib/functions2.lib.php @@ -1282,6 +1282,11 @@ function get_next_value($db, $mask, $table, $field, $where = '', $objsoc = '', $ $sql .= " FROM ".MAIN_DB_PREFIX.$table; $sql .= " WHERE ".$field." LIKE '".$db->escape($maskLike)."'"; $sql .= " AND ".$field." NOT LIKE '(PROV%)'"; + + // To ensure that all variables within the MAX() brackets are integers + $sql .= " AND ". $db->regexpsql($sqlstring, '^[0-9]+$', true); + + if ($bentityon) { // only if entity enable $sql .= " AND entity IN (".getEntity($sharetable).")"; } elseif (!empty($forceentity)) { @@ -2234,7 +2239,11 @@ function dolGetElementUrl($objectid, $objecttype, $withpicto = 0, $option = '') $classpath = 'compta/facture/class'; $classfile = 'facture-rec'; $classname = 'FactureRec'; - $module='facture'; + $module = 'facture'; + } elseif ($objecttype == 'mailing') { + $classpath = 'comm/mailing/class'; + $classfile = 'mailing'; + $classname = 'Mailing'; } if (isModEnabled($module)) { diff --git a/htdocs/core/modules/modProduct.class.php b/htdocs/core/modules/modProduct.class.php index 940c4fb2f9a..5224f82a2f5 100644 --- a/htdocs/core/modules/modProduct.class.php +++ b/htdocs/core/modules/modProduct.class.php @@ -860,7 +860,7 @@ class modProduct extends DolibarrModules )); } - $this->import_updatekeys_array[$r] = array('sp.fk_product'=>'ProductOrService', 'sp.ref_fourn'=>'SupplierRef', 'sp.fk_soc'=>'Supplier'); + $this->import_updatekeys_array[$r] = array('sp.fk_product'=>'ProductOrService', 'sp.ref_fourn'=>'SupplierRef', 'sp.fk_soc'=>'Supplier', 'sp.quantity'=>"QtyMin"); } if (!empty($conf->global->PRODUIT_MULTIPRICES)) { diff --git a/htdocs/core/triggers/interface_50_modAgenda_ActionsAuto.class.php b/htdocs/core/triggers/interface_50_modAgenda_ActionsAuto.class.php index f31a4c2c93e..e3f798dec62 100644 --- a/htdocs/core/triggers/interface_50_modAgenda_ActionsAuto.class.php +++ b/htdocs/core/triggers/interface_50_modAgenda_ActionsAuto.class.php @@ -742,7 +742,7 @@ class InterfaceActionsAuto extends DolibarrTriggers if (!is_object($member)) { // This should not happen include_once DOL_DOCUMENT_ROOT.'/adherents/class/adherent.class.php'; $member = new Adherent($this->db); - $member->fetch($this->fk_adherent); + $member->fetch($object->fk_adherent); } if (empty($object->actionmsg2)) { diff --git a/htdocs/install/mysql/migration/16.0.0-17.0.0.sql b/htdocs/install/mysql/migration/16.0.0-17.0.0.sql index 7ee97826b87..3a9d02c8583 100644 --- a/htdocs/install/mysql/migration/16.0.0-17.0.0.sql +++ b/htdocs/install/mysql/migration/16.0.0-17.0.0.sql @@ -54,6 +54,8 @@ ALTER TABLE llx_user DROP COLUMN idpers3; UPDATE llx_c_actioncomm SET type = 'system' WHERE code = 'AC_OTH'; +ALTER TABLE llx_opensurvey_user_studs MODIFY reponses VARCHAR(200) NOT NULL; + -- v17 ALTER TABLE llx_mailing_cibles MODIFY COLUMN source_type varchar(32); diff --git a/htdocs/install/mysql/tables/llx_opensurvey_user_studs-opensurvey.sql b/htdocs/install/mysql/tables/llx_opensurvey_user_studs-opensurvey.sql index d0d1c2a06b8..e139816c3fa 100644 --- a/htdocs/install/mysql/tables/llx_opensurvey_user_studs-opensurvey.sql +++ b/htdocs/install/mysql/tables/llx_opensurvey_user_studs-opensurvey.sql @@ -19,7 +19,7 @@ CREATE TABLE llx_opensurvey_user_studs ( id_users INTEGER NOT NULL AUTO_INCREMENT PRIMARY KEY, nom VARCHAR(64) NOT NULL, id_sondage VARCHAR(16) NOT NULL, - reponses VARCHAR(100) NOT NULL, -- Not used for 'F' surveys + reponses VARCHAR(200) NOT NULL, -- Not used for 'F' surveys tms timestamp DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP date_creation datetime NOT NULL, ) ENGINE=innodb; diff --git a/htdocs/loan/info.php b/htdocs/loan/info.php index 49618d0f46c..188a61c61e6 100644 --- a/htdocs/loan/info.php +++ b/htdocs/loan/info.php @@ -102,8 +102,6 @@ $morehtmlref .= ''; $linkback = ''.$langs->trans("BackToList").''; -$object->totalpaid = $totalpaid; // To give a chance to dol_banner_tab to use already paid amount to show correct status - dol_banner_tab($object, 'id', $linkback, 1, 'rowid', 'ref', $morehtmlref, '', 0, '', $morehtmlright); print '
'; diff --git a/htdocs/opensurvey/wizard/choix_date.php b/htdocs/opensurvey/wizard/choix_date.php index 46983829c3b..d8f89b18e16 100644 --- a/htdocs/opensurvey/wizard/choix_date.php +++ b/htdocs/opensurvey/wizard/choix_date.php @@ -37,6 +37,7 @@ if (!$user->rights->opensurvey->write) { $_SESSION["formatsondage"] = "D"; $erreur = false; +$erreurNbchoice = 0; /* * Actions @@ -49,114 +50,120 @@ if (GETPOST('confirmation')) { $nbofchoice = count($_SESSION["totalchoixjour"]); $errheure = array(); - for ($i = 0; $i < $nbofchoice; $i++) { - // Show hours choices - for ($j = 0; $j < $_SESSION["nbrecaseshoraires"]; $j++) { - $horairesi = GETPOST("horaires".$i); - $_SESSION["horaires$i"][$j] = $horairesi[$j]; - - $tmphorairesi = GETPOST('horaires'.$i, 'array'); - - if (!is_array($tmphorairesi)) { - $errheure[$i][$j] = true; - $erreur = true; - continue; - } - - // A range like 8:00-11:00 - $creneaux = array(); - $heures = array(); - if (preg_match("/(\d{1,2}:\d{2})-(\d{1,2}:\d{2})/", $tmphorairesi[$j], $creneaux)) { - //on recupere les deux parties du preg_match qu'on redécoupe autour des ":" - $debutcreneau = explode(":", $creneaux[1]); - $fincreneau = explode(":", $creneaux[2]); - - //comparaison des heures de fin et de debut - //si correctes, on entre les données dans la variables de session - if ($debutcreneau[0] < 24 && $fincreneau[0] < 24 && $debutcreneau[1] < 60 && $fincreneau[1] < 60 && ($debutcreneau[0] < $fincreneau[0] || ($debutcreneau[0] == $fincreneau[0] && $debutcreneau[1] < $fincreneau[1]))) { - $_SESSION["horaires$i"][$j] = $creneaux[1].'-'.$creneaux[2]; - } else { //sinon message d'erreur et nettoyage de la case - $errheure[$i][$j] = true; - $erreur = true; - } - } elseif (preg_match(";^(\d{1,2}h\d{0,2})-(\d{1,2}h\d{0,2})$;i", $tmphorairesi[$j], $creneaux)) { //si c'est un creneau type 8h00-11h00 - //on recupere les deux parties du preg_match qu'on redécoupe autour des "H" - $debutcreneau = preg_split("/h/i", $creneaux[1]); - $fincreneau = preg_split("/h/i", $creneaux[2]); - - //comparaison des heures de fin et de debut - //si correctes, on entre les données dans la variables de session - if ($debutcreneau[0] < 24 && $fincreneau[0] < 24 && $debutcreneau[1] < 60 && $fincreneau[1] < 60 && ($debutcreneau[0] < $fincreneau[0] || ($debutcreneau[0] == $fincreneau[0] && $debutcreneau[1] < $fincreneau[1]))) { - $_SESSION["horaires$i"][$j] = $creneaux[1].'-'.$creneaux[2]; - } else { //sinon message d'erreur et nettoyage de la case - $errheure[$i][$j] = true; - $erreur = true; - } - } elseif (preg_match(";^(\d{1,2}):(\d{2})$;", $tmphorairesi[$j], $heures)) { //si c'est une heure simple type 8:00 - //si valeures correctes, on entre les données dans la variables de session - if ($heures[1] < 24 && $heures[2] < 60) { - $_SESSION["horaires$i"][$j] = $heures[0]; - } else { //sinon message d'erreur et nettoyage de la case - $errheure[$i][$j] = true; - $erreur = true; - } - } elseif (preg_match(";^(\d{1,2})h(\d{0,2})$;i", $tmphorairesi[$j], $heures)) { //si c'est une heure encore plus simple type 8h - //si valeures correctes, on entre les données dans la variables de session - if ($heures[1] < 24 && $heures[2] < 60) { - $_SESSION["horaires$i"][$j] = $heures[0]; - } else { //sinon message d'erreur et nettoyage de la case - $errheure[$i][$j] = true; - $erreur = true; - } - } elseif (preg_match(";^(\d{1,2})-(\d{1,2})$;", $tmphorairesi[$j], $heures)) { //si c'est un creneau simple type 8-11 - //si valeures correctes, on entre les données dans la variables de session - if ($heures[1] < $heures[2] && $heures[1] < 24 && $heures[2] < 24) { - $_SESSION["horaires$i"][$j] = $heures[0]; - } else { //sinon message d'erreur et nettoyage de la case - $errheure[$i][$j] = true; - $erreur = true; - } - } elseif (preg_match(";^(\d{1,2})h-(\d{1,2})h$;", $tmphorairesi[$j], $heures)) { //si c'est un creneau H type 8h-11h - //si valeures correctes, on entre les données dans la variables de session - if ($heures[1] < $heures[2] && $heures[1] < 24 && $heures[2] < 24) { - $_SESSION["horaires$i"][$j] = $heures[0]; - } else { //sinon message d'erreur et nettoyage de la case - $errheure[$i][$j] = true; - $erreur = true; - } - } elseif ($tmphorairesi[$j] == "") { //Si la case est vide - unset($_SESSION["horaires$i"][$j]); - } else { //pour tout autre format, message d'erreur - $errheure[$i][$j] = true; - $erreur = true; - } - - if (issetAndNoEmpty('horaires'.$i, $_SESSION) === false || issetAndNoEmpty($j, $_SESSION['horaires'.$i]) === false) { - if (issetAndNoEmpty('horaires'.$i, $_SESSION) === true) { - $_SESSION["horaires$i"][$j] = ''; - } else { - $_SESSION["horaires$i"] = array(); - $_SESSION["horaires$i"][$j] = ''; - } - } - } - - if ($_SESSION["horaires$i"][0] == "" && $_SESSION["horaires$i"][1] == "" && $_SESSION["horaires$i"][2] == "" && $_SESSION["horaires$i"][3] == "" && $_SESSION["horaires$i"][4] == "") { - $choixdate .= ","; - $choixdate .= $_SESSION["totalchoixjour"][$i]; - } else { + if ($nbofchoice * $_SESSION["nbrecaseshoraires"] > 200) { + setEventMessages($langs->trans("ErrorFieldTooLong"), null, 'errors'); + $erreurNb++; + } else { + for ($i = 0; $i < $nbofchoice; $i++) { + // Show hours choices for ($j = 0; $j < $_SESSION["nbrecaseshoraires"]; $j++) { - if ($_SESSION["horaires$i"][$j] != "") { - $choixdate .= ","; - $choixdate .= $_SESSION["totalchoixjour"][$i]; - $choixdate .= "@"; - // On remplace la virgule et l'arobase pour ne pas avoir de problème par la suite - $choixdate .= str_replace(array(',', '@'), array(',', '@'), $_SESSION["horaires$i"][$j]); + $horairesi = GETPOST("horaires".$i); + $_SESSION["horaires$i"][$j] = $horairesi[$j]; + + $tmphorairesi = GETPOST('horaires'.$i, 'array'); + + if (!is_array($tmphorairesi)) { + $errheure[$i][$j] = true; + $erreur = true; + continue; + } + + // A range like 8:00-11:00 + $creneaux = array(); + $heures = array(); + if (preg_match("/(\d{1,2}:\d{2})-(\d{1,2}:\d{2})/", $tmphorairesi[$j], $creneaux)) { + //on recupere les deux parties du preg_match qu'on redécoupe autour des ":" + $debutcreneau = explode(":", $creneaux[1]); + $fincreneau = explode(":", $creneaux[2]); + + //comparaison des heures de fin et de debut + //si correctes, on entre les données dans la variables de session + if ($debutcreneau[0] < 24 && $fincreneau[0] < 24 && $debutcreneau[1] < 60 && $fincreneau[1] < 60 && ($debutcreneau[0] < $fincreneau[0] || ($debutcreneau[0] == $fincreneau[0] && $debutcreneau[1] < $fincreneau[1]))) { + $_SESSION["horaires$i"][$j] = $creneaux[1].'-'.$creneaux[2]; + } else { //sinon message d'erreur et nettoyage de la case + $errheure[$i][$j] = true; + $erreur = true; + } + } elseif (preg_match(";^(\d{1,2}h\d{0,2})-(\d{1,2}h\d{0,2})$;i", $tmphorairesi[$j], $creneaux)) { //si c'est un creneau type 8h00-11h00 + //on recupere les deux parties du preg_match qu'on redécoupe autour des "H" + $debutcreneau = preg_split("/h/i", $creneaux[1]); + $fincreneau = preg_split("/h/i", $creneaux[2]); + + //comparaison des heures de fin et de debut + //si correctes, on entre les données dans la variables de session + if ($debutcreneau[0] < 24 && $fincreneau[0] < 24 && $debutcreneau[1] < 60 && $fincreneau[1] < 60 && ($debutcreneau[0] < $fincreneau[0] || ($debutcreneau[0] == $fincreneau[0] && $debutcreneau[1] < $fincreneau[1]))) { + $_SESSION["horaires$i"][$j] = $creneaux[1].'-'.$creneaux[2]; + } else { //sinon message d'erreur et nettoyage de la case + $errheure[$i][$j] = true; + $erreur = true; + } + } elseif (preg_match(";^(\d{1,2}):(\d{2})$;", $tmphorairesi[$j], $heures)) { //si c'est une heure simple type 8:00 + //si valeures correctes, on entre les données dans la variables de session + if ($heures[1] < 24 && $heures[2] < 60) { + $_SESSION["horaires$i"][$j] = $heures[0]; + } else { //sinon message d'erreur et nettoyage de la case + $errheure[$i][$j] = true; + $erreur = true; + } + } elseif (preg_match(";^(\d{1,2})h(\d{0,2})$;i", $tmphorairesi[$j], $heures)) { //si c'est une heure encore plus simple type 8h + //si valeures correctes, on entre les données dans la variables de session + if ($heures[1] < 24 && $heures[2] < 60) { + $_SESSION["horaires$i"][$j] = $heures[0]; + } else { //sinon message d'erreur et nettoyage de la case + $errheure[$i][$j] = true; + $erreur = true; + } + } elseif (preg_match(";^(\d{1,2})-(\d{1,2})$;", $tmphorairesi[$j], $heures)) { //si c'est un creneau simple type 8-11 + //si valeures correctes, on entre les données dans la variables de session + if ($heures[1] < $heures[2] && $heures[1] < 24 && $heures[2] < 24) { + $_SESSION["horaires$i"][$j] = $heures[0]; + } else { //sinon message d'erreur et nettoyage de la case + $errheure[$i][$j] = true; + $erreur = true; + } + } elseif (preg_match(";^(\d{1,2})h-(\d{1,2})h$;", $tmphorairesi[$j], $heures)) { //si c'est un creneau H type 8h-11h + //si valeures correctes, on entre les données dans la variables de session + if ($heures[1] < $heures[2] && $heures[1] < 24 && $heures[2] < 24) { + $_SESSION["horaires$i"][$j] = $heures[0]; + } else { //sinon message d'erreur et nettoyage de la case + $errheure[$i][$j] = true; + $erreur = true; + } + } elseif ($tmphorairesi[$j] == "") { //Si la case est vide + unset($_SESSION["horaires$i"][$j]); + } else { //pour tout autre format, message d'erreur + $errheure[$i][$j] = true; + $erreur = true; + } + + if (issetAndNoEmpty('horaires'.$i, $_SESSION) === false || issetAndNoEmpty($j, $_SESSION['horaires'.$i]) === false) { + if (issetAndNoEmpty('horaires'.$i, $_SESSION) === true) { + $_SESSION["horaires$i"][$j] = ''; + } else { + $_SESSION["horaires$i"] = array(); + $_SESSION["horaires$i"][$j] = ''; + } + } + } + + if ($_SESSION["horaires$i"][0] == "" && $_SESSION["horaires$i"][1] == "" && $_SESSION["horaires$i"][2] == "" && $_SESSION["horaires$i"][3] == "" && $_SESSION["horaires$i"][4] == "") { + $choixdate .= ","; + $choixdate .= $_SESSION["totalchoixjour"][$i]; + } else { + for ($j = 0; $j < $_SESSION["nbrecaseshoraires"]; $j++) { + if ($_SESSION["horaires$i"][$j] != "") { + $choixdate .= ","; + $choixdate .= $_SESSION["totalchoixjour"][$i]; + $choixdate .= "@"; + // On remplace la virgule et l'arobase pour ne pas avoir de problème par la suite + $choixdate .= str_replace(array(',', '@'), array(',', '@'), $_SESSION["horaires$i"][$j]); + } } } } } + if (!empty($errheure)) { setEventMessages($langs->trans("ErrorBadFormat"), null, 'errors'); } @@ -170,7 +177,7 @@ if (GETPOST('confirmation')) { } // Add survey into database - if (!$erreur) { + if (!$erreur && $erreurNb == 0) { $_SESSION["toutchoix"] = substr("$choixdate", 1); ajouter_sondage(); diff --git a/htdocs/resource/contact.php b/htdocs/resource/contact.php index 45e4ce4b329..3b032fffb94 100644 --- a/htdocs/resource/contact.php +++ b/htdocs/resource/contact.php @@ -114,10 +114,6 @@ llxHeader('', $langs->trans("Resource")); // View and edit mode if ($id > 0 || !empty($ref)) { - $soc = new Societe($db); - $soc->fetch($object->socid); - - $head = resource_prepare_head($object); print dol_get_fiche_head($head, 'contact', $langs->trans("ResourceSingular"), -1, 'resource');