27 include_once
'inc.php';
28 if (file_exists($conffile)) {
29 include_once $conffile;
31 require_once $dolibarr_main_document_root.
'/core/lib/admin.lib.php';
32 include_once $dolibarr_main_document_root.
'/core/lib/images.lib.php';
33 require_once $dolibarr_main_document_root.
'/core/class/extrafields.class.php';
34 require_once
'lib/repair.lib.php';
42 $err = error_reporting();
45 error_reporting($err);
47 $setuplang =
GETPOST(
"selectlang",
'aZ09', 3) ?
GETPOST(
"selectlang",
'aZ09', 3) :
'auto';
48 $langs->setDefaultLang($setuplang);
50 $langs->loadLangs(array(
"admin",
"install",
"other"));
52 if ($dolibarr_main_db_type ==
"mysqli") {
55 if ($dolibarr_main_db_type ==
"pgsql") {
58 if ($dolibarr_main_db_type ==
"mssql") {
64 if (!is_object($conf)) {
78 print
'<h3>'.$langs->trans(
"Repair").
'</h3>';
80 print
'Option standard (\'test\' or \'confirmed\') is '.(GETPOST(
'standard',
'alpha') ?
GETPOST(
'standard',
'alpha') :
'undefined').
'<br>'.
"\n";
82 print
'Option force_disable_of_modules_not_found (\'test\' or \'confirmed\') is '.(GETPOST(
'force_disable_of_modules_not_found',
'alpha') ?
GETPOST(
'force_disable_of_modules_not_found',
'alpha') :
'undefined').
'<br>'.
"\n";
84 print
'Option restore_thirdparties_logos (\'test\' or \'confirmed\') is '.(GETPOST(
'restore_thirdparties_logos',
'alpha') ?
GETPOST(
'restore_thirdparties_logos',
'alpha') :
'undefined').
'<br>'.
"\n";
85 print
'Option restore_user_pictures (\'test\' or \'confirmed\') is '.(GETPOST(
'restore_user_pictures',
'alpha') ?
GETPOST(
'restore_user_pictures',
'alpha') :
'undefined').
'<br>'.
"\n";
86 print
'Option rebuild_product_thumbs (\'test\' or \'confirmed\') is '.(GETPOST(
'rebuild_product_thumbs',
'alpha') ?
GETPOST(
'rebuild_product_thumbs',
'alpha') :
'undefined').
'<br>'.
"\n";
88 print
'Option clean_linked_elements (\'test\' or \'confirmed\') is '.(GETPOST(
'clean_linked_elements',
'alpha') ?
GETPOST(
'clean_linked_elements',
'alpha') :
'undefined').
'<br>'.
"\n";
89 print
'Option clean_menus (\'test\' or \'confirmed\') is '.(GETPOST(
'clean_menus',
'alpha') ?
GETPOST(
'clean_menus',
'alpha') :
'undefined').
'<br>'.
"\n";
90 print
'Option clean_orphelin_dir (\'test\' or \'confirmed\') is '.(GETPOST(
'clean_orphelin_dir',
'alpha') ?
GETPOST(
'clean_orphelin_dir',
'alpha') :
'undefined').
'<br>'.
"\n";
91 print
'Option clean_product_stock_batch (\'test\' or \'confirmed\') is '.(GETPOST(
'clean_product_stock_batch',
'alpha') ?
GETPOST(
'clean_product_stock_batch',
'alpha') :
'undefined').
'<br>'.
"\n";
92 print
'Option clean_perm_table (\'test\' or \'confirmed\') is '.(GETPOST(
'clean_perm_table',
'alpha') ?
GETPOST(
'clean_perm_table',
'alpha') :
'undefined').
'<br>'.
"\n";
93 print
'Option repair_link_dispatch_lines_supplier_order_lines, (\'test\' or \'confirmed\') is '.(GETPOST(
'repair_link_dispatch_lines_supplier_order_lines',
'alpha') ?
GETPOST(
'repair_link_dispatch_lines_supplier_order_lines',
'alpha') :
'undefined').
'<br>'.
"\n";
95 print
'Option set_empty_time_spent_amount (\'test\' or \'confirmed\') is '.(GETPOST(
'set_empty_time_spent_amount',
'alpha') ?
GETPOST(
'set_empty_time_spent_amount',
'alpha') :
'undefined').
'<br>'.
"\n";
97 print
'Option force_utf8_on_tables (force utf8 + row=dynamic), for mysql/mariadb only (\'test\' or \'confirmed\') is '.(GETPOST(
'force_utf8_on_tables',
'alpha') ?
GETPOST(
'force_utf8_on_tables',
'alpha') :
'undefined').
'<br>'.
"\n";
98 print
"Option force_utf8mb4_on_tables (force utf8mb4 + row=dynamic, EXPERIMENTAL!), for mysql/mariadb only ('test' or 'confirmed') is ".(GETPOST(
'force_utf8mb4_on_tables',
'alpha') ?
GETPOST(
'force_utf8mb4_on_tables',
'alpha') :
'undefined').
"<br>\n";
100 print
'Option rebuild_sequences, for postgresql only (\'test\' or \'confirmed\') is '.(GETPOST(
'rebuild_sequences',
'alpha') ?
GETPOST(
'rebuild_sequences',
'alpha') :
'undefined').
'<br>'.
"\n";
103 print
'<table cellspacing="0" cellpadding="1" border="0" width="100%">';
107 if (preg_match(
'/crypted:/i', $dolibarr_main_db_pass) || !empty($dolibarr_main_db_encrypted_pass)) {
108 require_once $dolibarr_main_document_root.
'/core/lib/security.lib.php';
109 if (preg_match(
'/crypted:/i', $dolibarr_main_db_pass)) {
110 $dolibarr_main_db_pass = preg_replace(
'/crypted:/i',
'', $dolibarr_main_db_pass);
111 $dolibarr_main_db_pass =
dol_decode($dolibarr_main_db_pass);
112 $dolibarr_main_db_encrypted_pass = $dolibarr_main_db_pass;
114 $dolibarr_main_db_pass =
dol_decode($dolibarr_main_db_encrypted_pass);
119 $conf->db->type = $dolibarr_main_db_type;
120 $conf->db->host = $dolibarr_main_db_host;
121 $conf->db->port = $dolibarr_main_db_port;
122 $conf->db->name = $dolibarr_main_db_name;
123 $conf->db->user = $dolibarr_main_db_user;
124 $conf->db->pass = $dolibarr_main_db_pass;
127 $conf->db->dolibarr_main_db_encryption = isset($dolibarr_main_db_encryption) ? $dolibarr_main_db_encryption :
'';
128 $conf->db->dolibarr_main_db_cryptkey = isset($dolibarr_main_db_cryptkey) ? $dolibarr_main_db_cryptkey :
'';
130 $db =
getDoliDBInstance($conf->db->type, $conf->db->host, $conf->db->user, $conf->db->pass, $conf->db->name, $conf->db->port);
132 if ($db->connected) {
133 print
'<tr><td class="nowrap">';
134 print $langs->trans(
"ServerConnection").
" : $dolibarr_main_db_host</td><td class=\"right\">".$langs->trans(
"OK").
"</td></tr>";
135 dolibarr_install_syslog(
"repair: ".$langs->transnoentities(
"ServerConnection").
": ".$dolibarr_main_db_host.$langs->transnoentities(
"OK"));
138 print
"<tr><td>".$langs->trans(
"ErrorFailedToConnectToDatabase", $dolibarr_main_db_name).
"</td><td class=\"right\">".$langs->transnoentities(
"Error").
"</td></tr>";
139 dolibarr_install_syslog(
"repair: ".$langs->transnoentities(
"ErrorFailedToConnectToDatabase", $dolibarr_main_db_name));
144 if ($db->database_selected) {
145 print
'<tr><td class="nowrap">';
146 print $langs->trans(
"DatabaseConnection").
" : ".$dolibarr_main_db_name.
"</td><td class=\"right\">".$langs->trans(
"OK").
"</td></tr>";
150 print
"<tr><td>".$langs->trans(
"ErrorFailedToConnectToDatabase", $dolibarr_main_db_name).
"</td><td class=\"right\">".$langs->trans(
"Error").
"</td></tr>";
151 dolibarr_install_syslog(
"repair: ".$langs->transnoentities(
"ErrorFailedToConnectToDatabase", $dolibarr_main_db_name));
158 $version = $db->getVersion();
159 $versionarray = $db->getVersionArray();
160 print
'<tr><td>'.$langs->trans(
"ServerVersion").
'</td>';
161 print
'<td class="right">'.$version.
'</td></tr>';
166 $conf->setValues($db);
168 if (defined(
'SYSLOG_FILE')) {
169 $conf->global->SYSLOG_FILE = constant(
'SYSLOG_FILE');
171 $conf->global->MAIN_ENABLE_LOG_TO_HTML = 1;
176 $oneoptionset = (
GETPOST(
'standard',
'alpha') ||
GETPOST(
'restore_thirdparties_logos',
'alpha') ||
GETPOST(
'clean_linked_elements',
'alpha') ||
GETPOST(
'clean_menus',
'alpha')
177 ||
GETPOST(
'clean_orphelin_dir',
'alpha') ||
GETPOST(
'clean_product_stock_batch',
'alpha') ||
GETPOST(
'set_empty_time_spent_amount',
'alpha') ||
GETPOST(
'rebuild_product_thumbs',
'alpha')
178 ||
GETPOST(
'clean_perm_table',
'alpha')
179 ||
GETPOST(
'force_disable_of_modules_not_found',
'alpha')
180 ||
GETPOST(
'force_utf8_on_tables',
'alpha') ||
GETPOST(
'force_utf8mb4_on_tables',
'alpha')
181 ||
GETPOST(
'rebuild_sequences',
'alpha'));
183 if ($ok && $oneoptionset) {
185 print
'<tr><td colspan="2">'.$langs->trans(
"PleaseBePatient").
'<br><br></td></tr>';
191 if ($ok &&
GETPOST(
'standard',
'alpha')) {
192 $dir =
"mysql/migration/";
199 $filesindir = array();
200 $handle = opendir($dir);
201 if (is_resource($handle)) {
202 while (($file = readdir($handle)) !==
false) {
203 if (preg_match(
'/\.sql$/i', $file)) {
204 $filesindir[] = $file;
210 foreach ($filesindir as $file) {
211 if (preg_match(
'/repair/i', $file)) {
217 foreach ($filelist as $file) {
218 print
'<tr><td class="nowrap">*** ';
219 print $langs->trans(
"Script").
'</td><td class="right">'.$file.
'</td></tr>';
221 $name = substr($file, 0,
dol_strlen($file) - 4);
224 $ok =
run_sql($dir.$file, 0,
'', 1);
231 if ($ok &&
GETPOST(
'standard',
'alpha')) {
233 $listofmodulesextra = array(
'societe'=>
'societe',
'adherent'=>
'adherent',
'product'=>
'product',
234 'socpeople'=>
'socpeople',
'propal'=>
'propal',
'commande'=>
'commande',
'facture'=>
'facture',
235 'supplier_proposal'=>
'supplier_proposal',
'commande_fournisseur'=>
'commande_fournisseur',
'facture_fourn'=>
'facture_fourn',
236 'actioncomm'=>
'actioncomm',
'bom_bom'=>
'bom_bom',
'mrp_mo'=>
'mrp_mo',
237 'adherent_type'=>
'adherent_type',
'user'=>
'user',
'projet'=>
'projet',
'projet_task'=>
'projet_task');
238 print
'<tr><td colspan="2"><br>*** Check fields into extra table structure match table of definition. If not add column into table</td></tr>';
239 foreach ($listofmodulesextra as $tablename => $elementtype) {
241 $tableextra = MAIN_DB_PREFIX.$tablename.
'_extrafields';
244 $arrayoffieldsdesc = $extrafields->fetch_name_optionals_label($elementtype);
247 $arrayoffieldsfound = array();
248 $resql = $db->DDLDescTable($tableextra);
250 print
'<tr><td>Check availability of extra field for '.$tableextra.
"<br>\n";
252 while ($obj = $db->fetch_object(
$resql)) {
253 $fieldname = $fieldtype =
'';
254 if (preg_match(
'/mysql/', $db->type)) {
255 $fieldname = $obj->Field;
256 $fieldtype = $obj->Type;
258 $fieldname = isset($obj->Key) ? $obj->Key : $obj->attname;
259 $fieldtype = isset($obj->Type) ? $obj->Type :
'varchar';
262 if (empty($fieldname)) {
265 if (in_array($fieldname, array(
'rowid',
'tms',
'fk_object',
'import_key'))) {
268 $arrayoffieldsfound[$fieldname] = array(
'type'=>$fieldtype);
272 foreach ($arrayoffieldsdesc as $code => $label) {
273 if (!in_array($code, array_keys($arrayoffieldsfound))) {
274 print
'Found field '.$code.
' declared into '.MAIN_DB_PREFIX.
'extrafields table but not found into desc of table '.$tableextra.
" -> ";
275 $type = $extrafields->attributes[$elementtype][
'type'][$code]; $length = $extrafields->attributes[$elementtype][
'size'][$code]; $attribute =
''; $default =
''; $extra =
''; $null =
'null';
277 if ($type ==
'boolean') {
280 } elseif ($type ==
'price') {
283 } elseif ($type ==
'phone') {
286 } elseif ($type ==
'mail') {
289 } elseif (($type ==
'select') || ($type ==
'sellist') || ($type ==
'radio') || ($type ==
'checkbox') || ($type ==
'chkbxlst')) {
292 } elseif ($type ==
'link') {
303 'attribute'=>$attribute,
311 if (
GETPOST(
'standard',
'alpha') ==
'confirmed') {
312 $result = $db->DDLAddField($tableextra, $code, $field_desc,
"");
315 print
"KO ".$db->lasterror.
"<br>\n";
320 print
' - Mode test, no column added.';
325 print
"</td><td> </td></tr>\n";
334 if ($ok &&
GETPOST(
'standard',
'alpha')) {
340 if ($ok &&
GETPOST(
'standard',
'alpha')) {
341 print
'<tr><td colspan="2"><br>*** Clean constant record of modules not enabled</td></tr>';
343 $sql =
"SELECT name, entity, value";
344 $sql .=
" FROM ".MAIN_DB_PREFIX.
"const as c";
345 $sql .=
" WHERE name LIKE 'MAIN_MODULE_%_TPL' OR name LIKE 'MAIN_MODULE_%_CSS' OR name LIKE 'MAIN_MODULE_%_JS' OR name LIKE 'MAIN_MODULE_%_HOOKS'";
346 $sql .=
" OR name LIKE 'MAIN_MODULE_%_TRIGGERS' OR name LIKE 'MAIN_MODULE_%_THEME' OR name LIKE 'MAIN_MODULE_%_SUBSTITUTIONS' OR name LIKE 'MAIN_MODULE_%_MODELS'";
347 $sql .=
" OR name LIKE 'MAIN_MODULE_%_MENUS' OR name LIKE 'MAIN_MODULE_%_LOGIN' OR name LIKE 'MAIN_MODULE_%_BARCODE' OR name LIKE 'MAIN_MODULE_%_TABS_%'";
348 $sql .=
" OR name LIKE 'MAIN_MODULE_%_MODULEFOREXTERNAL'";
349 $sql .=
" ORDER BY name, entity";
351 $resql = $db->query($sql);
353 $num = $db->num_rows(
$resql);
360 $obj = $db->fetch_object(
$resql);
363 if (preg_match(
'/MAIN_MODULE_([^_]+)_(.+)/i', $obj->name, $reg)) {
367 $sql2 =
"SELECT COUNT(*) as nb";
368 $sql2 .=
" FROM ".MAIN_DB_PREFIX.
"const as c";
369 $sql2 .=
" WHERE name = 'MAIN_MODULE_".$name.
"'";
370 $sql2 .=
" AND entity = ".((int) $obj->entity);
371 $resql2 = $db->query($sql2);
373 $obj2 = $db->fetch_object($resql2);
374 if ($obj2 && $obj2->nb == 0) {
376 $sqldelete =
"DELETE FROM ".MAIN_DB_PREFIX.
"const WHERE name = '".$db->escape($obj->name).
"' AND entity = ".((int) $obj->entity);
378 if (
GETPOST(
'standard',
'alpha') ==
'confirmed') {
379 $db->query($sqldelete);
381 print
'<tr><td>Widget '.$obj->name.
' set in entity '.$obj->entity.
' with value '.$obj->value.
' -> Module '.$name.
' not enabled in entity '.((int) $obj->entity).
', we delete record</td></tr>';
383 print
'<tr><td>Widget '.$obj->name.
' set in entity '.$obj->entity.
' with value '.$obj->value.
' -> Module '.$name.
' not enabled in entity '.((int) $obj->entity).
', we should delete record (not done, mode test)</td></tr>';
403 if ($ok &&
GETPOST(
'standard',
'alpha')) {
404 print
'<tr><td colspan="2"><br>*** Clean definition of boxes of modules not enabled</td></tr>';
406 $sql =
"SELECT file, entity FROM ".MAIN_DB_PREFIX.
"boxes_def";
407 $sql .=
" WHERE file like '%@%'";
409 $resql = $db->query($sql);
411 $num = $db->num_rows(
$resql);
418 $obj = $db->fetch_object(
$resql);
421 if (preg_match(
'/^(.+)@(.+)$/i', $obj->file, $reg)) {
425 $sql2 =
"SELECT COUNT(*) as nb";
426 $sql2 .=
" FROM ".MAIN_DB_PREFIX.
"const as c";
427 $sql2 .=
" WHERE name = 'MAIN_MODULE_".strtoupper($module).
"'";
428 $sql2 .=
" AND entity = ".((int) $obj->entity);
429 $sql2 .=
" AND value <> 0";
430 $resql2 = $db->query($sql2);
432 $obj2 = $db->fetch_object($resql2);
433 if ($obj2 && $obj2->nb == 0) {
435 $sqldeletea =
"DELETE FROM ".MAIN_DB_PREFIX.
"boxes WHERE entity = ".((int) $obj->entity).
" AND box_id IN (SELECT rowid FROM ".MAIN_DB_PREFIX.
"boxes_def WHERE file = '".$db->escape($obj->file).
"' AND entity = ".((int) $obj->entity).
")";
436 $sqldeleteb =
"DELETE FROM ".MAIN_DB_PREFIX.
"boxes_def WHERE file = '".$db->escape($obj->file).
"' AND entity = ".((int) $obj->entity);
438 if (
GETPOST(
'standard',
'alpha') ==
'confirmed') {
439 $db->query($sqldeletea);
440 $db->query($sqldeleteb);
442 print
'<tr><td>Constant '.$obj->file.
' set in boxes_def for entity '.$obj->entity.
' but MAIN_MODULE_'.strtoupper($module).
' not defined in entity '.((int) $obj->entity).
', we delete record</td></tr>';
444 print
'<tr><td>Constant '.$obj->file.
' set in boxes_def for entity '.$obj->entity.
' but MAIN_MODULE_'.strtoupper($module).
' not defined in entity '.((int) $obj->entity).
', we should delete record (not done, mode test)</td></tr>';
462 if ($ok &&
GETPOST(
'restore_thirdparties_logos')) {
467 print
'<tr><td colspan="2"><br>*** Restore thirdparties logo<br>';
469 $sql =
"SELECT s.rowid, s.nom as name, s.logo FROM ".MAIN_DB_PREFIX.
"societe as s ORDER BY s.nom";
470 $resql = $db->query($sql);
472 $num = $db->num_rows(
$resql);
476 $obj = $db->fetch_object(
$resql);
484 $tmp = explode(
'.', $obj->logo);
486 if (isset($tmp[1])) {
491 $filetotest = $dolibarr_main_data_root.
'/societe/logos/'.$name.$ext;
492 $filetotestsmall = $dolibarr_main_data_root.
'/societe/logos/thumbs/'.$name.
'_small'.$ext;
494 print
'Check thirdparty '.$obj->rowid.
' name='.$obj->name.
' logo='.$obj->logo.
' file '.$filetotest.
" exists=".$exists.
"<br>\n";
496 $filetarget = $dolibarr_main_data_root.
'/societe/'.$obj->rowid.
'/logos/'.$name.$ext;
497 $filetargetsmall = $dolibarr_main_data_root.
'/societe/'.$obj->rowid.
'/logos/thumbs/'.$name.
'_small'.$ext;
500 if (
GETPOST(
'restore_thirdparties_logos',
'alpha') ==
'confirmed') {
501 dol_mkdir($dolibarr_main_data_root.
'/societe/'.$obj->rowid.
'/logos');
504 print
" -> Copy file ".$filetotest.
" -> ".$filetarget.
"<br>\n";
505 if (
GETPOST(
'restore_thirdparties_logos',
'alpha') ==
'confirmed') {
506 dol_copy($filetotest, $filetarget,
'', 0);
512 if (
GETPOST(
'restore_thirdparties_logos',
'alpha') ==
'confirmed') {
513 dol_mkdir($dolibarr_main_data_root.
'/societe/'.$obj->rowid.
'/logos/thumbs');
515 print
" -> Copy file ".$filetotestsmall.
" -> ".$filetargetsmall.
"<br>\n";
516 if (
GETPOST(
'restore_thirdparties_logos',
'alpha') ==
'confirmed') {
517 dol_copy($filetotestsmall, $filetargetsmall,
'', 0);
536 if ($ok &&
GETPOST(
'restore_user_pictures',
'alpha')) {
541 print
'<tr><td colspan="2"><br>*** Restore user pictures<br>';
543 $sql =
"SELECT s.rowid, s.firstname, s.lastname, s.login, s.photo FROM ".MAIN_DB_PREFIX.
"user as s ORDER BY s.rowid";
544 $resql = $db->query($sql);
546 $num = $db->num_rows(
$resql);
550 $obj = $db->fetch_object(
$resql);
558 $tmp = explode(
'.', $obj->photo);
560 if (isset($tmp[1])) {
565 $filetotest = $dolibarr_main_data_root.
'/users/'.substr(sprintf(
'%08d', $obj->rowid), -1, 1).
'/'.substr(sprintf(
'%08d', $obj->rowid), -2, 1).
'/'.$name.$ext;
566 $filetotestsmall = $dolibarr_main_data_root.
'/users/'.substr(sprintf(
'%08d', $obj->rowid), -1, 1).
'/'.substr(sprintf(
'%08d', $obj->rowid), -2, 1).
'/thumbs/'.$name.
'_small'.$ext;
567 $filetotestmini = $dolibarr_main_data_root.
'/users/'.substr(sprintf(
'%08d', $obj->rowid), -1, 1).
'/'.substr(sprintf(
'%08d', $obj->rowid), -2, 1).
'/thumbs/'.$name.
'_mini'.$ext;
569 print
'Check user '.$obj->rowid.
' lastname='.$obj->lastname.
' firstname='.$obj->firstname.
' photo='.$obj->photo.
' file '.$filetotest.
" exists=".$exists.
"<br>\n";
571 $filetarget = $dolibarr_main_data_root.
'/users/'.$obj->rowid.
'/'.$name.$ext;
572 $filetargetsmall = $dolibarr_main_data_root.
'/users/'.$obj->rowid.
'/thumbs/'.$name.
'_small'.$ext;
573 $filetargetmini = $dolibarr_main_data_root.
'/users/'.$obj->rowid.
'/thumbs/'.$name.
'_mini'.$ext;
577 if (
GETPOST(
'restore_user_pictures',
'alpha') ==
'confirmed') {
578 dol_mkdir($dolibarr_main_data_root.
'/users/'.$obj->rowid);
581 print
" -> Copy file ".$filetotest.
" -> ".$filetarget.
"<br>\n";
582 if (
GETPOST(
'restore_user_pictures',
'alpha') ==
'confirmed') {
583 dol_copy($filetotest, $filetarget,
'', 0);
589 if (
GETPOST(
'restore_user_pictures',
'alpha') ==
'confirmed') {
590 dol_mkdir($dolibarr_main_data_root.
'/users/'.$obj->rowid.
'/thumbs');
593 print
" -> Copy file ".$filetotestsmall.
" -> ".$filetargetsmall.
"<br>\n";
594 if (
GETPOST(
'restore_user_pictures',
'alpha') ==
'confirmed') {
595 dol_copy($filetotestsmall, $filetargetsmall,
'', 0);
601 if (
GETPOST(
'restore_user_pictures',
'alpha') ==
'confirmed') {
602 dol_mkdir($dolibarr_main_data_root.
'/users/'.$obj->rowid.
'/thumbs');
605 print
" -> Copy file ".$filetotestmini.
" -> ".$filetargetmini.
"<br>\n";
606 if (
GETPOST(
'restore_user_pictures',
'alpha') ==
'confirmed') {
607 dol_copy($filetotestmini, $filetargetmini,
'', 0);
625 if ($ok &&
GETPOST(
'rebuild_product_thumbs',
'alpha')) {
627 global $maxwidthsmall, $maxheightsmall, $maxwidthmini, $maxheightmini;
629 print
'<tr><td colspan="2"><br>*** Rebuild product thumbs<br>';
631 $sql =
"SELECT s.rowid, s.ref FROM ".MAIN_DB_PREFIX.
"product as s ORDER BY s.ref";
632 $resql = $db->query($sql);
634 $num = $db->num_rows(
$resql);
638 $obj = $db->fetch_object(
$resql);
640 if (!empty($obj->ref)) {
641 $files =
dol_dir_list($dolibarr_main_data_root.
'/produit/'.$obj->ref,
'files', 0);
642 foreach ($files as $file) {
645 $imgThumbSmall =
'notbuild';
646 if (
GETPOST(
'rebuild_product_thumbs',
'alpha') ==
'confirmed') {
648 $imgThumbSmall =
vignette($file[
'fullname'], $maxwidthsmall, $maxheightsmall,
'_small', 50,
"thumbs");
650 print
'Check product '.$obj->rowid.
", file ".$file[
'fullname'].
" -> ".$imgThumbSmall.
" maxwidthsmall=".$maxwidthsmall.
" maxheightsmall=".$maxheightsmall.
"<br>\n";
651 $imgThumbMini =
'notbuild';
652 if (
GETPOST(
'rebuild_product_thumbs',
'alpha') ==
'confirmed') {
655 $imgThumbMini =
vignette($file[
'fullname'], $maxwidthmini, $maxheightmini,
'_mini', 50,
"thumbs");
657 print
'Check product '.$obj->rowid.
", file ".$file[
'fullname'].
" -> ".$imgThumbMini.
" maxwidthmini=".$maxwidthmini.
" maxheightmini=".$maxheightmini.
"<br>\n";
673 if ($ok &&
GETPOST(
'clean_linked_elements',
'alpha')) {
674 print
'<tr><td colspan="2"><br>*** Check table of linked elements and delete orphelins links</td></tr>';
676 print
'<tr><td colspan="2">'.checkLinkedElements(
'propal',
'commande').
"</td></tr>\n";
679 print
'<tr><td colspan="2">'.checkLinkedElements(
'propal',
'facture').
"</td></tr>\n";
682 print
'<tr><td colspan="2">'.checkLinkedElements(
'commande',
'facture').
"</td></tr>\n";
685 print
'<tr><td colspan="2">'.checkLinkedElements(
'commande',
'shipping').
"</td></tr>\n";
688 print
'<tr><td colspan="2">'.checkLinkedElements(
'shipping',
'delivery').
"</td></tr>\n";
691 print
'<tr><td colspan="2">'.checkLinkedElements(
'order_supplier',
'invoice_supplier').
"</td></tr>\n";
696 if ($ok &&
GETPOST(
'clean_menus',
'alpha')) {
697 print
'<tr><td colspan="2"><br>*** Clean menu entries coming from disabled modules</td></tr>';
699 $sql =
"SELECT rowid, module";
700 $sql .=
" FROM ".MAIN_DB_PREFIX.
"menu as c";
701 $sql .=
" WHERE module IS NOT NULL AND module <> ''";
702 $sql .=
" ORDER BY module";
704 $resql = $db->query($sql);
706 $num = $db->num_rows(
$resql);
710 $obj = $db->fetch_object(
$resql);
712 $modulecond = $obj->module;
713 $modulecondarray = explode(
'|', $obj->module);
722 foreach ($modulecondarray as $tmpname) {
723 if ($tmpname ==
'margins') {
728 if (!empty($conf->$tmpname)) {
729 $result = $conf->$tmpname->enabled;
736 if (!$moduleok && $modulecond) {
737 print
' - Module condition '.$modulecond.
' seems ko, we delete menu entry.';
738 if (
GETPOST(
'clean_menus') ==
'confirmed') {
739 $sql2 =
"DELETE FROM ".MAIN_DB_PREFIX.
"menu WHERE module = '".$db->escape($modulecond).
"'";
740 $resql2 = $db->query($sql2);
745 print
' - <span class="warning">Cleaned</span>';
748 print
' - <span class="warning">Canceled (test mode)</span>';
751 print
' - Module condition '.$modulecond.
' is ok, we do nothing.';
770 print
'<tr><td>No menu entries of disabled menus found</td></tr>';
780 if ($ok &&
GETPOST(
'clean_orphelin_dir',
'alpha')) {
781 $listmodulepart = array(
'company',
'invoice',
'invoice_supplier',
'propal',
'order',
'order_supplier',
'contract',
'tax');
782 foreach ($listmodulepart as $modulepart) {
783 $filearray = array();
784 $upload_dir = isset($conf->$modulepart->dir_output) ? $conf->$modulepart->dir_output :
'';
785 if ($modulepart ==
'company') {
786 $upload_dir = $conf->societe->dir_output;
788 if ($modulepart ==
'invoice') {
789 $upload_dir = $conf->facture->dir_output;
791 if ($modulepart ==
'invoice_supplier') {
792 $upload_dir = $conf->fournisseur->facture->dir_output;
794 if ($modulepart ==
'order') {
795 $upload_dir = $conf->commande->dir_output;
797 if ($modulepart ==
'order_supplier') {
798 $upload_dir = $conf->fournisseur->commande->dir_output;
800 if ($modulepart ==
'contract') {
801 $upload_dir = $conf->contrat->dir_output;
804 if (empty($upload_dir)) {
808 print
'<tr><td colspan="2"><br>*** Clean orphelins files into files '.$upload_dir.
'</td></tr>';
810 $filearray =
dol_dir_list($upload_dir,
"files", 1,
'', array(
'^SPECIMEN\.pdf$',
'^\.',
'(\.meta|_preview.*\.png)$',
'^temp$',
'^payments$',
'^CVS$',
'^thumbs$'),
'', SORT_DESC, 1,
true);
813 if ($modulepart ==
'company') {
814 include_once DOL_DOCUMENT_ROOT.
'/societe/class/societe.class.php';
815 $object_instance =
new Societe($db);
817 if ($modulepart ==
'invoice') {
818 include_once DOL_DOCUMENT_ROOT.
'/compta/facture/class/facture.class.php';
819 $object_instance =
new Facture($db);
820 } elseif ($modulepart ==
'invoice_supplier') {
821 include_once DOL_DOCUMENT_ROOT.
'/fourn/class/fournisseur.facture.class.php';
823 } elseif ($modulepart ==
'propal') {
824 include_once DOL_DOCUMENT_ROOT.
'/comm/propal/class/propal.class.php';
825 $object_instance =
new Propal($db);
826 } elseif ($modulepart ==
'order') {
827 include_once DOL_DOCUMENT_ROOT.
'/commande/class/commande.class.php';
828 $object_instance =
new Commande($db);
829 } elseif ($modulepart ==
'order_supplier') {
830 include_once DOL_DOCUMENT_ROOT.
'/fourn/class/fournisseur.commande.class.php';
832 } elseif ($modulepart ==
'contract') {
833 include_once DOL_DOCUMENT_ROOT.
'/contrat/class/contrat.class.php';
834 $object_instance =
new Contrat($db);
835 } elseif ($modulepart ==
'tax') {
836 include_once DOL_DOCUMENT_ROOT.
'/compta/sociales/class/chargesociales.class.php';
840 foreach ($filearray as $key => $file) {
841 if (!is_dir($file[
'name'])
842 && $file[
'name'] !=
'.'
843 && $file[
'name'] !=
'..'
844 && $file[
'name'] !=
'CVS'
847 $relativefile = preg_replace(
'/'.preg_quote($upload_dir.
'/',
'/').
'/',
'', $file[
'fullname']);
850 $id = 0; $ref =
''; $object_instance->id = 0; $object_instance->ref =
''; $label =
'';
853 if ($modulepart ==
'invoice') {
854 preg_match(
'/(.*)\/[^\/]+$/', $relativefile, $reg); $ref = $reg[1];
856 if ($modulepart ==
'invoice_supplier') {
857 preg_match(
'/(\d+)\/[^\/]+$/', $relativefile, $reg); $id = empty($reg[1]) ?
'' : $reg[1];
859 if ($modulepart ==
'propal') {
860 preg_match(
'/(.*)\/[^\/]+$/', $relativefile, $reg); $ref = $reg[1];
862 if ($modulepart ==
'order') {
863 preg_match(
'/(.*)\/[^\/]+$/', $relativefile, $reg); $ref = $reg[1];
865 if ($modulepart ==
'order_supplier') {
866 preg_match(
'/(.*)\/[^\/]+$/', $relativefile, $reg); $ref = $reg[1];
868 if ($modulepart ==
'contract') {
869 preg_match(
'/(.*)\/[^\/]+$/', $relativefile, $reg); $ref = $reg[1];
871 if ($modulepart ==
'tax') {
872 preg_match(
'/(\d+)\/[^\/]+$/', $relativefile, $reg); $id = $reg[1];
877 $result = $object_instance->fetch($id, $ref);
881 print
'<tr><td colspan="2">';
882 print
'Delete orphelins file '.$file[
'fullname'].
'<br>';
883 if (
GETPOST(
'clean_orphelin_dir',
'alpha') ==
'confirmed') {
888 } elseif ($result < 0) {
889 print
'Error in '.get_class($object_instance).
'.fetch of id'.$id.
' ref='.$ref.
', result='.$result.
'<br>';
898 if ($ok &&
GETPOST(
'clean_product_stock_batch',
'alpha')) {
899 $methodtofix =
GETPOST(
'methodtofix',
'alpha') ?
GETPOST(
'methodtofix',
'alpha') :
'updatestock';
901 print
'<tr><td colspan="2"><br>*** Clean table product_batch, methodtofix='.$methodtofix.
' (possible values: updatestock or updatebatch)</td></tr>';
903 $sql =
"SELECT p.rowid, p.ref, p.tobatch, ps.rowid as psrowid, ps.fk_entrepot, ps.reel, SUM(pb.qty) as reelbatch";
904 $sql .=
" FROM ".MAIN_DB_PREFIX.
"product as p, ".MAIN_DB_PREFIX.
"product_stock as ps LEFT JOIN ".MAIN_DB_PREFIX.
"product_batch as pb ON ps.rowid = pb.fk_product_stock";
905 $sql .=
" WHERE p.rowid = ps.fk_product";
906 $sql .=
" GROUP BY p.rowid, p.ref, p.tobatch, ps.rowid, ps.fk_entrepot, ps.reel";
907 $sql .=
" HAVING (SUM(pb.qty) IS NOT NULL AND reel != SUM(pb.qty)) OR (SUM(pb.qty) IS NULL AND p.tobatch > 0)";
909 $resql = $db->query($sql);
911 $num = $db->num_rows(
$resql);
916 $obj = $db->fetch_object(
$resql);
917 print
'<tr><td>Product '.$obj->rowid.
'-'.$obj->ref.
' in warehouse id='.$obj->fk_entrepot.
' -> product_stock.id='.$obj->psrowid.
': '.$obj->reel.
' (product_stock.reel) != '.($obj->reelbatch ? $obj->reelbatch :
'0').
' (sum product_batch)';
920 if ($obj->reel != $obj->reelbatch) {
921 if (empty($obj->tobatch)) {
923 print
' -> Delete qty '.$obj->reelbatch.
' for any lot linked to fk_product_stock='.$obj->psrowid;
924 $sql2 =
"DELETE FROM ".MAIN_DB_PREFIX.
"product_batch";
925 $sql2 .=
" WHERE fk_product_stock = ".((int) $obj->psrowid);
928 if (
GETPOST(
'clean_product_stock_batch') ==
'confirmed') {
929 $resql2 = $db->query($sql2);
936 if ($methodtofix ==
'updatebatch') {
938 print
' -> Insert qty '.($obj->reel - $obj->reelbatch).
' with lot 000000 linked to fk_product_stock='.$obj->psrowid;
939 $sql2 =
"INSERT INTO ".MAIN_DB_PREFIX.
"product_batch(fk_product_stock, batch, qty)";
940 $sql2 .=
"VALUES(".((int) $obj->psrowid).
", '000000', ".((
float) ($obj->reel - $obj->reelbatch)).
")";
943 if (
GETPOST(
'clean_product_stock_batch') ==
'confirmed') {
944 $resql2 = $db->query($sql2);
953 if ($methodtofix ==
'updatestock') {
955 print
' -> Update qty of product_stock with qty = '.($obj->reelbatch ? ((
float) $obj->reelbatch) :
'0').
' for ps.rowid = '.((
int) $obj->psrowid);
956 $sql2 =
"UPDATE ".MAIN_DB_PREFIX.
"product_stock";
957 $sql2 .=
" SET reel = ".($obj->reelbatch ? ((
float) $obj->reelbatch) :
'0').
" WHERE rowid = ".((
int) $obj->psrowid);
960 if (
GETPOST(
'clean_product_stock_batch') ==
'confirmed') {
965 $resql2 = $db->query($sql2);
968 $sql3 =
'UPDATE '.MAIN_DB_PREFIX.
'product p SET p.stock= (SELECT SUM(ps.reel) FROM '.MAIN_DB_PREFIX.
'product_stock ps WHERE ps.fk_product = p.rowid)';
969 $resql3 = $db->query($sql3);
994 print
'<tr><td colspan="2">Nothing to do</td></tr>';
1003 if ($ok &&
GETPOST(
'clean_product_stock_negative_if_batch',
'alpha')) {
1004 print
'<tr><td colspan="2"><br>Clean table product_batch, methodtofix='.$methodtofix.
' (possible values: updatestock or updatebatch)</td></tr>';
1006 $sql =
"SELECT p.rowid, p.ref, p.tobatch, ps.rowid as psrowid, ps.fk_entrepot, ps.reel, SUM(pb.qty) as reelbatch";
1007 $sql .=
" FROM ".MAIN_DB_PREFIX.
"product as p, ".MAIN_DB_PREFIX.
"product_stock as ps, ".MAIN_DB_PREFIX.
"product_batch as pb";
1008 $sql .=
" WHERE p.rowid = ps.fk_product AND ps.rowid = pb.fk_product_stock";
1009 $sql .=
" AND p.tobatch > 0";
1010 $sql .=
" GROUP BY p.rowid, p.ref, p.tobatch, ps.rowid, ps.fk_entrepot, ps.reel";
1011 $sql .=
" HAVING reel != SUM(pb.qty)";
1012 $resql = $db->query($sql);
1014 $num = $db->num_rows(
$resql);
1019 $obj = $db->fetch_object(
$resql);
1020 print
'<tr><td>'.$obj->rowid.
'-'.$obj->ref.
'-'.$obj->fk_entrepot.
' -> '.$obj->psrowid.
': '.$obj->reel.
' != '.$obj->reelbatch;
1029 if ($ok &&
GETPOST(
'set_empty_time_spent_amount',
'alpha')) {
1030 print
'<tr><td colspan="2"><br>*** Set value of time spent without amount</td></tr>';
1032 $sql =
"SELECT COUNT(ptt.rowid) as nb, u.rowid as user_id, u.login, u.thm as user_thm";
1033 $sql .=
" FROM ".MAIN_DB_PREFIX.
"projet_task_time as ptt, ".MAIN_DB_PREFIX.
"user as u";
1034 $sql .=
" WHERE ptt.fk_user = u.rowid";
1035 $sql .=
" AND ptt.thm IS NULL and u.thm > 0";
1036 $sql .=
" GROUP BY u.rowid, u.login, u.thm";
1038 $resql = $db->query($sql);
1040 $num = $db->num_rows(
$resql);
1045 $obj = $db->fetch_object(
$resql);
1046 print
'<tr><td>'.$obj->login.
'-'.$obj->user_id.
' ('.$obj->nb.
' lines to fix) -> '.$obj->user_thm;
1050 if (
GETPOST(
'set_empty_time_spent_amount') ==
'confirmed') {
1051 $sql2 =
"UPDATE ".MAIN_DB_PREFIX.
"projet_task_time";
1052 $sql2 .=
" SET thm = ".$obj->user_thm.
" WHERE thm IS NULL AND fk_user = ".((int) $obj->user_id);
1053 $resql2 = $db->query($sql2);
1075 print
'<tr><td>No time spent with empty line on users with a hourly rate defined</td></tr>';
1084 if ($ok &&
GETPOST(
'force_disable_of_modules_not_found',
'alpha')) {
1085 print
'<tr><td colspan="2"><br>*** Force modules not found physicaly to be disabled (only modules adding js, css or hooks can be detected as removed physicaly)</td></tr>';
1087 $arraylistofkey = array(
'hooks',
'js',
'css');
1089 foreach ($arraylistofkey as $key) {
1090 $sql =
"SELECT DISTINCT name, value";
1091 $sql .=
" FROM ".MAIN_DB_PREFIX.
"const as c";
1092 $sql .=
" WHERE name LIKE 'MAIN_MODULE_%_".strtoupper($key).
"'";
1093 $sql .=
" ORDER BY name";
1095 $resql = $db->query($sql);
1097 $num = $db->num_rows(
$resql);
1101 $obj = $db->fetch_object(
$resql);
1102 $constantname = $obj->name;
1110 if (preg_match(
'/MAIN_MODULE_(.*)_'.strtoupper($key).
'/i', $constantname, $reg)) {
1111 $name = strtolower($reg[1]);
1117 if ($key ==
'hooks') {
1118 $reloffile = $name.
'/class/actions_'.$name.
'.class.php';
1121 $value = $obj->value;
1122 $valuearray = (array) json_decode($value);
1123 $reloffile = $valuearray[0];
1124 $reloffile = preg_replace(
'/^\//',
'', $valuearray[0]);
1126 if ($key ==
'css') {
1127 $value = $obj->value;
1128 $valuearray = (array) json_decode($value);
1129 if ($value && (!is_array($valuearray) || count($valuearray) == 0)) {
1130 $valuearray = array();
1131 $valuearray[0] = $value;
1133 $reloffile = preg_replace(
'/^\//',
'', $valuearray[0]);
1148 print
' - File of '.$key.
' ('.$reloffile.
') NOT found, we disable the module.';
1149 if (
GETPOST(
'force_disable_of_modules_not_found') ==
'confirmed') {
1150 $sql2 =
"DELETE FROM ".MAIN_DB_PREFIX.
"const WHERE name = 'MAIN_MODULE_".strtoupper($name).
"_".strtoupper($key).
"'";
1151 $resql2 = $db->query($sql2);
1156 $sql3 =
"DELETE FROM ".MAIN_DB_PREFIX.
"const WHERE name = 'MAIN_MODULE_".strtoupper($name).
"'";
1157 $resql3 = $db->query($sql3);
1162 print
' - <span class="warning">Cleaned</span>';
1165 print
' - <span class="warning">Canceled (test mode)</span>';
1168 print
' - File of '.$key.
' ('.$reloffile.
') found, we do nothing.';
1188 print
'<tr><td>No active module with missing files found by searching on MAIN_MODULE_(.*)_'.strtoupper($key).
'</td></tr>';
1198 if ($ok &&
GETPOST(
'clean_perm_table',
'alpha')) {
1199 print
'<tr><td colspan="2"><br>*** Clean table user_rights from lines of external modules no more enabled</td></tr>';
1202 foreach ($conf->modules as $key => $val) {
1203 $listofmods .= ($listofmods ?
',' :
'').
"'".$db->escape($val).
"'";
1206 $sql =
"SELECT id, libelle as label, module from ".MAIN_DB_PREFIX.
"rights_def WHERE module NOT IN (".$db->sanitize($listofmods, 1).
") AND id > 100000";
1208 $resql = $db->query($sql);
1210 $num = $db->num_rows(
$resql);
1214 $obj = $db->fetch_object(
$resql);
1216 print
'<tr><td>Found line with id '.$obj->id.
', label "'.$obj->label.
'" of module "'.$obj->module.
'" to delete';
1217 if (
GETPOST(
'clean_perm_table',
'alpha') ==
'confirmed') {
1218 $sqldelete =
"DELETE FROM ".MAIN_DB_PREFIX.
"rights_def WHERE id = ".((int) $obj->id);
1219 $resqldelete = $db->query($sqldelete);
1220 if (!$resqldelete) {
1230 print
'<tr><td>No lines of a disabled external module (with id > 100000) found into table rights_def</td></tr>';
1240 if ($ok &&
GETPOST(
'force_utf8_on_tables',
'alpha')) {
1241 print
'<tr><td colspan="2"><br>*** Force page code and collation of tables into utf8/utf8_unicode_ci and row_format=dynamic (for mysql/mariadb only)</td></tr>';
1243 if ($db->type ==
"mysql" || $db->type ==
"mysqli") {
1244 $force_utf8_on_tables =
GETPOST(
'force_utf8_on_tables',
'alpha');
1246 $listoftables = $db->DDLListTables($db->database_name);
1249 if ($force_utf8_on_tables ==
'confirmed') {
1250 $sql =
'SET FOREIGN_KEY_CHECKS=0';
1251 print
'<!-- '.$sql.
' -->';
1252 $resql = $db->query($sql);
1255 foreach ($listoftables as $table) {
1257 if ($conf->db->dolibarr_main_db_encryption != 0 && preg_match(
'/\_const$/', $table)) {
1261 print
'<tr><td colspan="2">';
1263 $sql1 =
"ALTER TABLE ".$table.
" ROW_FORMAT=dynamic";
1264 $sql2 =
"ALTER TABLE ".$table.
" CONVERT TO CHARACTER SET utf8 COLLATE utf8_unicode_ci";
1265 print
'<!-- '.$sql1.
' -->';
1266 print
'<!-- '.$sql2.
' -->';
1267 if ($force_utf8_on_tables ==
'confirmed') {
1268 $resql1 = $db->query($sql1);
1270 $resql2 = $db->query($sql2);
1274 print
' - Done ('.(($resql1 && $resql2) ?
'OK' :
'KO').
')';
1276 print
' - Disabled';
1282 if ($force_utf8_on_tables ==
'confirmed') {
1283 $sql =
'SET FOREIGN_KEY_CHECKS=1';
1284 print
'<!-- '.$sql.
' -->';
1285 $resql = $db->query($sql);
1288 print
'<tr><td colspan="2">Not available with database type '.$db->type.
'</td></tr>';
1293 if ($ok &&
GETPOST(
'force_utf8mb4_on_tables',
'alpha')) {
1294 print
'<tr><td colspan="2"><br>*** Force page code and collation of tables into utf8mb4/utf8mb4_unicode_ci (for mysql/mariadb only)</td></tr>';
1296 if ($db->type ==
"mysql" || $db->type ==
"mysqli") {
1297 $force_utf8mb4_on_tables =
GETPOST(
'force_utf8mb4_on_tables',
'alpha');
1299 $listoftables = $db->DDLListTables($db->database_name);
1302 if ($force_utf8mb4_on_tables ==
'confirmed') {
1303 $sql =
'SET FOREIGN_KEY_CHECKS=0';
1304 print
'<!-- '.$sql.
' -->';
1305 $resql = $db->query($sql);
1308 foreach ($listoftables as $table) {
1310 if ($conf->db->dolibarr_main_db_encryption != 0 && preg_match(
'/\_const$/', $table)) {
1314 print
'<tr><td colspan="2">';
1316 $sql1 =
"ALTER TABLE ".$table.
" ROW_FORMAT=dynamic";
1317 $sql2 =
"ALTER TABLE ".$table.
" CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci";
1318 print
'<!-- '.$sql1.
' -->';
1319 print
'<!-- '.$sql2.
' -->';
1320 if ($force_utf8mb4_on_tables ==
'confirmed') {
1321 $resql1 = $db->query($sql1);
1323 $resql2 = $db->query($sql2);
1327 print
' - Done ('.(($resql1 && $resql2) ?
'OK' :
'KO').
')';
1329 print
' - Disabled';
1337 if ($force_utf8mb4_on_tables ==
'confirmed') {
1338 $sql =
'SET FOREIGN_KEY_CHECKS=1';
1339 print
'<!-- '.$sql.
' -->';
1340 $resql = $db->query($sql);
1343 print
'<tr><td colspan="2">Not available with database type '.$db->type.
'</td></tr>';
1348 if ($ok &&
GETPOST(
'rebuild_sequences',
'alpha')) {
1349 print
'<tr><td colspan="2"><br>*** Force to rebuild sequences (for postgresql only)</td></tr>';
1351 if ($db->type ==
"pgsql") {
1352 $rebuild_sequence =
GETPOST(
'rebuild_sequences',
'alpha');
1354 if ($rebuild_sequence ==
'confirmed') {
1355 $sql =
"SELECT dol_util_rebuild_sequences();";
1356 print
'<!-- '.$sql.
' -->';
1357 $resql = $db->query($sql);
1360 print
'<tr><td colspan="2">Not available with database type '.$db->type.
'</td></tr>';
1365 if ($ok &&
GETPOST(
'repair_link_dispatch_lines_supplier_order_lines')) {
1389 $repair_link_dispatch_lines_supplier_order_lines =
GETPOST(
'repair_link_dispatch_lines_supplier_order_lines',
'alpha');
1392 echo
'<tr><th>Repair llx_commande_fournisseur_dispatch.fk_commandefourndet</th></tr>';
1393 echo
'<tr><td>Repair in progress. This may take a while.</td></tr>';
1395 $sql_dispatch =
'SELECT * FROM '.MAIN_DB_PREFIX.
'commande_fournisseur_dispatch WHERE COALESCE(fk_commandefourndet, 0) = 0';
1397 $resql_dispatch = $db->query($sql_dispatch);
1398 $n_processed_rows = 0;
1400 if ($resql_dispatch) {
1401 if ($db->num_rows($resql_dispatch) == 0) {
1402 echo
'<tr><td>Nothing to do.</td></tr>';
1405 while ($obj_dispatch = $db->fetch_object($resql_dispatch)) {
1406 $sql_line =
'SELECT line.rowid, line.qty FROM '.MAIN_DB_PREFIX.
'commande_fournisseurdet AS line';
1407 $sql_line .=
' WHERE line.fk_commande = '.((int) $obj_dispatch->fk_commande);
1408 $sql_line .=
' AND line.fk_product = '.((int) $obj_dispatch->fk_product);
1409 $resql_line = $db->query($sql_line);
1415 $remaining_qty = $obj_dispatch->qty;
1416 $first_iteration =
true;
1418 echo
'<tr><td>Unable to find a matching supplier order line for dispatch #'.$obj_dispatch->rowid.
'</td></tr>';
1419 $errors[] = $sql_line;
1420 $n_processed_rows++;
1423 if ($db->num_rows($resql_line) == 0) {
1426 while ($obj_line = $db->fetch_object($resql_line)) {
1427 if (!$remaining_qty) {
1430 if (!$obj_line->rowid) {
1433 $qty_for_line = min($remaining_qty, $obj_line->qty);
1434 if ($first_iteration) {
1435 $sql_attach =
'UPDATE '.MAIN_DB_PREFIX.
'commande_fournisseur_dispatch';
1436 $sql_attach .=
' SET fk_commandefourndet = '.((int) $obj_line->rowid).
', qty = '.((
float) $qty_for_line);
1437 $sql_attach .=
' WHERE rowid = '.((int) $obj_dispatch->rowid);
1438 $first_iteration =
false;
1440 $sql_attach_values = array(
1441 ((
int) $obj_dispatch->fk_commande),
1442 ((
int) $obj_dispatch->fk_product),
1443 ((
int) $obj_line->rowid),
1444 ((
float) $qty_for_line),
1445 ((
int) $obj_dispatch->fk_entrepot),
1446 ((
int) $obj_dispatch->fk_user),
1447 $obj_dispatch->datec ?
"'".$db->idate($db->jdate($obj_dispatch->datec)).
"'" :
'NULL',
1448 $obj_dispatch->comment ?
"'".$db->escape($obj_dispatch->comment).
"'" :
'NULL',
1449 $obj_dispatch->status ? ((
int) $obj_dispatch->status) :
'NULL',
1450 $obj_dispatch->tms ?
"'".$db->idate($db->jdate($obj_dispatch->tms)).
"'" :
'NULL',
1451 $obj_dispatch->batch ?
"'".$db->escape($obj_dispatch->batch).
"'" :
'NULL',
1452 $obj_dispatch->eatby ?
"'".$db->escape($obj_dispatch->eatby).
"'" :
'NULL',
1453 $obj_dispatch->sellby ?
"'".$db->escape($obj_dispatch->sellby).
"'" :
'NULL'
1455 $sql_attach_values = join(
', ', $sql_attach_values);
1457 $sql_attach =
'INSERT INTO '.MAIN_DB_PREFIX.
'commande_fournisseur_dispatch';
1458 $sql_attach .=
' (fk_commande, fk_product, fk_commandefourndet, qty, fk_entrepot, fk_user, datec, comment, status, tms, batch, eatby, sellby)';
1459 $sql_attach .=
" VALUES (".$sql_attach_values.
")";
1462 if ($repair_link_dispatch_lines_supplier_order_lines ==
'confirmed') {
1463 $resql_attach = $db->query($sql_attach);
1465 $resql_attach =
true;
1468 if ($resql_attach) {
1469 $remaining_qty -= $qty_for_line;
1471 $errors[] = $sql_attach;
1474 $first_iteration =
false;
1476 $n_processed_rows++;
1479 if (!($n_processed_rows & 0xff)) {
1480 echo
'<tr><td>Processed '.$n_processed_rows.
' rows with '.count($errors).
' errors…'.
"</td></tr>\n";
1486 echo
'<tr><td>Unable to find any dispatch without an fk_commandefourndet.'.
"</td></tr>\n";
1487 echo $sql_dispatch.
"\n";
1489 echo
'<tr><td>Fixed '.$n_processed_rows.
' rows with '.count($errors).
' errors…'.
"</td></tr>\n";
1490 echo
'<tr><td>DONE.'.
"</td></tr>\n";
1492 if (count($errors)) {
1494 echo
'<tr><td>The transaction was rolled back due to errors: nothing was changed by the script.</td></tr>';
1500 echo
'<tr><td><h3>SQL queries with errors:</h3></tr></td>';
1501 echo
'<tr><td>'.join(
'</td></tr><tr><td>', $errors).
'</td></tr>';
1508 if (empty($actiondone)) {
1509 print
'<div class="error">'.$langs->trans(
"ErrorWrongParameters").
'</div>';
1512 if ($oneoptionset) {
1513 print
'<div class="center" style="padding-top: 10px"><a href="../index.php?mainmenu=home&leftmenu=home'.(GETPOSTISSET(
"login") ?
'&username='.urlencode(
GETPOST(
"login")) :
'').
'">';
1514 print $langs->trans(
"GoToDolibarr");
1517 print
'<div class="center warning" style="padding-top: 10px">';
1518 print $langs->trans(
"SetAtLeastOneOptionAsUrlParameter");
1525 if ($db->connected) {
1530 if (!$ok && isset($argv[1])) {
run_sql($sqlfile, $silent=1, $entity='', $usesavepoint=1, $handler='', $okerror='default', $linelengthlimit=32768, $nocommentremoval=0, $offsetforchartofaccount=0, $colspan=0, $onlysqltoimportwebsite=0)
Launch a sql file.
Classe permettant la gestion des paiements des charges La tva collectee n'est calculee que sur les fa...
Class to manage predefined suppliers products.
Class to manage customers orders.
Class to manage contracts.
Class to manage suppliers invoices.
Class to manage invoices.
Class to manage proposals.
Class to manage third parties objects (customers, suppliers, prospects...)
if(isModEnabled('facture') &&!empty($user->rights->facture->lire)) if((isModEnabled('fournisseur') &&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD) && $user->hasRight("fournisseur", "facture", "lire"))||(isModEnabled('supplier_invoice') && $user->hasRight("supplier_invoice", "lire"))) if(isModEnabled('don') &&!empty($user->rights->don->lire)) if(isModEnabled('tax') &&!empty($user->rights->tax->charges->lire)) if(isModEnabled('facture') &&isModEnabled('commande') && $user->hasRight("commande", "lire") &&empty($conf->global->WORKFLOW_DISABLE_CREATE_INVOICE_FROM_ORDER)) $resql
Social contributions to pay.
dol_copy($srcfile, $destfile, $newmask=0, $overwriteifexists=1)
Copy a file to another file.
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($dir, $nophperrors=0)
Remove a directory (not recursive, so content must be empty).
dol_is_file($pathoffile)
Return if path is a file.
dol_dir_list($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.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0)
Returns text escaped for inclusion in HTML alt or title tags, or into values of HTML input fields.
dol_print_error($db='', $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
dol_strlen($string, $stringencoding='UTF-8')
Make a strlen call.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_buildpath($path, $type=0, $returnemptyifnotfound=0)
Return path of url or filesystem.
dol_mkdir($dir, $dataroot='', $newmask='')
Creation of a directory (this can create recursive subdir)
getDoliDBInstance($type, $host, $user, $pass, $name, $port)
Return a DoliDB instance (database handler).
vignette($file, $maxWidth=160, $maxHeight=120, $extName='_small', $quality=50, $outdir='thumbs', $targetformat=0)
Create a thumbnail from an image file (Supported extensions are gif, jpg, png and bmp).
image_format_supported($file, $acceptsvg=0)
Return if a filename is file name of a supported image format.
pHeader($subtitle, $next, $action='set', $param='', $forcejqueryurl='', $csstable='main-inside')
Show HTML header of install pages.
pFooter($nonext=0, $setuplang='', $jscheckfunction='', $withpleasewait=0, $morehtml='')
Print HTML footer of install pages.
dolibarr_install_syslog($message, $level=LOG_DEBUG)
Log function for install pages.
div float
Buy price without taxes.
clean_data_ecm_directories()
Clean data into ecm_directories table.
dol_decode($chain, $key='1')
Decode a base 64 encoded + specific delta change.