dolibarr  13.0.2
import.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2005-2016 Laurent Destailleur <eldy@users.sourceforge.net>
3  * Copyright (C) 2005-2009 Regis Houssin <regis.houssin@inodbox.com>
4  * Copyright (C) 2012 Christophe Battarel <christophe.battarel@altairis.fr>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program. If not, see <https://www.gnu.org/licenses/>.
18  */
19 
26 require_once '../main.inc.php';
27 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
28 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formother.class.php';
29 require_once DOL_DOCUMENT_ROOT.'/imports/class/import.class.php';
30 require_once DOL_DOCUMENT_ROOT.'/core/modules/import/modules_import.php';
31 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
32 require_once DOL_DOCUMENT_ROOT.'/core/lib/images.lib.php';
33 require_once DOL_DOCUMENT_ROOT.'/core/lib/import.lib.php';
34 
35 // Load translation files required by the page
36 $langs->loadLangs(array('exports', 'compta', 'errors'));
37 
38 // Security check
39 $result = restrictedArea($user, 'import');
40 
41 // Map icons, array duplicated in export.php, was not synchronized, TODO put it somewhere only once
42 $entitytoicon = array(
43  'invoice' => 'bill',
44  'invoice_line' => 'bill',
45  'order' => 'order',
46  'order_line' => 'order',
47  'propal' => 'propal',
48  'propal_line' => 'propal',
49  'intervention' => 'intervention',
50  'inter_line' => 'intervention',
51  'member' => 'user',
52  'member_type' => 'group',
53  'subscription' => 'payment',
54  'payment' => 'payment',
55  'tax' => 'bill',
56  'tax_type' => 'generic',
57  'other' => 'generic',
58  'account' => 'account',
59  'product' => 'product',
60  'virtualproduct'=>'product',
61  'subproduct' => 'product',
62  'product_supplier_ref' => 'product',
63  'stock' => 'stock',
64  'warehouse' => 'stock',
65  'batch' => 'stock',
66  'stockbatch' => 'stock',
67  'category' => 'category',
68  'shipment' => 'sending',
69  'shipment_line'=> 'sending',
70  'reception'=> 'sending',
71  'reception_line'=> 'sending',
72  'expensereport'=> 'trip',
73  'expensereport_line'=> 'trip',
74  'holiday' => 'holiday',
75  'contract_line' => 'contract',
76  'translation' => 'generic',
77  'bomm' => 'bom',
78  'bomline' => 'bom'
79 );
80 
81 // Translation code, array duplicated in export.php, was not synchronized, TODO put it somewhere only once
82 $entitytolang = array(
83  'user' => 'User',
84  'company' => 'Company',
85  'contact' => 'Contact',
86  'invoice' => 'Bill',
87  'invoice_line' => 'InvoiceLine',
88  'order' => 'Order',
89  'order_line' => 'OrderLine',
90  'propal' => 'Proposal',
91  'propal_line' => 'ProposalLine',
92  'intervention' => 'Intervention',
93  'inter_line' => 'InterLine',
94  'member' => 'Member',
95  'member_type' => 'MemberType',
96  'subscription' => 'Subscription',
97  'tax' => 'SocialContribution',
98  'tax_type' => 'DictionarySocialContributions',
99  'account' => 'BankTransactions',
100  'payment' => 'Payment',
101  'product' => 'Product',
102  'virtualproduct' => 'AssociatedProducts',
103  'subproduct' => 'SubProduct',
104  'product_supplier_ref' => 'SupplierPrices',
105  'service' => 'Service',
106  'stock' => 'Stock',
107  'movement' => 'StockMovement',
108  'batch' => 'Batch',
109  'stockbatch' => 'StockDetailPerBatch',
110  'warehouse' => 'Warehouse',
111  'category' => 'Category',
112  'other' => 'Other',
113  'trip' => 'TripsAndExpenses',
114  'shipment' => 'Shipments',
115  'shipment_line'=> 'ShipmentLine',
116  'project' => 'Projects',
117  'projecttask' => 'Tasks',
118  'task_time' => 'TaskTimeSpent',
119  'action' => 'Event',
120  'expensereport'=> 'ExpenseReport',
121  'expensereport_line'=> 'ExpenseReportLine',
122  'holiday' => 'TitreRequestCP',
123  'contract' => 'Contract',
124  'contract_line'=> 'ContractLine',
125  'translation' => 'Translation',
126  'bom' => 'BOM',
127  'bomline' => 'BOMLine'
128 );
129 
130 $datatoimport = GETPOST('datatoimport');
131 $format = GETPOST('format');
132 $filetoimport = GETPOST('filetoimport');
133 $action = GETPOST('action', 'alpha');
134 $confirm = GETPOST('confirm', 'alpha');
135 $step = (GETPOST('step') ? GETPOST('step') : 1);
136 $import_name = GETPOST('import_name');
137 $hexa = GETPOST('hexa');
138 $importmodelid = GETPOST('importmodelid');
139 $excludefirstline = (GETPOST('excludefirstline') ? GETPOST('excludefirstline') : 1);
140 $endatlinenb = (GETPOST('endatlinenb') ? GETPOST('endatlinenb') : '');
141 $updatekeys = (GETPOST('updatekeys', 'array') ? GETPOST('updatekeys', 'array') : array());
142 $separator = (GETPOST('separator', 'nohtml') ? GETPOST('separator', 'nohtml') : (!empty($conf->global->IMPORT_CSV_SEPARATOR_TO_USE) ? $conf->global->IMPORT_CSV_SEPARATOR_TO_USE : ','));
143 $enclosure = (GETPOST('enclosure', 'nohtml') ? GETPOST('enclosure', 'nohtml') : '"');
144 
145 $objimport = new Import($db);
146 $objimport->load_arrays($user, ($step == 1 ? '' : $datatoimport));
147 
148 $objmodelimport = new ModeleImports();
149 
150 $form = new Form($db);
151 $htmlother = new FormOther($db);
152 $formfile = new FormFile($db);
153 
154 // Init $array_match_file_to_database from _SESSION
155 $serialized_array_match_file_to_database = isset($_SESSION["dol_array_match_file_to_database"]) ? $_SESSION["dol_array_match_file_to_database"] : '';
156 $array_match_file_to_database = array();
157 $fieldsarray = explode(',', $serialized_array_match_file_to_database);
158 foreach ($fieldsarray as $elem)
159 {
160  $tabelem = explode('=', $elem, 2);
161  $key = $tabelem[0];
162  $val = (isset($tabelem[1]) ? $tabelem[1] : '');
163  if ($key && $val)
164  {
165  $array_match_file_to_database[$key] = $val;
166  }
167 }
168 
169 
170 /*
171  * Actions
172  */
173 
174 /*
175 if ($action=='downfield' || $action=='upfield')
176 {
177  $pos=$array_match_file_to_database[$_GET["field"]];
178  if ($action=='downfield') $newpos=$pos+1;
179  if ($action=='upfield') $newpos=$pos-1;
180  // Recherche code avec qui switcher
181  $newcode="";
182  foreach($array_match_file_to_database as $code=>$value)
183  {
184  if ($value == $newpos)
185  {
186  $newcode=$code;
187  break;
188  }
189  }
190  //print("Switch pos=$pos (code=".$_GET["field"].") and newpos=$newpos (code=$newcode)");
191  if ($newcode) // Si newcode trouve (protection contre resoumission de page)
192  {
193  $array_match_file_to_database[$_GET["field"]]=$newpos;
194  $array_match_file_to_database[$newcode]=$pos;
195  $_SESSION["dol_array_match_file_to_database"]=$serialized_array_match_file_to_database;
196  }
197 }
198 */
199 if ($action == 'builddoc')
200 {
201  // Build import file
202  $result = $objimport->build_file($user, GETPOST('model', 'alpha'), $datatoimport, $array_match_file_to_database);
203  if ($result < 0)
204  {
205  setEventMessages($objimport->error, $objimport->errors, 'errors');
206  } else {
207  setEventMessages($langs->trans("FileSuccessfullyBuilt"), null, 'mesgs');
208  }
209 }
210 
211 if ($action == 'deleteprof')
212 {
213  if (GETPOST("id", 'int'))
214  {
215  $objimport->fetch(GETPOST("id", 'int'));
216  $result = $objimport->delete($user);
217  }
218 }
219 
220 // Save import config to database
221 if ($action == 'add_import_model')
222 {
223  if ($import_name)
224  {
225  // Set save string
226  $hexa = '';
227  foreach ($array_match_file_to_database as $key=>$val)
228  {
229  if ($hexa) $hexa .= ',';
230  $hexa .= $key.'='.$val;
231  }
232 
233  $objimport->model_name = $import_name;
234  $objimport->datatoimport = $datatoimport;
235  $objimport->hexa = $hexa;
236 
237  $result = $objimport->create($user);
238  if ($result >= 0)
239  {
240  setEventMessages($langs->trans("ImportModelSaved", $objimport->model_name), null, 'mesgs');
241  } else {
242  $langs->load("errors");
243  if ($objimport->errno == 'DB_ERROR_RECORD_ALREADY_EXISTS')
244  {
245  setEventMessages($langs->trans("ErrorImportDuplicateProfil"), null, 'errors');
246  } else {
247  setEventMessages($objimport->error, null, 'errors');
248  }
249  }
250  } else {
251  setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentities("ImportModelName")), null, 'errors');
252  }
253 }
254 
255 if ($step == 3 && $datatoimport)
256 {
257  if (GETPOST('sendit') && !empty($conf->global->MAIN_UPLOAD_DOC))
258  {
259  dol_mkdir($conf->import->dir_temp);
260  $nowyearmonth = dol_print_date(dol_now(), '%Y%m%d%H%M%S');
261 
262  $fullpath = $conf->import->dir_temp."/".$nowyearmonth.'-'.$_FILES['userfile']['name'];
263  if (dol_move_uploaded_file($_FILES['userfile']['tmp_name'], $fullpath, 1) > 0)
264  {
265  dol_syslog("File ".$fullpath." was added for import");
266  } else {
267  $langs->load("errors");
268  setEventMessages($langs->trans("ErrorFailedToSaveFile"), null, 'errors');
269  }
270  }
271 
272  // Delete file
273  if ($action == 'confirm_deletefile' && $confirm == 'yes')
274  {
275  $langs->load("other");
276 
277  $param = '&datatoimport='.urlencode($datatoimport).'&format='.urlencode($format);
278  if ($excludefirstline) $param .= '&excludefirstline='.urlencode($excludefirstline);
279  if ($endatlinenb) $param .= '&endatlinenb='.urlencode($endatlinenb);
280 
281  $file = $conf->import->dir_temp.'/'.GETPOST('urlfile'); // Do not use urldecode here ($_GET and $_REQUEST are already decoded by PHP).
282  $ret = dol_delete_file($file);
283  if ($ret) setEventMessages($langs->trans("FileWasRemoved", GETPOST('urlfile')), null, 'mesgs');
284  else setEventMessages($langs->trans("ErrorFailToDeleteFile", GETPOST('urlfile')), null, 'errors');
285  Header('Location: '.$_SERVER["PHP_SELF"].'?step='.$step.$param);
286  exit;
287  }
288 }
289 
290 if ($step == 4 && $action == 'select_model')
291 {
292  // Reinit match arrays
293  $_SESSION["dol_array_match_file_to_database"] = '';
294  $serialized_array_match_file_to_database = '';
295  $array_match_file_to_database = array();
296 
297  // Load model from $importmodelid and set $array_match_file_to_database
298  // and $_SESSION["dol_array_match_file_to_database"]
299  $result = $objimport->fetch($importmodelid);
300  if ($result > 0)
301  {
302  $serialized_array_match_file_to_database = $objimport->hexa;
303  $fieldsarray = explode(',', $serialized_array_match_file_to_database);
304  foreach ($fieldsarray as $elem)
305  {
306  $tabelem = explode('=', $elem);
307  $key = $tabelem[0];
308  $val = $tabelem[1];
309  if ($key && $val)
310  {
311  $array_match_file_to_database[$key] = $val;
312  }
313  }
314  $_SESSION["dol_array_match_file_to_database"] = $serialized_array_match_file_to_database;
315  }
316 }
317 
318 if ($action == 'saveorder')
319 {
320  // Enregistrement de la position des champs
321  dol_syslog("boxorder=".$_GET['boxorder']." datatoimport=".$_GET["datatoimport"], LOG_DEBUG);
322  $part = explode(':', $_GET['boxorder']);
323  $colonne = $part[0];
324  $list = $part[1];
325  dol_syslog('column='.$colonne.' list='.$list);
326 
327  // Init targets fields array
328  $fieldstarget = $objimport->array_import_fields[0];
329 
330  // Reinit match arrays. We redefine array_match_file_to_database
331  $serialized_array_match_file_to_database = '';
332  $array_match_file_to_database = array();
333  $fieldsarray = explode(',', $list);
334  $pos = 0;
335  foreach ($fieldsarray as $fieldnb) // For each elem in list. fieldnb start from 1 to ...
336  {
337  // Get name of database fields at position $pos and put it into $namefield
338  $posbis = 0; $namefield = '';
339  foreach ($fieldstarget as $key => $val) // key: val:
340  {
341  //dol_syslog('AjaxImport key='.$key.' val='.$val);
342  if ($posbis < $pos)
343  {
344  $posbis++;
345  continue;
346  }
347  // We found the key of targets that is at position pos
348  $namefield = $key;
349  //dol_syslog('AjaxImport Field name found for file field nb '.$fieldnb.'='.$namefield);
350 
351  break;
352  }
353 
354  if ($fieldnb && $namefield)
355  {
356  $array_match_file_to_database[$fieldnb] = $namefield;
357  if ($serialized_array_match_file_to_database) $serialized_array_match_file_to_database .= ',';
358  $serialized_array_match_file_to_database .= ($fieldnb.'='.$namefield);
359  }
360 
361  $pos++;
362  }
363 
364  // We save new matching in session
365  $_SESSION["dol_array_match_file_to_database"] = $serialized_array_match_file_to_database;
366  dol_syslog('dol_array_match_file_to_database='.$serialized_array_match_file_to_database);
367 }
368 
369 
370 
371 
372 /*
373  * View
374  */
375 
376 
377 // STEP 1: Page to select dataset to import
378 if ($step == 1 || !$datatoimport)
379 {
380  // Clean saved file-database matching
381  $serialized_array_match_file_to_database = '';
382  $array_match_file_to_database = array();
383  $_SESSION["dol_array_match_file_to_database"] = '';
384 
385  $param = '';
386  if ($excludefirstline) $param .= '&excludefirstline='.urlencode($excludefirstline);
387  if ($endatlinenb) $param .= '&endatlinenb='.urlencode($endatlinenb);
388  if ($separator) $param .= '&separator='.urlencode($separator);
389  if ($enclosure) $param .= '&enclosure='.urlencode($enclosure);
390 
391  llxHeader('', $langs->trans("NewImport"), 'EN:Module_Imports_En|FR:Module_Imports|ES:M&oacute;dulo_Importaciones');
392 
393  $head = import_prepare_head($param, 1);
394 
395  print dol_get_fiche_head($head, 'step1', '', -1);
396 
397  print '<div class="opacitymedium">'.$langs->trans("SelectImportDataSet").'</div><br>';
398 
399  // Affiche les modules d'imports
400  print '<div class="div-table-responsive-no-min">'; // You can use div-table-responsive-no-min if you dont need reserved height for your table
401  print '<table class="noborder centpercent">';
402  print '<tr class="liste_titre">';
403  print '<td>'.$langs->trans("Module").'</td>';
404  print '<td>'.$langs->trans("ImportableDatas").'</td>';
405  print '<td>&nbsp;</td>';
406  print '</tr>';
407 
408  if (count($objimport->array_import_module))
409  {
410  $sortedarrayofmodules = dol_sort_array($objimport->array_import_module, 'position_of_profile', 'asc', 0, 0, 1);
411  foreach ($sortedarrayofmodules as $key => $value)
412  {
413  //var_dump($key.' '.$value['position_of_profile'].' '.$value['import_code'].' '.$objimport->array_import_module[$key]['module']->getName().' '.$objimport->array_import_code[$key]);
414  print '<tr class="oddeven"><td>';
415  $titleofmodule = $objimport->array_import_module[$key]['module']->getName();
416  // Special cas for import common to module/services
417  if (in_array($objimport->array_import_code[$key], array('produit_supplierprices', 'produit_multiprice', 'produit_languages'))) $titleofmodule = $langs->trans("ProductOrService");
418  print $titleofmodule;
419  print '</td><td>';
420  $entity = preg_replace('/:.*$/', '', $objimport->array_import_icon[$key]);
421  $entityicon = strtolower(!empty($entitytoicon[$entity]) ? $entitytoicon[$entity] : $entity);
422  print img_object($objimport->array_import_module[$key]['module']->getName(), $entityicon).' ';
423  print $objimport->array_import_label[$key];
424  print '</td><td style="text-align: right">';
425  if ($objimport->array_import_perms[$key])
426  {
427  print '<a href="'.DOL_URL_ROOT.'/imports/import.php?step=2&datatoimport='.$objimport->array_import_code[$key].$param.'">'.img_picto($langs->trans("NewImport"), 'next', 'class="fa-15x"').'</a>';
428  } else {
429  print $langs->trans("NotEnoughPermissions");
430  }
431  print '</td></tr>';
432  }
433  } else {
434  print '<tr><td class="oddeven" colspan="3">'.$langs->trans("NoImportableData").'</td></tr>';
435  }
436  print '</table>';
437  print '</div>';
438 
440 }
441 
442 
443 // STEP 2: Page to select input format file
444 if ($step == 2 && $datatoimport)
445 {
446  $param = '&datatoimport='.urlencode($datatoimport);
447  if ($excludefirstline) $param .= '&excludefirstline='.urlencode($excludefirstline);
448  if ($endatlinenb) $param .= '&endatlinenb='.urlencode($endatlinenb);
449  if ($separator) $param .= '&separator='.urlencode($separator);
450  if ($enclosure) $param .= '&enclosure='.urlencode($enclosure);
451 
452  llxHeader('', $langs->trans("NewImport"), 'EN:Module_Imports_En|FR:Module_Imports|ES:M&oacute;dulo_Importaciones');
453 
454  $head = import_prepare_head($param, 2);
455 
456  print dol_get_fiche_head($head, 'step2', '', -2);
457 
458  print '<div class="underbanner clearboth"></div>';
459  print '<div class="fichecenter">';
460 
461  print '<table width="100%" class="border tableforfield">';
462 
463  // Module
464  print '<tr><td class="titlefield">'.$langs->trans("Module").'</td>';
465  print '<td>';
466  $titleofmodule = $objimport->array_import_module[0]['module']->getName();
467  // Special cas for import common to module/services
468  if (in_array($objimport->array_import_code[0], array('produit_supplierprices', 'produit_multiprice', 'produit_languages'))) $titleofmodule = $langs->trans("ProductOrService");
469  print $titleofmodule;
470  print '</td></tr>';
471 
472  // Lot de donnees a importer
473  print '<tr><td>'.$langs->trans("DatasetToImport").'</td>';
474  print '<td>';
475  $entity = preg_replace('/:.*$/', '', $objimport->array_import_icon[0]);
476  $entityicon = strtolower(!empty($entitytoicon[$entity]) ? $entitytoicon[$entity] : $entity);
477  print img_object($objimport->array_import_module[0]['module']->getName(), $entityicon).' ';
478  print $objimport->array_import_label[0];
479  print '</td></tr>';
480 
481  print '</table>';
482  print '</div>';
483 
485 
486  print '<form name="userfile" action="'.$_SERVER["PHP_SELF"].'" enctype="multipart/form-data" METHOD="POST">';
487  print '<input type="hidden" name="token" value="'.newToken().'">';
488  print '<input type="hidden" name="max_file_size" value="'.$conf->maxfilesize.'">';
489 
490  print '<span class="opacitymedium">';
491  $s = $langs->trans("ChooseFormatOfFileToImport", '{s1}');
492  $s = str_replace('{s1}', img_picto('', 'next'), $s);
493  print $s;
494  print '</span><br><br>';
495 
496  print '<div class="div-table-responsive-no-min">'; // You can use div-table-responsive-no-min if you dont need reserved height for your table
497  print '<table class="noborder" width="100%" cellspacing="0" cellpadding="4">';
498 
499  $filetoimport = '';
500 
501  // Add format informations and link to download example
502  print '<tr class="liste_titre"><td colspan="6">';
503  print $langs->trans("FileMustHaveOneOfFollowingFormat");
504  print '</td></tr>';
505  $liste = $objmodelimport->liste_modeles($db);
506  foreach ($liste as $key)
507  {
508  print '<tr class="oddeven">';
509  print '<td width="16">'.img_picto_common($key, $objmodelimport->getPictoForKey($key)).'</td>';
510  $text = $objmodelimport->getDriverDescForKey($key);
511  print '<td>'.$form->textwithpicto($objmodelimport->getDriverLabelForKey($key), $text).'</td>';
512  print '<td style="text-align:center"><a href="'.DOL_URL_ROOT.'/imports/emptyexample.php?format='.$key.$param.'" target="_blank">'.$langs->trans("DownloadEmptyExample").'</a></td>';
513  // Action button
514  print '<td style="text-align:right">';
515  print '<a href="'.DOL_URL_ROOT.'/imports/import.php?step=3&format='.$key.$param.'">'.img_picto($langs->trans("SelectFormat"), 'next', 'class="fa-15x"').'</a>';
516  print '</td>';
517  print '</tr>';
518  }
519 
520  print '</table>';
521  print '</div>';
522 
523  print '</form>';
524 }
525 
526 
527 // STEP 3: Page to select file
528 if ($step == 3 && $datatoimport)
529 {
530  $param = '&datatoimport='.urlencode($datatoimport).'&format='.urlencode($format);
531  if ($excludefirstline) $param .= '&excludefirstline='.urlencode($excludefirstline);
532  if ($endatlinenb) $param .= '&endatlinenb='.urlencode($endatlinenb);
533  if ($separator) $param .= '&separator='.urlencode($separator);
534  if ($enclosure) $param .= '&enclosure='.urlencode($enclosure);
535 
536  $liste = $objmodelimport->liste_modeles($db);
537 
538  llxHeader('', $langs->trans("NewImport"), 'EN:Module_Imports_En|FR:Module_Imports|ES:M&oacute;dulo_Importaciones');
539 
540  $head = import_prepare_head($param, 3);
541 
542  print dol_get_fiche_head($head, 'step3', '', -2);
543 
544  /*
545  * Confirm delete file
546  */
547  if ($action == 'delete')
548  {
549  print $form->formconfirm($_SERVER["PHP_SELF"].'?urlfile='.urlencode(GETPOST('urlfile')).'&step=3'.$param, $langs->trans('DeleteFile'), $langs->trans('ConfirmDeleteFile'), 'confirm_deletefile', '', 0, 1);
550  }
551 
552  print '<div class="underbanner clearboth"></div>';
553  print '<div class="fichecenter">';
554 
555  print '<table width="100%" class="border tableforfield">';
556 
557  // Module
558  print '<tr><td class="titlefield">'.$langs->trans("Module").'</td>';
559  print '<td>';
560  $titleofmodule = $objimport->array_import_module[0]['module']->getName();
561  // Special cas for import common to module/services
562  if (in_array($objimport->array_import_code[0], array('produit_supplierprices', 'produit_multiprice', 'produit_languages'))) $titleofmodule = $langs->trans("ProductOrService");
563  print $titleofmodule;
564  print '</td></tr>';
565 
566  // Lot de donnees a importer
567  print '<tr><td>'.$langs->trans("DatasetToImport").'</td>';
568  print '<td>';
569  $entity = preg_replace('/:.*$/', '', $objimport->array_import_icon[0]);
570  $entityicon = strtolower(!empty($entitytoicon[$entity]) ? $entitytoicon[$entity] : $entity);
571  print img_object($objimport->array_import_module[0]['module']->getName(), $entityicon).' ';
572  print $objimport->array_import_label[0];
573  print '</td></tr>';
574 
575  print '</table>';
576  print '</div>';
577 
578  print load_fiche_titre($langs->trans("InformationOnSourceFile"), '', '');
579 
580  print '<div class="underbanner clearboth"></div>';
581  print '<div class="fichecenter">';
582  print '<table width="100%" class="border tableforfield">';
583 
584  // Source file format
585  print '<tr><td class="titlefield">'.$langs->trans("SourceFileFormat").'</td>';
586  print '<td>';
587  $text = $objmodelimport->getDriverDescForKey($format);
588  print $form->textwithpicto($objmodelimport->getDriverLabelForKey($format), $text);
589  print '</td><td style="text-align:right" class="nowrap"><a href="'.DOL_URL_ROOT.'/imports/emptyexample.php?format='.$format.$param.'" target="_blank">'.$langs->trans("DownloadEmptyExample").'</a>';
590 
591  print '</td></tr>';
592 
593  print '</table>';
594  print '</div>';
595 
596  print dol_get_fiche_end();
597 
598 
599  if ($format == 'xlsx' && !class_exists('XMLWriter')) {
600  $langs->load("install");
601  print info_admin($langs->trans("ErrorPHPDoesNotSupport", 'php-xml'), 0, 0, 1, 'error');
602  }
603 
604 
605  print '<br>';
606 
607  print '<form name="userfile" action="'.$_SERVER["PHP_SELF"].'" enctype="multipart/form-data" METHOD="POST">';
608  print '<input type="hidden" name="token" value="'.newToken().'">';
609  print '<input type="hidden" name="max_file_size" value="'.$conf->maxfilesize.'">';
610 
611  print '<input type="hidden" value="'.$step.'" name="step">';
612  print '<input type="hidden" value="'.dol_escape_htmltag($format).'" name="format">';
613  print '<input type="hidden" value="'.$excludefirstline.'" name="excludefirstline">';
614  print '<input type="hidden" value="'.$endatlinenb.'" name="endatlinenb">';
615  print '<input type="hidden" value="'.dol_escape_htmltag($separator).'" name="separator">';
616  print '<input type="hidden" value="'.dol_escape_htmltag($enclosure).'" name="enclosure">';
617  print '<input type="hidden" value="'.dol_escape_htmltag($datatoimport).'" name="datatoimport">';
618 
619  print '<span class="opacitymedium">';
620  $s = $langs->trans("ChooseFileToImport", '{s1}');
621  $s = str_replace('{s1}', img_picto('', 'next'), $s);
622  print $s;
623  print '</span><br><br>';
624 
625  print '<div class="div-table-responsive-no-min">'; // You can use div-table-responsive-no-min if you dont need reserved height for your table
626  print '<table class="noborder" width="100%" cellspacing="0" cellpadding="4">';
627 
628  $filetoimport = '';
629 
630  //print '<tr class="liste_titre"><td colspan="6">'.$langs->trans("FileWithDataToImport").'</td></tr>';
631 
632  // Input file name box
633  print '<tr class="oddeven nohover"><td colspan="6">';
634  print '<input type="file" name="userfile" size="20" maxlength="80"> &nbsp; &nbsp; ';
635  $out = (empty($conf->global->MAIN_UPLOAD_DOC) ? ' disabled' : '');
636  print '<input type="submit" class="button" value="'.$langs->trans("AddFile").'"'.$out.' name="sendit">';
637  $out = '';
638  if (!empty($conf->global->MAIN_UPLOAD_DOC))
639  {
640  $max = $conf->global->MAIN_UPLOAD_DOC; // In Kb
641  $maxphp = @ini_get('upload_max_filesize'); // In unknown
642  if (preg_match('/k$/i', $maxphp)) $maxphp = $maxphp * 1;
643  if (preg_match('/m$/i', $maxphp)) $maxphp = $maxphp * 1024;
644  if (preg_match('/g$/i', $maxphp)) $maxphp = $maxphp * 1024 * 1024;
645  if (preg_match('/t$/i', $maxphp)) $maxphp = $maxphp * 1024 * 1024 * 1024;
646  $maxphp2 = @ini_get('post_max_size'); // In unknown
647  if (preg_match('/k$/i', $maxphp2)) $maxphp2 = $maxphp2 * 1;
648  if (preg_match('/m$/i', $maxphp2)) $maxphp2 = $maxphp2 * 1024;
649  if (preg_match('/g$/i', $maxphp2)) $maxphp2 = $maxphp2 * 1024 * 1024;
650  if (preg_match('/t$/i', $maxphp2)) $maxphp2 = $maxphp2 * 1024 * 1024 * 1024;
651  // Now $max and $maxphp and $maxphp2 are in Kb
652  $maxmin = $max;
653  $maxphptoshow = $maxphptoshowparam = '';
654  if ($maxphp > 0)
655  {
656  $maxmin = min($max, $maxphp);
657  $maxphptoshow = $maxphp;
658  $maxphptoshowparam = 'upload_max_filesize';
659  }
660  if ($maxphp2 > 0)
661  {
662  $maxmin = min($max, $maxphp2);
663  if ($maxphp2 < $maxphp)
664  {
665  $maxphptoshow = $maxphp2;
666  $maxphptoshowparam = 'post_max_size';
667  }
668  }
669 
670  $langs->load('other');
671  $out .= ' ';
672  $out .= info_admin($langs->trans("ThisLimitIsDefinedInSetup", $max, $maxphptoshow), 1);
673  } else {
674  $out .= ' ('.$langs->trans("UploadDisabled").')';
675  }
676  print $out;
677  print '</td>';
678  print "</tr>\n";
679 
680  // Search available imports
681  $filearray = dol_dir_list($conf->import->dir_temp, 'files', 0, '', '', 'name', SORT_DESC);
682  if (count($filearray) > 0)
683  {
684  $dir = $conf->import->dir_temp;
685 
686  // Search available files to import
687  $i = 0;
688  foreach ($filearray as $key => $val)
689  {
690  $file = $val['name'];
691 
692  // readdir return value in ISO and we want UTF8 in memory
693  if (!utf8_check($file)) $file = utf8_encode($file);
694 
695  if (preg_match('/^\./', $file)) continue;
696 
697  $modulepart = 'import';
698  $urlsource = $_SERVER["PHP_SELF"].'?step='.$step.$param.'&filetoimport='.urlencode($filetoimport);
699  $relativepath = $file;
700 
701  print '<tr class="oddeven">';
702  print '<td width="16">'.img_mime($file).'</td>';
703  print '<td>';
704  print '<a data-ajax="false" href="'.DOL_URL_ROOT.'/document.php?modulepart='.$modulepart.'&file='.urlencode($relativepath).'&step=3'.$param.'" target="_blank">';
705  print $file;
706  print '</a>';
707  print '</td>';
708  // Affiche taille fichier
709  print '<td style="text-align:right">'.dol_print_size(dol_filesize($dir.'/'.$file)).'</td>';
710  // Affiche date fichier
711  print '<td style="text-align:right">'.dol_print_date(dol_filemtime($dir.'/'.$file), 'dayhour').'</td>';
712  // Del button
713  print '<td style="text-align:right"><a href="'.$_SERVER['PHP_SELF'].'?action=delete&token='.newToken().'&step=3'.$param.'&urlfile='.urlencode($relativepath);
714  print '">'.img_delete().'</a></td>';
715  // Action button
716  print '<td style="text-align:right">';
717  print '<a href="'.$_SERVER['PHP_SELF'].'?step=4'.$param.'&filetoimport='.urlencode($relativepath).'">'.img_picto($langs->trans("NewImport"), 'next', 'class="fa-15x"').'</a>';
718  print '</td>';
719  print '</tr>';
720  }
721  }
722 
723  print '</table>';
724  print '</div>';
725 
726  print '</form>';
727 }
728 
729 
730 // STEP 4: Page to make matching between source file and database fields
731 if ($step == 4 && $datatoimport)
732 {
733  $model = $format;
734  $liste = $objmodelimport->liste_modeles($db);
735 
736  // Create classe to use for import
737  $dir = DOL_DOCUMENT_ROOT."/core/modules/import/";
738  $file = "import_".$model.".modules.php";
739  $classname = "Import".ucfirst($model);
740  require_once $dir.$file;
741  $obj = new $classname($db, $datatoimport);
742  if ($model == 'csv')
743  {
744  $obj->separator = $separator;
745  $obj->enclosure = $enclosure;
746  }
747  if ($model == 'xlsx') {
748  if (!preg_match('/\.xlsx$/i', $filetoimport))
749  {
750  $langs->load("errors");
751  $param = '&datatoimport='.$datatoimport.'&format='.$format;
752  setEventMessages($langs->trans("ErrorFileMustHaveFormat", $model), null, 'errors');
753  header("Location: ".$_SERVER["PHP_SELF"].'?step=3'.$param.'&filetoimport='.urlencode($relativepath));
754  exit;
755  }
756  }
757 
758  if (GETPOST('update')) {
759  $array_match_file_to_database = array();
760  }
761 
762  // Load source fields in input file
763  $fieldssource = array();
764  $result = $obj->import_open_file($conf->import->dir_temp.'/'.$filetoimport, $langs);
765  if ($result >= 0)
766  {
767  // Read first line
768  $arrayrecord = $obj->import_read_record();
769  // Put into array fieldssource starting with 1.
770  $i = 1;
771  foreach ($arrayrecord as $key => $val)
772  {
773  $fieldssource[$i]['example1'] = dol_trunc($val['val'], 24);
774  $i++;
775  }
776  $obj->import_close_file();
777  }
778 
779  // Load targets fields in database
780  $fieldstarget = $objimport->array_import_fields[0];
781 
782  $maxpos = max(count($fieldssource), count($fieldstarget));
783 
784  //var_dump($array_match_file_to_database);
785 
786  // Is it a first time in page (if yes, we must initialize array_match_file_to_database)
787  if (count($array_match_file_to_database) == 0)
788  {
789  // This is first input in screen, we need to define
790  // $array_match_file_to_database
791  // $serialized_array_match_file_to_database
792  // $_SESSION["dol_array_match_file_to_database"]
793  $pos = 1;
794  $num = count($fieldssource);
795  while ($pos <= $num)
796  {
797  if ($num >= 1 && $pos <= $num)
798  {
799  $posbis = 1;
800  foreach ($fieldstarget as $key => $val)
801  {
802  if ($posbis < $pos)
803  {
804  $posbis++;
805  continue;
806  }
807  // We found the key of targets that is at position pos
808  $array_match_file_to_database[$pos] = $key;
809  if ($serialized_array_match_file_to_database) $serialized_array_match_file_to_database .= ',';
810  $serialized_array_match_file_to_database .= ($pos.'='.$key);
811  break;
812  }
813  }
814  $pos++;
815  }
816  // Save the match array in session. We now will use the array in session.
817  $_SESSION["dol_array_match_file_to_database"] = $serialized_array_match_file_to_database;
818  }
819  $array_match_database_to_file = array_flip($array_match_file_to_database);
820 
821  //print $serialized_array_match_file_to_database;
822  //print $_SESSION["dol_array_match_file_to_database"];
823  //var_dump($array_match_file_to_database);exit;
824 
825  // Now $array_match_file_to_database contains fieldnb(1,2,3...)=>fielddatabase(key in $array_match_file_to_database)
826 
827  $param = '&format='.$format.'&datatoimport='.urlencode($datatoimport).'&filetoimport='.urlencode($filetoimport);
828  if ($excludefirstline) $param .= '&excludefirstline='.urlencode($excludefirstline);
829  if ($endatlinenb) $param .= '&endatlinenb='.urlencode($endatlinenb);
830  if ($separator) $param .= '&separator='.urlencode($separator);
831  if ($enclosure) $param .= '&enclosure='.urlencode($enclosure);
832 
833  llxHeader('', $langs->trans("NewImport"), 'EN:Module_Imports_En|FR:Module_Imports|ES:M&oacute;dulo_Importaciones');
834 
835  $head = import_prepare_head($param, 4);
836 
837  print dol_get_fiche_head($head, 'step4', '', -2);
838 
839  print '<div class="underbanner clearboth"></div>';
840  print '<div class="fichecenter">';
841 
842  print '<table width="100%" class="border tableforfield">';
843 
844  // Module
845  print '<tr><td class="titlefield">'.$langs->trans("Module").'</td>';
846  print '<td>';
847  $titleofmodule = $objimport->array_import_module[0]['module']->getName();
848  // Special cas for import common to module/services
849  if (in_array($objimport->array_import_code[0], array('produit_supplierprices', 'produit_multiprice', 'produit_languages'))) $titleofmodule = $langs->trans("ProductOrService");
850  print $titleofmodule;
851  print '</td></tr>';
852 
853  // Lot de donnees a importer
854  print '<tr><td>'.$langs->trans("DatasetToImport").'</td>';
855  print '<td>';
856  $entity = preg_replace('/:.*$/', '', $objimport->array_import_icon[0]);
857  $entityicon = strtolower(!empty($entitytoicon[$entity]) ? $entitytoicon[$entity] : $entity);
858  print img_object($objimport->array_import_module[0]['module']->getName(), $entityicon).' ';
859  print $objimport->array_import_label[0];
860  print '</td></tr>';
861 
862  print '</table>';
863  print '</div>';
864 
865  print load_fiche_titre($langs->trans("InformationOnSourceFile"), '', '');
866 
867  print '<div class="underbanner clearboth"></div>';
868  print '<div class="fichecenter">';
869  print '<table width="100%" class="border tableforfield">';
870 
871  // Source file format
872  print '<tr><td class="titlefield">'.$langs->trans("SourceFileFormat").'</td>';
873  print '<td>';
874  $text = $objmodelimport->getDriverDescForKey($format);
875  print $form->textwithpicto($objmodelimport->getDriverLabelForKey($format), $text);
876  print '</td></tr>';
877 
878  // Separator and enclosure
879  if ($model == 'csv') {
880  print '<tr><td>'.$langs->trans("CsvOptions").'</td>';
881  print '<td>';
882  print '<form>';
883  print '<input type="hidden" name="token" value="'.newToken().'">';
884  print '<input type="hidden" value="'.$step.'" name="step">';
885  print '<input type="hidden" value="'.$format.'" name="format">';
886  print '<input type="hidden" value="'.$excludefirstline.'" name="excludefirstline">';
887  print '<input type="hidden" value="'.$endatlinenb.'" name="endatlinenb">';
888  print '<input type="hidden" value="'.$datatoimport.'" name="datatoimport">';
889  print '<input type="hidden" value="'.$filetoimport.'" name="filetoimport">';
890  print $langs->trans("Separator").' : ';
891  print '<input type="text" size="1" name="separator" value="'.dol_escape_htmltag($separator).'"/>';
892  print '&nbsp;&nbsp;&nbsp;&nbsp;'.$langs->trans("Enclosure").' : ';
893  print '<input type="text" size="1" name="enclosure" value="'.dol_escape_htmltag($enclosure).'"/>';
894  print '<input name="update" type="submit" value="'.$langs->trans('Update').'" class="button" />';
895  print '</form>';
896  print '</td></tr>';
897  }
898 
899  // File to import
900  print '<tr><td>'.$langs->trans("FileToImport").'</td>';
901  print '<td>';
902  $modulepart = 'import';
903  $relativepath = GETPOST('filetoimport');
904  print '<a data-ajax="false" href="'.DOL_URL_ROOT.'/document.php?modulepart='.$modulepart.'&file='.urlencode($relativepath).'&step=4'.$param.'" target="_blank">';
905  print $filetoimport;
906  print '</a>';
907  print '</td></tr>';
908 
909  print '</table>';
910  print '</div>';
911 
912  print dol_get_fiche_end();
913 
914  print '<br>'."\n";
915 
916 
917  // List of source fields
918  print '<!-- List of source fields -->'."\n";
919  print '<form action="'.$_SERVER["PHP_SELF"].'" method="post">';
920  print '<input type="hidden" name="token" value="'.newToken().'">';
921  print '<input type="hidden" name="action" value="select_model">';
922  print '<input type="hidden" name="step" value="4">';
923  print '<input type="hidden" name="format" value="'.$format.'">';
924  print '<input type="hidden" name="datatoimport" value="'.$datatoimport.'">';
925  print '<input type="hidden" name="filetoimport" value="'.$filetoimport.'">';
926  print '<input type="hidden" name="excludefirstline" value="'.$excludefirstline.'">';
927  print '<input type="hidden" name="endatlinenb" value="'.$endatlinenb.'">';
928  print '<input type="hidden" name="separator" value="'.dol_escape_htmltag($separator).'">';
929  print '<input type="hidden" name="enclosure" value="'.dol_escape_htmltag($enclosure).'">';
930 
931  print '<div class="marginbottomonly">';
932  print '<span class="opacitymedium">';
933  $s = $langs->trans("SelectImportFields", '{s1}');
934  $s = str_replace('{s1}', img_picto('', 'grip_title', '', false, 0, 0, '', '', 0), $s);
935  print $s;
936  print '</span> ';
937  $htmlother->select_import_model($importmodelid, 'importmodelid', $datatoimport, 1);
938  print '<input type="submit" class="button" value="'.$langs->trans("Select").'">';
939  print '</div>';
940  print '</form>';
941 
942  // Title of array with fields
943  print '<div class="div-table-responsive-no-min">'; // You can use div-table-responsive-no-min if you dont need reserved height for your table
944  print '<table class="noborder centpercent">';
945  print '<tr class="liste_titre">';
946  print '<td>'.$langs->trans("FieldsInSourceFile").'</td>';
947  print '<td>'.$langs->trans("FieldsInTargetDatabase").'</td>';
948  print '</tr>';
949 
950  //var_dump($array_match_file_to_database);
951 
952  print '<tr valign="top"><td width="50%">';
953 
954  $fieldsplaced = array();
955  $valforsourcefieldnb = array();
956  $listofkeys = array();
957  foreach ($array_match_file_to_database as $key => $val)
958  {
959  $listofkeys[$key] = 1;
960  }
961 
962  print "\n<!-- Box left container -->\n";
963  print '<div id="left" class="connectedSortable">'."\n";
964 
965  // List of source fields
966  $var = true;
967  $lefti = 1;
968  foreach ($array_match_file_to_database as $key => $val)
969  {
970  $var = !$var;
971  show_elem($fieldssource, $key, $val, $var); // key is field number in source file
972  //print '> '.$lefti.'-'.$key.'-'.$val;
973  $listofkeys[$key] = 1;
974  $fieldsplaced[$key] = 1;
975  $valforsourcefieldnb[$lefti] = $key;
976  $lefti++;
977 
978  if ($lefti > count($fieldstarget)) break; // Other fields are in the not imported area
979  }
980  //var_dump($valforsourcefieldnb);
981 
982  // Complete source fields from count($fieldssource)+1 to count($fieldstarget)
983  $more = 1;
984  $num = count($fieldssource);
985  while ($lefti <= $num)
986  {
987  $var = !$var;
988  $newkey = getnewkey($fieldssource, $listofkeys);
989  show_elem($fieldssource, $newkey, '', $var); // key start after field number in source file
990  //print '> '.$lefti.'-'.$newkey;
991  $listofkeys[$key] = 1;
992  $lefti++;
993  $more++;
994  }
995 
996  print "</div>\n";
997  print "<!-- End box left container -->\n";
998 
999 
1000  print '</td><td width="50%">';
1001 
1002  // List of target fields
1003  $height = '24px'; //needs px for css height attribute below
1004  $i = 0;
1005  $mandatoryfieldshavesource = true;
1006 
1007  print '<table width="100%" class="nobordernopadding">';
1008  foreach ($fieldstarget as $code=>$label)
1009  {
1010  print '<tr class="oddeven" style="height:'.$height.'">';
1011 
1012  $i++;
1013  $entity = (!empty($objimport->array_import_entities[0][$code]) ? $objimport->array_import_entities[0][$code] : $objimport->array_import_icon[0]);
1014 
1015  $tablealias = preg_replace('/(\..*)$/i', '', $code);
1016  $tablename = $objimport->array_import_tables[0][$tablealias];
1017 
1018  $entityicon = $entitytoicon[$entity] ? $entitytoicon[$entity] : $entity; // $entityicon must string name of picto of the field like 'project', 'company', 'contact', 'modulename', ...
1019  $entitylang = $entitytolang[$entity] ? $entitytolang[$entity] : $objimport->array_import_label[0]; // $entitylang must be a translation key to describe object the field is related to, like 'Company', 'Contact', 'MyModyle', ...
1020 
1021  print '<td class="nowrap" style="font-weight: normal">=>'.img_object('', $entityicon).' '.$langs->trans($entitylang).'</td>';
1022  print '<td style="font-weight: normal">';
1023  $newlabel = preg_replace('/\*$/', '', $label);
1024  $text = $langs->trans($newlabel);
1025  $more = '';
1026  if (preg_match('/\*$/', $label))
1027  {
1028  $text = '<span class="fieldrequired">'.$text.'</span>';
1029  $more = ((!empty($valforsourcefieldnb[$i]) && $valforsourcefieldnb[$i] <= count($fieldssource)) ? '' : img_warning($langs->trans("FieldNeedSource")));
1030  if ($mandatoryfieldshavesource) $mandatoryfieldshavesource = (!empty($valforsourcefieldnb[$i]) && ($valforsourcefieldnb[$i] <= count($fieldssource)));
1031  //print 'xx'.($i).'-'.$valforsourcefieldnb[$i].'-'.$mandatoryfieldshavesource;
1032  }
1033  print $text;
1034  print '</td>';
1035  // Info field
1036  print '<td style="font-weight:normal; text-align:right">';
1037  $filecolumn = $array_match_database_to_file[$code];
1038  // Source field info
1039  $htmltext = '<b><u>'.$langs->trans("FieldSource").'</u></b><br>';
1040  if ($filecolumn > count($fieldssource)) $htmltext .= $langs->trans("DataComeFromNoWhere").'<br>';
1041  else {
1042  if (empty($objimport->array_import_convertvalue[0][$code])) // If source file does not need convertion
1043  {
1044  $filecolumntoshow = $filecolumn;
1045  $htmltext .= $langs->trans("DataComeFromFileFieldNb", $filecolumntoshow).'<br>';
1046  } else {
1047  if ($objimport->array_import_convertvalue[0][$code]['rule'] == 'fetchidfromref') $htmltext .= $langs->trans("DataComeFromIdFoundFromRef", $filecolumn, $langs->transnoentitiesnoconv($entitylang)).'<br>';
1048  if ($objimport->array_import_convertvalue[0][$code]['rule'] == 'fetchidfromcodeid') $htmltext .= $langs->trans("DataComeFromIdFoundFromCodeId", $filecolumn, $langs->transnoentitiesnoconv($objimport->array_import_convertvalue[0][$code]['dict'])).'<br>';
1049  }
1050  }
1051  // Source required
1052  $htmltext .= $langs->trans("SourceRequired").': <b>'.yn(preg_match('/\*$/', $label)).'</b><br>';
1053  $example = $objimport->array_import_examplevalues[0][$code];
1054  // Example
1055  if (empty($objimport->array_import_convertvalue[0][$code])) // If source file does not need convertion
1056  {
1057  if ($example) $htmltext .= $langs->trans("SourceExample").': <b>'.$example.'</b><br>';
1058  } else {
1059  if ($objimport->array_import_convertvalue[0][$code]['rule'] == 'fetchidfromref') $htmltext .= $langs->trans("SourceExample").': <b>'.$langs->transnoentitiesnoconv("ExampleAnyRefFoundIntoElement", $entitylang).($example ? ' ('.$langs->transnoentitiesnoconv("Example").': '.$example.')' : '').'</b><br>';
1060  elseif ($objimport->array_import_convertvalue[0][$code]['rule'] == 'fetchidfromcodeid') $htmltext .= $langs->trans("SourceExample").': <b>'.$langs->trans("ExampleAnyCodeOrIdFoundIntoDictionary", $langs->transnoentitiesnoconv($objimport->array_import_convertvalue[0][$code]['dict'])).($example ? ' ('.$langs->transnoentitiesnoconv("Example").': '.$example.')' : '').'</b><br>';
1061  elseif ($example) $htmltext .= $langs->trans("SourceExample").': <b>'.$example.'</b><br>';
1062  }
1063  // Format control rule
1064  if (!empty($objimport->array_import_regex[0][$code]))
1065  {
1066  $htmltext .= $langs->trans("FormatControlRule").': <b>'.$objimport->array_import_regex[0][$code].'</b><br>';
1067  }
1068  $htmltext .= '<br>';
1069  // Target field info
1070  $htmltext .= '<b><u>'.$langs->trans("FieldTarget").'</u></b><br>';
1071  if (empty($objimport->array_import_convertvalue[0][$code])) // If source file does not need convertion
1072  {
1073  $htmltext .= $langs->trans("DataIsInsertedInto").'<br>';
1074  } else {
1075  if ($objimport->array_import_convertvalue[0][$code]['rule'] == 'fetchidfromref') $htmltext .= $langs->trans("DataIDSourceIsInsertedInto").'<br>';
1076  if ($objimport->array_import_convertvalue[0][$code]['rule'] == 'fetchidfromcodeid') $htmltext .= $langs->trans("DataCodeIDSourceIsInsertedInto").'<br>';
1077  }
1078  $htmltext .= $langs->trans("FieldTitle").": <b>".$langs->trans($newlabel)."</b><br>";
1079  $htmltext .= $langs->trans("Table")." -> ".$langs->trans("Field").': <b>'.$tablename." -> ".preg_replace('/^.*\./', '', $code)."</b><br>";
1080  print $form->textwithpicto($more, $htmltext);
1081  print '</td>';
1082 
1083  print '</tr>';
1084  $save_select .= $bit;
1085  }
1086  print '</table>';
1087 
1088  print '</td></tr>';
1089 
1090  // List of not imported fields
1091  print '<tr class="liste_titre"><td colspan="2">'.$langs->trans("NotImportedFields").'</td></tr>';
1092 
1093  print '<tr valign="top"><td width="50%">';
1094 
1095  print "\n<!-- Box ignore container -->\n";
1096  print '<div id="right" class="connectedSortable">'."\n";
1097 
1098  $nbofnotimportedfields = 0;
1099  foreach ($fieldssource as $key => $val)
1100  {
1101  if (empty($fieldsplaced[$key]))
1102  {
1103  //
1104  $nbofnotimportedfields++;
1105  show_elem($fieldssource, $key, '', $var, 'nostyle');
1106  //print '> '.$lefti.'-'.$key;
1107  $listofkeys[$key] = 1;
1108  $lefti++;
1109  }
1110  }
1111 
1112  // Print one more empty field
1113  $newkey = getnewkey($fieldssource, $listofkeys);
1114  show_elem($fieldssource, $newkey, '', $var, 'nostyle');
1115  //print '> '.$lefti.'-'.$newkey;
1116  $listofkeys[$newkey] = 1;
1117  $nbofnotimportedfields++;
1118 
1119  print "</div>\n";
1120  print "<!-- End box ignore container -->\n";
1121 
1122  print '</td>';
1123  print '<td width="50%">';
1124  $i = 0;
1125  while ($i < $nbofnotimportedfields)
1126  {
1127  // Print empty cells
1128  show_elem('', '', 'none', $var, 'nostyle');
1129  $i++;
1130  }
1131  print '</td></tr>';
1132 
1133  print '</table>';
1134  print '</div>';
1135 
1136 
1137  if ($conf->use_javascript_ajax)
1138  {
1139  print '<script type="text/javascript" language="javascript">';
1140  print 'jQuery(function() {
1141  jQuery("#left, #right").sortable({
1142  /* placeholder: \'ui-state-highlight\', */
1143  handle: \'.boxhandle\',
1144  revert: \'invalid\',
1145  items: \'.box\',
1146  containment: \'.fiche\',
1147  connectWith: \'.connectedSortable\',
1148  stop: function(event, ui) {
1149  updateOrder();
1150  }
1151  });
1152  });
1153  ';
1154  print "\n";
1155  print 'function updateOrder(){'."\n";
1156  print 'var left_list = cleanSerialize(jQuery("#left").sortable("serialize" ));'."\n";
1157  //print 'var right_list = cleanSerialize(jQuery("#right").sortable("serialize" ));'."\n";
1158  print 'var boxorder = \'A:\' + left_list;'."\n";
1159  //print 'var boxorder = \'A:\' + left_list + \'-B:\' + right_list;'."\n";
1160  //print 'alert(\'boxorder=\' + boxorder);';
1161  //print 'var userid = \''.$user->id.'\';'."\n";
1162  //print 'var datatoimport = "'.$datatoimport.'";'."\n";
1163  // print 'jQuery.ajax({ url: "ajaximport.php?step=4&boxorder=" + boxorder + "&userid=" + userid + "&datatoimport=" + datatoimport,
1164  // async: false
1165  // });'."\n";
1166  // Now reload page
1167  print 'var newlocation= \''.$_SERVER["PHP_SELF"].'?step=4'.$param.'&action=saveorder&boxorder=\' + boxorder;'."\n";
1168  //print 'alert(newlocation);';
1169  print 'window.location.href=newlocation;'."\n";
1170  print '}'."\n";
1171  print '</script>'."\n";
1172  }
1173 
1174  /*
1175  * Barre d'action
1176  */
1177  print '<div class="tabsAction">';
1178 
1179  if (count($array_match_file_to_database))
1180  {
1181  if ($mandatoryfieldshavesource)
1182  {
1183  print '<a class="butAction" href="import.php?step=5'.$param.'&filetoimport='.urlencode($filetoimport).'">'.$langs->trans("NextStep").'</a>';
1184  } else {
1185  print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("SomeMandatoryFieldHaveNoSource")).'">'.$langs->trans("NextStep").'</a>';
1186  }
1187  }
1188 
1189  print '</div>';
1190 
1191 
1192  // Area for profils import
1193  if (count($array_match_file_to_database))
1194  {
1195  print '<br>'."\n";
1196  print '<!-- Area to add new import profile -->'."\n";
1197  print '<div class="marginbottomonly"><span class="opacitymedium">'.$langs->trans("SaveImportModel").'</span></div>';
1198 
1199  print '<form class="nocellnopadd" action="'.$_SERVER["PHP_SELF"].'" method="post">';
1200  print '<input type="hidden" name="token" value="'.newToken().'">';
1201  print '<input type="hidden" name="action" value="add_import_model">';
1202  print '<input type="hidden" name="step" value="'.$step.'">';
1203  print '<input type="hidden" name="format" value="'.$format.'">';
1204  print '<input type="hidden" name="datatoimport" value="'.$datatoimport.'">';
1205  print '<input type="hidden" name="filetoimport" value="'.$filetoimport.'">';
1206  print '<input type="hidden" name="hexa" value="'.$hexa.'">';
1207  print '<input type="hidden" name="excludefirstline" value="'.$excludefirstline.'">';
1208  print '<input type="hidden" name="endatlinenb" value="'.$endatlinenb.'">';
1209  print '<input type="hidden" value="'.dol_escape_htmltag($separator).'" name="separator">';
1210  print '<input type="hidden" value="'.dol_escape_htmltag($enclosure).'" name="enclosure">';
1211 
1212  print '<table summary="selectofimportprofil" class="noborder centpercent">';
1213  print '<tr class="liste_titre">';
1214  print '<td>'.$langs->trans("ImportModelName").'</td>';
1215  print '<td>&nbsp;</td>';
1216  print '</tr>';
1217 
1218  print '<tr class="oddeven">';
1219  print '<td><input name="import_name" size="48" value=""></td><td style="text-align:right">';
1220  print '<input type="submit" class="button" value="'.$langs->trans("SaveImportProfile").'">';
1221  print '</td></tr>';
1222 
1223  // List of existing import profils
1224  $sql = "SELECT rowid, label";
1225  $sql .= " FROM ".MAIN_DB_PREFIX."import_model";
1226  $sql .= " WHERE type = '".$db->escape($datatoimport)."'";
1227  $sql .= " ORDER BY rowid";
1228  $resql = $db->query($sql);
1229  if ($resql)
1230  {
1231  $num = $db->num_rows($resql);
1232  $i = 0;
1233  while ($i < $num)
1234  {
1235  $obj = $db->fetch_object($resql);
1236  print '<tr class="oddeven"><td>';
1237  print $obj->label;
1238  print '</td><td style="text-align:right">';
1239  print '<a class="reposition" href="'.$_SERVER["PHP_SELF"].'?step='.$step.$param.'&action=deleteprof&token='.newToken().'&id='.$obj->rowid.'&filetoimport='.urlencode($filetoimport).'">';
1240  print img_delete();
1241  print '</a>';
1242  print '</tr>';
1243  $i++;
1244  }
1245  } else {
1246  dol_print_error($db);
1247  }
1248 
1249  print '</table>';
1250  print '</form>';
1251  }
1252 }
1253 
1254 
1255 // STEP 5: Summary of choices and launch simulation
1256 if ($step == 5 && $datatoimport)
1257 {
1258  $max_execution_time_for_importexport = (empty($conf->global->IMPORT_MAX_EXECUTION_TIME) ? 300 : $conf->global->IMPORT_MAX_EXECUTION_TIME); // 5mn if not defined
1259  $max_time = @ini_get("max_execution_time");
1260  if ($max_time && $max_time < $max_execution_time_for_importexport)
1261  {
1262  dol_syslog("max_execution_time=".$max_time." is lower than max_execution_time_for_importexport=".$max_execution_time_for_importexport.". We try to increase it dynamically.");
1263  @ini_set("max_execution_time", $max_execution_time_for_importexport); // This work only if safe mode is off. also web servers has timeout of 300
1264  }
1265 
1266  $model = $format;
1267  $liste = $objmodelimport->liste_modeles($db);
1268 
1269  // Create classe to use for import
1270  $dir = DOL_DOCUMENT_ROOT."/core/modules/import/";
1271  $file = "import_".$model.".modules.php";
1272  $classname = "Import".ucfirst($model);
1273  require_once $dir.$file;
1274  $obj = new $classname($db, $datatoimport);
1275  if ($model == 'csv') {
1276  $obj->separator = $separator;
1277  $obj->enclosure = $enclosure;
1278  }
1279 
1280  // Load source fields in input file
1281  $fieldssource = array();
1282  $result = $obj->import_open_file($conf->import->dir_temp.'/'.$filetoimport, $langs);
1283 
1284  if ($result >= 0)
1285  {
1286  // Read first line
1287  $arrayrecord = $obj->import_read_record();
1288  // Put into array fieldssource starting with 1.
1289  $i = 1;
1290  foreach ($arrayrecord as $key => $val)
1291  {
1292  $fieldssource[$i]['example1'] = dol_trunc($val['val'], 24);
1293  $i++;
1294  }
1295  $obj->import_close_file();
1296  }
1297 
1298  $nboflines = $obj->import_get_nb_of_lines($conf->import->dir_temp.'/'.$filetoimport);
1299 
1300  $param = '&leftmenu=import&format='.urlencode($format).'&datatoimport='.urlencode($datatoimport).'&filetoimport='.urlencode($filetoimport).'&nboflines='.urlencode($nboflines).'&separator='.urlencode($separator).'&enclosure='.urlencode($enclosure);
1301  $param2 = $param; // $param2 = $param without excludefirstline and endatlinenb
1302  if ($excludefirstline) $param .= '&excludefirstline='.urlencode($excludefirstline);
1303  if ($endatlinenb) $param .= '&endatlinenb='.urlencode($endatlinenb);
1304  if (!empty($updatekeys)) $param .= '&updatekeys[]='.implode('&updatekeys[]=', $updatekeys);
1305 
1306  llxHeader('', $langs->trans("NewImport"), 'EN:Module_Imports_En|FR:Module_Imports|ES:M&oacute;dulo_Importaciones');
1307 
1308  $head = import_prepare_head($param, 5);
1309 
1310 
1311  print '<form action="'.$_SERVER["PHP_SELF"].'?'.$param2.'" method="POST">';
1312  print '<input type="hidden" name="token" value="'.newToken().'">';
1313  print '<input type="hidden" name="step" value="5">'; // step 5
1314  print '<input type="hidden" name="action" value="launchsimu">'; // step 5
1315 
1316  print dol_get_fiche_head($head, 'step5', '', -2);
1317 
1318  print '<div class="underbanner clearboth"></div>';
1319  print '<div class="fichecenter">';
1320 
1321  print '<table width="100%" class="border tableforfield">';
1322 
1323  // Module
1324  print '<tr><td class="titlefield">'.$langs->trans("Module").'</td>';
1325  print '<td>';
1326  $titleofmodule = $objimport->array_import_module[0]['module']->getName();
1327  // Special cas for import common to module/services
1328  if (in_array($objimport->array_import_code[0], array('produit_supplierprices', 'produit_multiprice', 'produit_languages'))) $titleofmodule = $langs->trans("ProductOrService");
1329  print $titleofmodule;
1330  print '</td></tr>';
1331 
1332  // Lot de donnees a importer
1333  print '<tr><td>'.$langs->trans("DatasetToImport").'</td>';
1334  print '<td>';
1335  $entity = preg_replace('/:.*$/', '', $objimport->array_import_icon[0]);
1336  $entityicon = strtolower(!empty($entitytoicon[$entity]) ? $entitytoicon[$entity] : $entity);
1337  print img_object($objimport->array_import_module[0]['module']->getName(), $entityicon).' ';
1338  print $objimport->array_import_label[0];
1339  print '</td></tr>';
1340 
1341  print '</table>';
1342  print '</div>';
1343 
1344  print load_fiche_titre($langs->trans("InformationOnSourceFile"), '', '');
1345 
1346  print '<div class="underbanner clearboth"></div>';
1347  print '<div class="fichecenter">';
1348  print '<table width="100%" class="border tableforfield">';
1349 
1350  // Source file format
1351  print '<tr><td class="titlefield">'.$langs->trans("SourceFileFormat").'</td>';
1352  print '<td>';
1353  $text = $objmodelimport->getDriverDescForKey($format);
1354  print $form->textwithpicto($objmodelimport->getDriverLabelForKey($format), $text);
1355  print '</td></tr>';
1356 
1357  // Separator and enclosure
1358  if ($model == 'csv') {
1359  print '<tr><td>'.$langs->trans("CsvOptions").'</td>';
1360  print '<td>';
1361  print $langs->trans("Separator").' : '.dol_escape_htmltag($separator);
1362  print '&nbsp;&nbsp;&nbsp;&nbsp;'.$langs->trans("Enclosure").' : '.dol_escape_htmltag($enclosure);
1363  print '</td></tr>';
1364  }
1365 
1366  // File to import
1367  print '<tr><td>'.$langs->trans("FileToImport").'</td>';
1368  print '<td>';
1369  $modulepart = 'import';
1370  $relativepath = GETPOST('filetoimport');
1371  print '<a data-ajax="false" href="'.DOL_URL_ROOT.'/document.php?modulepart='.$modulepart.'&file='.urlencode($relativepath).'&step=4'.$param.'" target="_blank">';
1372  print $filetoimport;
1373  print '</a>';
1374  print '</td></tr>';
1375 
1376  // Total lines in source file
1377  print '<tr><td>';
1378  print $langs->trans("NbOfSourceLines");
1379  print '</td><td>';
1380  print $nboflines;
1381  print '</td></tr>';
1382 
1383  // Range of lines to import
1384  print '<tr><td>';
1385  print $langs->trans("ImportFromToLine");
1386  print '</td><td>';
1387  if ($action == 'launchsimu')
1388  {
1389  print '<input type="number" class="maxwidth50" name="excludefirstlinebis" disabled="disabled" value="'.$excludefirstline.'">';
1390  print '<input type="hidden" name="excludefirstline" value="'.$excludefirstline.'">';
1391  } else {
1392  print '<input type="number" class="maxwidth50" name="excludefirstline" value="'.$excludefirstline.'">';
1393  print $form->textwithpicto("", $langs->trans("SetThisValueTo2ToExcludeFirstLine"));
1394  }
1395  print ' - ';
1396  if ($action == 'launchsimu')
1397  {
1398  print '<input type="text" class="maxwidth50" name="endatlinenbbis" disabled="disabled" value="'.$endatlinenb.'">';
1399  print '<input type="hidden" name="endatlinenb" value="'.$endatlinenb.'">';
1400  } else {
1401  print '<input type="text" class="maxwidth50" name="endatlinenb" value="'.$endatlinenb.'">';
1402  print $form->textwithpicto("", $langs->trans("KeepEmptyToGoToEndOfFile"));
1403  }
1404  if ($action == 'launchsimu') print ' &nbsp; <a href="'.$_SERVER["PHP_SELF"].'?step=5'.$param.'">'.$langs->trans("Modify").'</a>';
1405  print '</td></tr>';
1406 
1407  // Keys for data UPDATE (not INSERT of new data)
1408  print '<tr><td>';
1409  print $langs->trans("KeysToUseForUpdates");
1410  print '</td><td>';
1411  if ($action == 'launchsimu') {
1412  if (count($updatekeys))
1413  {
1414  print $form->multiselectarray('updatekeysbis', $objimport->array_import_updatekeys[0], $updatekeys, 0, 0, '', 1, '80%', 'disabled');
1415  } else {
1416  print '<span class="opacitymedium">'.$langs->trans("NoUpdateAttempt").'</span> &nbsp; -';
1417  }
1418  foreach ($updatekeys as $val) {
1419  print '<input type="hidden" name="updatekeys[]" value="'.$val.'">';
1420  }
1421  print ' &nbsp; <a href="'.$_SERVER["PHP_SELF"].'?step=5'.$param.'">'.$langs->trans("Modify").'</a>';
1422  } else {
1423  if (is_array($objimport->array_import_updatekeys[0]) && count($objimport->array_import_updatekeys[0]))
1424  { //TODO dropdown UL is created inside nested SPANS
1425  print $form->multiselectarray('updatekeys', $objimport->array_import_updatekeys[0], $updatekeys, 0, 0, '', 1, '80%');
1426  print $form->textwithpicto("", $langs->trans("SelectPrimaryColumnsForUpdateAttempt"));
1427  } else {
1428  print '<span class="opacitymedium">'.$langs->trans("UpdateNotYetSupportedForThisImport").'</span>';
1429  }
1430  }
1431  /*echo '<pre>';
1432  print_r($objimport->array_import_updatekeys);
1433  echo '</pre>';*/
1434  print '</td></tr>';
1435 
1436  print '</table>';
1437  print '</div>';
1438 
1439 
1440  print load_fiche_titre($langs->trans("InformationOnTargetTables"), '', '');
1441 
1442  print '<div class="underbanner clearboth"></div>';
1443  print '<div class="fichecenter">';
1444 
1445  print '<table width="100%" class="border tableforfield">';
1446 
1447  // Tables imported
1448  print '<tr><td class="titlefield">';
1449  print $langs->trans("TablesTarget");
1450  print '</td><td>';
1451  $listtables = array();
1452  $sort_array_match_file_to_database = $array_match_file_to_database;
1453  foreach ($array_match_file_to_database as $code=>$label)
1454  {
1455  //var_dump($fieldssource);
1456  if ($code > count($fieldssource)) continue;
1457  //print $code.'-'.$label;
1458  $alias = preg_replace('/(\..*)$/i', '', $label);
1459  $listtables[$alias] = $objimport->array_import_tables[0][$alias];
1460  }
1461  if (count($listtables))
1462  {
1463  $newval = '';
1464  //ksort($listtables);
1465  foreach ($listtables as $val)
1466  {
1467  if ($newval) print ', ';
1468  $newval = $val;
1469  // Link to Dolibarr wiki pages
1470  /*$helppagename='EN:Table_'.$newval;
1471  if ($helppagename && empty($conf->global->MAIN_HELP_DISABLELINK))
1472  {
1473  // Get helpbaseurl, helppage and mode from helppagename and langs
1474  $arrayres=getHelpParamFor($helppagename,$langs);
1475  $helpbaseurl=$arrayres['helpbaseurl'];
1476  $helppage=$arrayres['helppage'];
1477  $mode=$arrayres['mode'];
1478  $newval.=' <a href="'.sprintf($helpbaseurl,$helppage).'">'.img_picto($langs->trans($mode == 'wiki' ? 'GoToWikiHelpPage': 'GoToHelpPage'),DOL_URL_ROOT.'/theme/common/helpdoc.png','',1).'</a>';
1479  }*/
1480  print $newval;
1481  }
1482  } else print $langs->trans("Error");
1483  print '</td></tr>';
1484 
1485  // Fields imported
1486  print '<tr><td>';
1487  print $langs->trans("FieldsTarget").'</td><td>';
1488  $listfields = array();
1489  $i = 0;
1490  //print 'fieldsource='.$fieldssource;
1491  $sort_array_match_file_to_database = $array_match_file_to_database;
1492  ksort($sort_array_match_file_to_database);
1493  //var_dump($sort_array_match_file_to_database);
1494  foreach ($sort_array_match_file_to_database as $code=>$label)
1495  {
1496  $i++;
1497  //var_dump($fieldssource);
1498  if ($code > count($fieldssource)) continue;
1499  //print $code.'-'.$label;
1500  $alias = preg_replace('/(\..*)$/i', '', $label);
1501  $listfields[$i] = $langs->trans("Field").' '.$code.'->'.$label;
1502  }
1503  print count($listfields) ? (join(', ', $listfields)) : $langs->trans("Error");
1504  print '</td></tr>';
1505 
1506  print '</table>';
1507  print '</div>';
1508 
1509  print dol_get_fiche_end();
1510 
1511 
1512  if ($action != 'launchsimu')
1513  {
1514  // Show import id
1515  print '<br><span class="opacitymedium">';
1516  print $langs->trans("NowClickToTestTheImport", $langs->transnoentitiesnoconv("RunSimulateImportFile")).'</span><br>';
1517  print '<br>';
1518 
1519  // Actions
1520  print '<div class="center">';
1521  if ($user->rights->import->run)
1522  {
1523  print '<input type="submit" class="butAction" value="'.$langs->trans("RunSimulateImportFile").'">';
1524  } else {
1525  print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("RunSimulateImportFile").'</a>';
1526  }
1527  print '</div>';
1528  } else {
1529  // Launch import
1530  $arrayoferrors = array();
1531  $arrayofwarnings = array();
1532  $maxnboferrors = empty($conf->global->IMPORT_MAX_NB_OF_ERRORS) ? 50 : $conf->global->IMPORT_MAX_NB_OF_ERRORS;
1533  $maxnbofwarnings = empty($conf->global->IMPORT_MAX_NB_OF_WARNINGS) ? 50 : $conf->global->IMPORT_MAX_NB_OF_WARNINGS;
1534  $nboferrors = 0;
1535  $nbofwarnings = 0;
1536 
1537  $importid = dol_print_date(dol_now(), '%Y%m%d%H%M%S');
1538 
1539  //var_dump($array_match_file_to_database);
1540 
1541  $db->begin();
1542 
1543  // Open input file
1544  $nbok = 0;
1545  $pathfile = $conf->import->dir_temp.'/'.$filetoimport;
1546  $result = $obj->import_open_file($pathfile, $langs);
1547  if ($result > 0)
1548  {
1549  global $tablewithentity_cache;
1550  $tablewithentity_cache = array();
1551  $sourcelinenb = 0; $endoffile = 0;
1552 
1553  // Loop on each input file record
1554  while (($sourcelinenb < $nboflines) && !$endoffile)
1555  {
1556  $sourcelinenb++;
1557  // Read line and store it into $arrayrecord
1558  //dol_syslog("line ".$sourcelinenb.' - '.$nboflines.' - '.$excludefirstline.' - '.$endatlinenb);
1559  $arrayrecord = $obj->import_read_record();
1560  if ($arrayrecord === false)
1561  {
1562  $arrayofwarnings[$sourcelinenb][0] = array('lib'=>'File has '.$nboflines.' lines. However we reach end of file after record '.$sourcelinenb.'. This may occurs when some records are split onto several lines. Ensure the complete string is delimited correctly when there is a separator character in the text string.', 'type'=>'EOF_RECORD_ON_SEVERAL_LINES');
1563  $endoffile++;
1564  continue;
1565  }
1566  if ($excludefirstline && ($sourcelinenb < $excludefirstline)) continue;
1567  if ($endatlinenb && ($sourcelinenb > $endatlinenb)) break;
1568 
1569  // Run import
1570  $result = $obj->import_insert($arrayrecord, $array_match_file_to_database, $objimport, count($fieldssource), $importid, $updatekeys);
1571 
1572  if (count($obj->errors)) $arrayoferrors[$sourcelinenb] = $obj->errors;
1573  if (count($obj->warnings)) $arrayofwarnings[$sourcelinenb] = $obj->warnings;
1574  if (!count($obj->errors) && !count($obj->warnings)) $nbok++;
1575  }
1576  // Close file
1577  $obj->import_close_file();
1578  } else {
1579  print $langs->trans("ErrorFailedToOpenFile", $pathfile);
1580  }
1581 
1582  $error = 0;
1583 
1584  // Run the sql after import if defined
1585  //var_dump($objimport->array_import_run_sql_after[0]);
1586  if (!empty($objimport->array_import_run_sql_after[0]) && is_array($objimport->array_import_run_sql_after[0]))
1587  {
1588  $i = 0;
1589  foreach ($objimport->array_import_run_sql_after[0] as $sqlafterimport)
1590  {
1591  $i++;
1592  $resqlafterimport = $db->query($sqlafterimport);
1593  if (!$resqlafterimport)
1594  {
1595  $arrayoferrors['none'][] = array('lib'=>$langs->trans("Error running final request: ".$sqlafterimport));
1596  $error++;
1597  }
1598  }
1599  }
1600 
1601  $db->rollback(); // We force rollback because this was just a simulation.
1602 
1603  // Show OK
1604  if (!count($arrayoferrors) && !count($arrayofwarnings)) {
1605  print '<div class="center">'.img_picto($langs->trans("OK"), 'tick').' <b>'.$langs->trans("NoError").'</b></div><br><br>';
1606  print '<div class="ok">';
1607  print $langs->trans("NbInsert", empty($obj->nbinsert) ? 0 : $obj->nbinsert).'<br>';
1608  print $langs->trans("NbUpdate", empty($obj->nbupdate) ? 0 : $obj->nbupdate).'<br><br>';
1609  print '</div>';
1610  } else print $langs->trans("NbOfLinesOK", $nbok).'<br><br>';
1611 
1612  // Show Errors
1613  //var_dump($arrayoferrors);
1614  if (count($arrayoferrors))
1615  {
1616  print img_error().' <b>'.$langs->trans("ErrorsOnXLines", count($arrayoferrors)).'</b><br>';
1617  print '<table width="100%" class="border"><tr><td>';
1618  foreach ($arrayoferrors as $key => $val)
1619  {
1620  $nboferrors++;
1621  if ($nboferrors > $maxnboferrors)
1622  {
1623  print $langs->trans("TooMuchErrors", (count($arrayoferrors) - $nboferrors))."<br>";
1624  break;
1625  }
1626  print '* '.$langs->trans("Line").' '.$key.'<br>';
1627  foreach ($val as $i => $err)
1628  {
1629  print ' &nbsp; &nbsp; > '.$err['lib'].'<br>';
1630  }
1631  }
1632  print '</td></tr></table>';
1633  print '<br>';
1634  }
1635 
1636  // Show Warnings
1637  //var_dump($arrayoferrors);
1638  if (count($arrayofwarnings))
1639  {
1640  print img_warning().' <b>'.$langs->trans("WarningsOnXLines", count($arrayofwarnings)).'</b><br>';
1641  print '<table width="100%" class="border"><tr><td>';
1642  foreach ($arrayofwarnings as $key => $val)
1643  {
1644  $nbofwarnings++;
1645  if ($nbofwarnings > $maxnbofwarnings)
1646  {
1647  print $langs->trans("TooMuchWarnings", (count($arrayofwarnings) - $nbofwarnings))."<br>";
1648  break;
1649  }
1650  print ' * '.$langs->trans("Line").' '.$key.'<br>';
1651  foreach ($val as $i => $err)
1652  {
1653  print ' &nbsp; &nbsp; > '.$err['lib'].'<br>';
1654  }
1655  }
1656  print '</td></tr></table>';
1657  print '<br>';
1658  }
1659 
1660  // Show import id
1661  $importid = dol_print_date(dol_now(), '%Y%m%d%H%M%S');
1662 
1663  print '<div class="center">';
1664  print '<span class="opacitymedium">'.$langs->trans("NowClickToRunTheImport", $langs->transnoentitiesnoconv("RunImportFile")).'</span><br>';
1665  if (empty($nboferrors)) print $langs->trans("DataLoadedWithId", $importid).'<br>';
1666  print '</div>';
1667 
1668  print '<br>';
1669 
1670  // Actions
1671  print '<div class="center">';
1672  if ($user->rights->import->run)
1673  {
1674  if (empty($nboferrors))
1675  {
1676  print '<a class="butAction" href="'.DOL_URL_ROOT.'/imports/import.php?leftmenu=import&step=6&importid='.$importid.$param.'">'.$langs->trans("RunImportFile").'</a>';
1677  } else {
1678  //print '<input type="submit" class="butAction" value="'.dol_escape_htmltag($langs->trans("RunSimulateImportFile")).'">';
1679 
1680  print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("CorrectErrorBeforeRunningImport")).'">'.$langs->trans("RunImportFile").'</a>';
1681  }
1682  } else {
1683  print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("RunSimulateImportFile").'</a>';
1684 
1685  print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("RunImportFile").'</a>';
1686  }
1687  print '</div>';
1688  }
1689 
1690  print '</form>';
1691 }
1692 
1693 
1694 // STEP 6: Real import
1695 if ($step == 6 && $datatoimport)
1696 {
1697  $max_execution_time_for_importexport = (empty($conf->global->IMPORT_MAX_EXECUTION_TIME) ? 300 : $conf->global->IMPORT_MAX_EXECUTION_TIME); // 5mn if not defined
1698  $max_time = @ini_get("max_execution_time");
1699  if ($max_time && $max_time < $max_execution_time_for_importexport)
1700  {
1701  dol_syslog("max_execution_time=".$max_time." is lower than max_execution_time_for_importexport=".$max_execution_time_for_importexport.". We try to increase it dynamically.");
1702  @ini_set("max_execution_time", $max_execution_time_for_importexport); // This work only if safe mode is off. also web servers has timeout of 300
1703  }
1704 
1705  $model = $format;
1706  $liste = $objmodelimport->liste_modeles($db);
1707  $importid = GETPOST("importid", 'alphanohtml');
1708 
1709 
1710  // Create classe to use for import
1711  $dir = DOL_DOCUMENT_ROOT."/core/modules/import/";
1712  $file = "import_".$model.".modules.php";
1713  $classname = "Import".ucfirst($model);
1714  require_once $dir.$file;
1715  $obj = new $classname($db, $datatoimport);
1716  if ($model == 'csv') {
1717  $obj->separator = $separator;
1718  $obj->enclosure = $enclosure;
1719  }
1720 
1721  // Load source fields in input file
1722  $fieldssource = array();
1723  $result = $obj->import_open_file($conf->import->dir_temp.'/'.$filetoimport, $langs);
1724  if ($result >= 0)
1725  {
1726  // Read first line
1727  $arrayrecord = $obj->import_read_record();
1728  // Put into array fieldssource starting with 1.
1729  $i = 1;
1730  foreach ($arrayrecord as $key => $val)
1731  {
1732  $fieldssource[$i]['example1'] = dol_trunc($val['val'], 24);
1733  $i++;
1734  }
1735  $obj->import_close_file();
1736  }
1737 
1738  $nboflines = (!empty($_GET["nboflines"]) ? $_GET["nboflines"] : dol_count_nb_of_line($conf->import->dir_temp.'/'.$filetoimport));
1739 
1740  $param = '&format='.$format.'&datatoimport='.urlencode($datatoimport).'&filetoimport='.urlencode($filetoimport).'&nboflines='.urlencode($nboflines);
1741  if ($excludefirstline) $param .= '&excludefirstline='.urlencode($excludefirstline);
1742  if ($endatlinenb) $param .= '&endatlinenb='.urlencode($endatlinenb);
1743  if ($separator) $param .= '&separator='.urlencode($separator);
1744  if ($enclosure) $param .= '&enclosure='.urlencode($enclosure);
1745 
1746  llxHeader('', $langs->trans("NewImport"), 'EN:Module_Imports_En|FR:Module_Imports|ES:M&oacute;dulo_Importaciones');
1747 
1748  $head = import_prepare_head($param, 6);
1749 
1750  print dol_get_fiche_head($head, 'step6', '', -1);
1751 
1752  print '<div class="underbanner clearboth"></div>';
1753  print '<div class="fichecenter">';
1754 
1755  print '<table width="100%" class="border">';
1756 
1757  // Module
1758  print '<tr><td class="titlefield">'.$langs->trans("Module").'</td>';
1759  print '<td>';
1760  $titleofmodule = $objimport->array_import_module[0]['module']->getName();
1761  // Special cas for import common to module/services
1762  if (in_array($objimport->array_import_code[0], array('produit_supplierprices', 'produit_multiprice', 'produit_languages'))) $titleofmodule = $langs->trans("ProductOrService");
1763  print $titleofmodule;
1764  print '</td></tr>';
1765 
1766  // Lot de donnees a importer
1767  print '<tr><td>'.$langs->trans("DatasetToImport").'</td>';
1768  print '<td>';
1769  $entity = preg_replace('/:.*$/', '', $objimport->array_import_icon[0]);
1770  $entityicon = strtolower(!empty($entitytoicon[$entity]) ? $entitytoicon[$entity] : $entity);
1771  print img_object($objimport->array_import_module[0]['module']->getName(), $entityicon).' ';
1772  print $objimport->array_import_label[0];
1773  print '</td></tr>';
1774 
1775  print '</table>';
1776  print '</div>';
1777 
1778  print load_fiche_titre($langs->trans("InformationOnSourceFile"), '', '');
1779 
1780  print '<div class="underbanner clearboth"></div>';
1781  print '<div class="fichecenter">';
1782  print '<table width="100%" class="border">';
1783 
1784  // Source file format
1785  print '<tr><td class="titlefield">'.$langs->trans("SourceFileFormat").'</td>';
1786  print '<td>';
1787  $text = $objmodelimport->getDriverDescForKey($format);
1788  print $form->textwithpicto($objmodelimport->getDriverLabelForKey($format), $text);
1789  print '</td></tr>';
1790 
1791  // Separator and enclosure
1792  if ($model == 'csv') {
1793  print '<tr><td>'.$langs->trans("CsvOptions").'</td>';
1794  print '<td>';
1795  print $langs->trans("Separator").' : ';
1796  print htmlentities($separator);
1797  print '&nbsp;&nbsp;&nbsp;&nbsp;'.$langs->trans("Enclosure").' : ';
1798  print htmlentities($enclosure);
1799  print '</td></tr>';
1800  }
1801 
1802  // File to import
1803  print '<tr><td>'.$langs->trans("FileToImport").'</td>';
1804  print '<td>';
1805  $modulepart = 'import';
1806  $relativepath = GETPOST('filetoimport');
1807  print '<a data-ajax="false" href="'.DOL_URL_ROOT.'/document.php?modulepart='.$modulepart.'&file='.urlencode($relativepath).'&step=4'.$param.'" target="_blank">';
1808  print $filetoimport;
1809  print '</a>';
1810  print '</td></tr>';
1811 
1812  // Nb of fields
1813  print '<tr><td>';
1814  print $langs->trans("NbOfSourceLines");
1815  print '</td><td>';
1816  print $nboflines;
1817  print '</td></tr>';
1818 
1819  // Do not import first lines
1820  print '<tr><td>';
1821  print $langs->trans("ImportFromLine");
1822  print '</td><td>';
1823  print '<input type="text" size="4" name="excludefirstline" disabled="disabled" value="'.$excludefirstline.'">';
1824  print '</td></tr>';
1825 
1826  // Do not import end lines
1827  print '<tr><td>';
1828  print $langs->trans("EndAtLineNb");
1829  print '</td><td>';
1830  print '<input type="text" size="4" name="endatlinenb" disabled="disabled" value="'.$endatlinenb.'">';
1831  print '</td></tr>';
1832 
1833  print '</table>';
1834  print '</div>';
1835 
1836  print '<br>';
1837 
1838  print '<b>'.$langs->trans("InformationOnTargetTables").'</b>';
1839  print '<div class="underbanner clearboth"></div>';
1840  print '<div class="fichecenter">';
1841  print '<table width="100%" class="border">';
1842  //print '<tr><td colspan="2"><b>'.$langs->trans("InformationOnTargetTables").'</b></td></tr>';
1843 
1844  // Tables imported
1845  print '<tr><td width="25%">';
1846  print $langs->trans("TablesTarget");
1847  print '</td><td>';
1848  $listtables = array();
1849  foreach ($array_match_file_to_database as $code=>$label)
1850  {
1851  //var_dump($fieldssource);
1852  if ($code > count($fieldssource)) continue;
1853  //print $code.'-'.$label;
1854  $alias = preg_replace('/(\..*)$/i', '', $label);
1855  $listtables[$alias] = $objimport->array_import_tables[0][$alias];
1856  }
1857  if (count($listtables))
1858  {
1859  $newval = '';
1860  foreach ($listtables as $val)
1861  {
1862  if ($newval) print ', ';
1863  $newval = $val;
1864  // Link to Dolibarr wiki pages
1865  /*$helppagename='EN:Table_'.$newval;
1866  if ($helppagename && empty($conf->global->MAIN_HELP_DISABLELINK))
1867  {
1868  // Get helpbaseurl, helppage and mode from helppagename and langs
1869  $arrayres=getHelpParamFor($helppagename,$langs);
1870  $helpbaseurl=$arrayres['helpbaseurl'];
1871  $helppage=$arrayres['helppage'];
1872  $mode=$arrayres['mode'];
1873  $newval.=' <a href="'.sprintf($helpbaseurl,$helppage).'">'.img_picto($langs->trans($mode == 'wiki' ? 'GoToWikiHelpPage': 'GoToHelpPage'),DOL_URL_ROOT.'/theme/common/helpdoc.png','',1).'</a>';
1874  }*/
1875  print $newval;
1876  }
1877  } else print $langs->trans("Error");
1878  print '</td></tr>';
1879 
1880  // Fields imported
1881  print '<tr><td>';
1882  print $langs->trans("FieldsTarget").'</td><td>';
1883  $listfields = array();
1884  $i = 0;
1885  $sort_array_match_file_to_database = $array_match_file_to_database;
1886  ksort($sort_array_match_file_to_database);
1887  //var_dump($sort_array_match_file_to_database);
1888  foreach ($sort_array_match_file_to_database as $code=>$label)
1889  {
1890  $i++;
1891  //var_dump($fieldssource);
1892  if ($code > count($fieldssource)) continue;
1893  //print $code.'-'.$label;
1894  $alias = preg_replace('/(\..*)$/i', '', $label);
1895  $listfields[$i] = $langs->trans("Field").' '.$code.'->'.$label;
1896  }
1897  print count($listfields) ? (join(', ', $listfields)) : $langs->trans("Error");
1898  print '</td></tr>';
1899 
1900  print '</table>';
1901  print '</div>';
1902 
1903  // Launch import
1904  $arrayoferrors = array();
1905  $arrayofwarnings = array();
1906  $maxnboferrors = empty($conf->global->IMPORT_MAX_NB_OF_ERRORS) ? 50 : $conf->global->IMPORT_MAX_NB_OF_ERRORS;
1907  $maxnbofwarnings = empty($conf->global->IMPORT_MAX_NB_OF_WARNINGS) ? 50 : $conf->global->IMPORT_MAX_NB_OF_WARNINGS;
1908  $nboferrors = 0;
1909  $nbofwarnings = 0;
1910 
1911  $importid = dol_print_date(dol_now(), '%Y%m%d%H%M%S');
1912 
1913  //var_dump($array_match_file_to_database);
1914 
1915  $db->begin();
1916 
1917  // Open input file
1918  $nbok = 0;
1919  $pathfile = $conf->import->dir_temp.'/'.$filetoimport;
1920  $result = $obj->import_open_file($pathfile, $langs);
1921  if ($result > 0)
1922  {
1923  global $tablewithentity_cache;
1924  $tablewithentity_cache = array();
1925  $sourcelinenb = 0; $endoffile = 0;
1926 
1927  while ($sourcelinenb < $nboflines && !$endoffile)
1928  {
1929  $sourcelinenb++;
1930  $arrayrecord = $obj->import_read_record();
1931  if ($arrayrecord === false)
1932  {
1933  $arrayofwarnings[$sourcelinenb][0] = array('lib'=>'File has '.$nboflines.' lines. However we reach end of file after record '.$sourcelinenb.'. This may occurs when some records are split onto several lines.', 'type'=>'EOF_RECORD_ON_SEVERAL_LINES');
1934  $endoffile++;
1935  continue;
1936  }
1937  if ($excludefirstline && ($sourcelinenb < $excludefirstline)) continue;
1938  if ($endatlinenb && ($sourcelinenb > $endatlinenb)) break;
1939 
1940  // Run import
1941  $result = $obj->import_insert($arrayrecord, $array_match_file_to_database, $objimport, count($fieldssource), $importid, $updatekeys);
1942 
1943  if (count($obj->errors)) $arrayoferrors[$sourcelinenb] = $obj->errors;
1944  if (count($obj->warnings)) $arrayofwarnings[$sourcelinenb] = $obj->warnings;
1945  if (!count($obj->errors) && !count($obj->warnings)) $nbok++;
1946  }
1947  // Close file
1948  $obj->import_close_file();
1949  } else {
1950  print $langs->trans("ErrorFailedToOpenFile", $pathfile);
1951  }
1952 
1953  if (count($arrayoferrors) > 0) $db->rollback(); // We force rollback because this was errors.
1954  else {
1955  $error = 0;
1956 
1957  // Run the sql after import if defined
1958  //var_dump($objimport->array_import_run_sql_after[0]);
1959  if (!empty($objimport->array_import_run_sql_after[0]) && is_array($objimport->array_import_run_sql_after[0]))
1960  {
1961  $i = 0;
1962  foreach ($objimport->array_import_run_sql_after[0] as $sqlafterimport)
1963  {
1964  $i++;
1965  $resqlafterimport = $db->query($sqlafterimport);
1966  if (!$resqlafterimport)
1967  {
1968  $arrayoferrors['none'][] = array('lib'=>$langs->trans("Error running final request: ".$sqlafterimport));
1969  $error++;
1970  }
1971  }
1972  }
1973 
1974  if (!$error) $db->commit(); // We can commit if no errors.
1975  else $db->rollback();
1976  }
1977 
1978  print dol_get_fiche_end();
1979 
1980 
1981  // Show result
1982  print '<br>';
1983  print '<div class="ok">';
1984  print $langs->trans("NbOfLinesImported", $nbok).'</b><br>';
1985  print $langs->trans("NbInsert", empty($obj->nbinsert) ? 0 : $obj->nbinsert).'<br>';
1986  print $langs->trans("NbUpdate", empty($obj->nbupdate) ? 0 : $obj->nbupdate).'<br><br>';
1987  print '</div>';
1988  print '<div class="center">';
1989  print $langs->trans("FileWasImported", $importid).'<br>';
1990  print '<span class="opacitymedium">'.$langs->trans("YouCanUseImportIdToFindRecord", $importid).'</span><br>';
1991  print '</div>';
1992 }
1993 
1994 
1995 
1996 print '<br>';
1997 
1998 // End of page
1999 llxFooter();
2000 $db->close();
2001 
2002 
2013 function show_elem($fieldssource, $pos, $key, $var, $nostyle = '')
2014 {
2015  global $langs, $bc;
2016 
2017  $height = '24px';
2018 
2019  if ($key == 'none') {
2020  //stop multiple duplicate ids with no number
2021  print "\n\n<!-- Box_no-key start-->\n";
2022  print '<div class="box boximport" style="padding:0;">'."\n";
2023  print '<table summary="boxtable_no-key" width="100%" class="nobordernopadding">'."\n";
2024  } else {
2025  print "\n\n<!-- Box ".$pos." start -->\n";
2026  print '<div class="box boximport" style="padding: 0;" id="boxto_'.$pos.'">'."\n";
2027 
2028  print '<table summary="boxtable'.$pos.'" width="100%" class="nobordernopadding">'."\n";
2029  }
2030 
2031  if ($pos && $pos > count($fieldssource)) // No fields
2032  {
2033  print '<tr'.($nostyle ? '' : ' '.$bc[$var]).' style="height:'.$height.'">';
2034  print '<td class="nocellnopadding" width="16" style="font-weight: normal">';
2035  print img_picto(($pos > 0 ? $langs->trans("MoveField", $pos) : ''), 'grip_title', 'class="boxhandle" style="cursor:move;"');
2036  print '</td>';
2037  print '<td style="font-weight: normal">';
2038  print $langs->trans("NoFields");
2039  print '</td>';
2040  print '</tr>';
2041  } elseif ($key == 'none') // Empty line
2042  {
2043  print '<tr'.($nostyle ? '' : ' '.$bc[$var]).' style="height:'.$height.'">';
2044  print '<td class="nocellnopadding" width="16" style="font-weight: normal">';
2045  print '&nbsp;';
2046  print '</td>';
2047  print '<td style="font-weight: normal">';
2048  print '&nbsp;';
2049  print '</td>';
2050  print '</tr>';
2051  } else // Print field of source file
2052  {
2053  print '<tr'.($nostyle ? '' : ' '.$bc[$var]).' style="height:'.$height.'">';
2054  print '<td class="nocellnopadding" width="16" style="font-weight: normal">';
2055  // The image must have the class 'boxhandle' beause it's value used in DOM draggable objects to define the area used to catch the full object
2056  print img_picto($langs->trans("MoveField", $pos), 'grip_title', 'class="boxhandle" style="cursor:move;"');
2057  print '</td>';
2058  print '<td style="font-weight: normal">';
2059  print $langs->trans("Field").' '.$pos;
2060  $example = $fieldssource[$pos]['example1'];
2061  if ($example)
2062  {
2063  if (!utf8_check($example)) $example = utf8_encode($example);
2064  print ' (<i>'.$example.'</i>)';
2065  }
2066  print '</td>';
2067  print '</tr>';
2068  }
2069 
2070  print "</table>\n";
2071 
2072  print "</div>\n";
2073  print "<!-- Box end -->\n\n";
2074 }
2075 
2076 
2084 function getnewkey(&$fieldssource, &$listofkey)
2085 {
2086  $i = count($fieldssource) + 1;
2087  // Max number of key
2088  $maxkey = 0;
2089  foreach ($listofkey as $key=>$val)
2090  {
2091  $maxkey = max($maxkey, $key);
2092  }
2093  // Found next empty key
2094  while ($i <= $maxkey)
2095  {
2096  if (empty($listofkey[$i])) break;
2097  else $i++;
2098  }
2099 
2100  $listofkey[$i] = 1;
2101  return $i;
2102 }
GETPOST($paramname, $check= 'alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
yn($yesno, $case=1, $color=0)
Return yes or no in current language.
getnewkey(&$fieldssource, &$listofkey)
Return not used field number.
Definition: import.php:2084
Class to manage imports.
dol_now($mode= 'auto')
Return date for now.
dol_filesize($pathoffile)
Return size of a file.
Definition: files.lib.php:555
show_elem($fieldssource, $pos, $key, $var, $nostyle= '')
Function to put the movable box of a source field.
Definition: import.php:2013
img_warning($titlealt= 'default', $moreatt= '', $morecss= 'pictowarning')
Show warning logo.
llxHeader()
Empty header.
Definition: wrapper.php:45
setEventMessages($mesg, $mesgs, $style= 'mesgs', $messagekey= '')
Set event messages in dol_events session object.
img_error($titlealt= 'default')
Show error logo.
Class to manage generation of HTML components Only common components must be here.
load_fiche_titre($titre, $morehtmlright= '', $picto= 'generic', $pictoisfullpath=0, $id= '', $morecssontable= '', $morehtmlcenter= '')
Load a title with picto.
img_picto($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt= '', $morecss= '', $marginleftonlyshort=2)
Show picto whatever it&#39;s its name (generic function)
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename= '', $restricttologhandler= '', $logcontext=null)
Write log message into outputs.
Classe permettant la generation de composants html autre Only common components are here...
dol_delete_file($file, $disableglob=0, $nophperrors=0, $nohook=0, $object=null, $allowdotdot=false, $indexdatabase=1)
Remove a file or several files with a mask.
Definition: files.lib.php:1144
img_object($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0)
Show a picto called object_picto (generic function)
restrictedArea($user, $features, $objectid=0, $tableandshare= '', $feature2= '', $dbt_keyfield= 'fk_soc', $dbt_select= 'rowid', $isdraft=0)
Check permissions of a user to show a page and an object.
dol_dir_list($path, $types="all", $recursive=0, $filter="", $excludefilter=null, $sortcriteria="name", $sortorder=SORT_ASC, $mode=0, $nohook=0, $relativename="", $donotfollowsymlinks=0)
Scan a directory and return a list of files/directories.
Definition: files.lib.php:60
utf8_check($str)
Check if a string is in UTF8.
dol_count_nb_of_line($file)
Count number of lines in a file.
Definition: files.lib.php:524
Class to offer components to list and upload files.
dol_move_uploaded_file($src_file, $dest_file, $allowoverwrite, $disablevirusscan=0, $uploaderrorcode=0, $nohook=0, $varfiles= 'addedfile', $upload_dir= '')
Make control on an uploaded file from an GUI page and move it to final destination.
Definition: files.lib.php:999
print $_SERVER["PHP_SELF"]
Edit parameters.
Parent class for import file readers.
dol_sort_array(&$array, $index, $order= 'asc', $natsort=0, $case_sensitive=0, $keepindex=0)
Advanced sort array by second index function, which produces ascending (default) or descending output...
dol_get_fiche_head($links=array(), $active= '', $title= '', $notab=0, $picto= '', $pictoisfullpath=0, $morehtmlright= '', $morecss= '', $limittoshow=0, $moretabssuffix= '')
Show tabs of a record.
print
Draft customers invoices.
Definition: index.php:89
dol_print_date($time, $format= '', $tzoutput= 'auto', $outputlangs= '', $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
dol_filemtime($pathoffile)
Return time of a file.
Definition: files.lib.php:567
if(!empty($conf->facture->enabled)&&$user->rights->facture->lire) if((!empty($conf->fournisseur->enabled)&&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD)||!empty($conf->supplier_invoice->enabled))&&$user->rights->fournisseur->facture->lire) if(!empty($conf->don->enabled)&&$user->rights->don->lire) if(!empty($conf->tax->enabled)&&$user->rights->tax->charges->lire) if(!empty($conf->facture->enabled)&&!empty($conf->commande->enabled)&&$user->rights->commande->lire &&empty($conf->global->WORKFLOW_DISABLE_CREATE_INVOICE_FROM_ORDER)) if(!empty($conf->facture->enabled)&&$user->rights->facture->lire) if((!empty($conf->fournisseur->enabled)&&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD)||!empty($conf->supplier_invoice->enabled))&&$user->rights->fournisseur->facture->lire) $resql
Social contributions to pay.
Definition: index.php:1232
dol_print_error($db= '', $error= '', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
newToken()
Return the value of token currently saved into session with name &#39;newtoken&#39;.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
dol_trunc($string, $size=40, $trunc= 'right', $stringencoding= 'UTF-8', $nodot=0, $display=0)
Truncate a string to a particular length adding &#39;...&#39; if string larger than length.
llxFooter()
Empty footer.
Definition: wrapper.php:59
img_delete($titlealt= 'default', $other= 'class="pictodelete"', $morecss= '')
Show delete logo.
if(!defined('CSRFCHECK_WITH_TOKEN')) define('CSRFCHECK_WITH_TOKEN'
Draft customers invoices.
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin= '1', $morecss= '', $textfordropdown= '')
Show information for admin users or standard users.
dol_mkdir($dir, $dataroot= '', $newmask=null)
Creation of a directory (this can create recursive subdir)
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $keepmoretags= '', $escapeonlyhtmltags=0)
Returns text escaped for inclusion in HTML alt or title tags, or into values of HTML input fields...