dolibarr 20.0.0
list.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2012 Nicolas Villa aka Boyquotes http://informetic.fr
3 * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
4 * Copyright (C) 2013-2021 Laurent Destailleur <eldy@users.sourceforge.net>
5 * Copyright (C) 2019-2024 Frédéric France <frederic.france@free.fr>
6 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
7 * Copyright (C) 2024 Alexandre Spangaro <alexandre@inovea-conseil.com>
8 *
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 3 of the License, or
12 * (at your option) any later version.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program. If not, see <https://www.gnu.org/licenses/>.
21 */
22
29// Load Dolibarr environment
30require '../main.inc.php';
31require_once DOL_DOCUMENT_ROOT.'/core/lib/admin.lib.php';
32require_once DOL_DOCUMENT_ROOT.'/cron/class/cronjob.class.php';
33require_once DOL_DOCUMENT_ROOT.'/core/lib/cron.lib.php';
34require_once DOL_DOCUMENT_ROOT.'/core/lib/date.lib.php';
35
36// Load translation files required by the page
37$langs->loadLangs(array("admin", "cron", "bills", "members"));
38
39$action = GETPOST('action', 'aZ09');
40$massaction = GETPOST('massaction', 'alpha'); // The bulk action (combo box choice into lists)
41$confirm = GETPOST('confirm', 'alpha');
42$toselect = GETPOST('toselect', 'array'); // Array of ids of elements selected into a list
43$contextpage = GETPOST('contextpage', 'aZ') ? GETPOST('contextpage', 'aZ') : 'cronjoblist'; // To manage different context of search
44
45$id = GETPOSTINT('id');
46
47$limit = GETPOSTINT('limit') ? GETPOSTINT('limit') : $conf->liste_limit;
48$sortfield = GETPOST('sortfield', 'aZ09comma');
49$sortorder = GETPOST('sortorder', 'aZ09comma');
50$page = GETPOSTISSET('pageplusone') ? (GETPOSTINT('pageplusone') - 1) : GETPOSTINT("page");
51if (empty($page) || $page == -1) {
52 $page = 0;
53} // If $page is not defined, or '' or -1
54$offset = $limit * $page;
55$pageprev = $page - 1;
56$pagenext = $page + 1;
57if (!$sortfield) {
58 $sortfield = 't.priority,t.status';
59}
60if (!$sortorder) {
61 $sortorder = 'ASC,DESC';
62}
63$optioncss = GETPOST('optioncss', 'alpha');
64$mode = GETPOST('mode', 'aZ09');
65//Search criteria
66$search_status = GETPOST('search_status', 'intcomma');
67$search_label = GETPOST("search_label", 'alpha');
68$search_module_name = GETPOST("search_module_name", 'alpha');
69$search_lastresult = GETPOST("search_lastresult", "alphawithlgt");
70$search_processing = GETPOST("search_processing", 'int');
71$securitykey = GETPOST('securitykey', 'alpha');
72
73$outputdir = $conf->cron->dir_output;
74if (empty($outputdir)) {
75 $outputdir = $conf->cronjob->dir_output;
76}
77$diroutputmassaction = $outputdir.'/temp/massgeneration/'.$user->id;
78
79$object = new Cronjob($db);
80
81// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
82$hookmanager->initHooks(array('cronjoblist'));
83$extrafields = new ExtraFields($db);
84
85// fetch optionals attributes and labels
86$extrafields->fetch_name_optionals_label($object->table_element);
87
88$search_array_options = $extrafields->getOptionalsFromPost($object->table_element, '', 'search_');
89
90// Security
91if (!$user->hasRight('cron', 'read')) {
93}
94
95$permissiontoread = $user->hasRight('cron', 'read');
96$permissiontoadd = $user->hasRight('cron', 'create') ? $user->hasRight('cron', 'create') : $user->hasRight('cron', 'write');
97$permissiontodelete = $user->hasRight('cron', 'delete');
98$permissiontoexecute = $user->hasRight('cron', 'execute');
99
100
101/*
102 * Actions
103 */
104
105if (GETPOST('cancel', 'alpha')) {
106 $action = 'list';
107 $massaction = '';
108}
109if (!GETPOST('confirmmassaction', 'alpha') && $massaction != 'presend' && $massaction != 'confirm_presend') {
110 $massaction = '';
111}
112
113$parameters = array();
114$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
115if ($reshook < 0) {
116 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
117}
118
119if (empty($reshook)) {
120 // Selection of new fields
121 include DOL_DOCUMENT_ROOT.'/core/actions_changeselectedfields.inc.php';
122
123 // Purge search criteria
124 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')) { // All tests are required to be compatible with all browsers
125 $search_label = '';
126 $search_status = -1;
127 $search_lastresult = '';
128 $toselect = array();
129 $search_array_options = array();
130 }
131 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')
132 || GETPOST('button_search_x', 'alpha') || GETPOST('button_search.x', 'alpha') || GETPOST('button_search', 'alpha')) {
133 $massaction = ''; // Protection to avoid mass action if we force a new search during a mass action confirmation
134 }
135
136 $filter = array();
137 if (!empty($search_label)) {
138 $filter['t.label'] = $search_label;
139 }
140
141 // Delete jobs
142 if ($action == 'confirm_delete' && $confirm == "yes" && $permissiontodelete) {
143 //Delete cron task
144 $object = new Cronjob($db);
145 $object->id = $id;
146 $result = $object->delete($user);
147
148 if ($result < 0) {
149 setEventMessages($object->error, $object->errors, 'errors');
150 }
151 }
152
153 // Execute jobs
154 if ($action == 'confirm_execute' && $confirm == "yes" && $permissiontoexecute) {
155 if (getDolGlobalString('CRON_KEY') && $conf->global->CRON_KEY != $securitykey) {
156 setEventMessages('Security key '.$securitykey.' is wrong', null, 'errors');
157 $action = '';
158 } else {
159 $object = new Cronjob($db);
160 $job = $object->fetch($id);
161
162 $now = dol_now(); // Date we start
163
164 $resrunjob = $object->run_jobs($user->login); // Return -1 if KO, 1 if OK
165 if ($resrunjob < 0) {
166 setEventMessages($object->error, $object->errors, 'errors');
167 }
168
169 // Plan next run
170 $res = $object->reprogram_jobs($user->login, $now);
171 if ($res > 0) {
172 if ($resrunjob >= 0) { // We show the result of reprogram only if no error message already reported
173 if ($object->lastresult >= 0) {
174 setEventMessages($langs->trans("JobFinished"), null, 'mesgs');
175 } else {
176 setEventMessages($langs->trans("JobFinished"), null, 'errors');
177 }
178 }
179 $action = '';
180 } else {
181 setEventMessages($object->error, $object->errors, 'errors');
182 $action = '';
183 }
184
185 $param = '&search_status='.urlencode($search_status);
186 if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
187 $param .= '&contextpage='.urlencode($contextpage);
188 }
189 if ($limit > 0 && $limit != $conf->liste_limit) {
190 $param .= '&limit='.((int) $limit);
191 }
192 if ($search_label) {
193 $param .= '&search_label='.urlencode($search_label);
194 }
195 if ($optioncss != '') {
196 $param .= '&optioncss='.urlencode($optioncss);
197 }
198 // Add $param from extra fields
199 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
200
201 header("Location: ".DOL_URL_ROOT.'/cron/list.php?'.$param.($sortfield ? '&sortfield='.$sortfield : '').($sortorder ? '&sortorder='.$sortorder : '')); // Make a redirect to avoid to run twice the job when using back
202 exit;
203 }
204 }
205
206 // Mass actions
207 $objectclass = 'CronJob';
208 $objectlabel = 'CronJob';
209 $uploaddir = $conf->cron->dir_output;
210 include DOL_DOCUMENT_ROOT.'/core/actions_massactions.inc.php';
211 if ($massaction && $permissiontoadd) {
212 $tmpcron = new Cronjob($db);
213 foreach ($toselect as $id) {
214 $result = $tmpcron->fetch($id);
215 if ($result) {
216 $result = 0;
217 if ($massaction == 'disable') {
218 $result = $tmpcron->setStatut(Cronjob::STATUS_DISABLED);
219 } elseif ($massaction == 'enable') {
220 $result = $tmpcron->setStatut(Cronjob::STATUS_ENABLED);
221 }
222 //else dol_print_error($db, 'Bad value for massaction');
223 if ($result < 0) {
224 setEventMessages($tmpcron->error, $tmpcron->errors, 'errors');
225 }
226 } else {
227 $error++;
228 }
229 }
230 }
231}
232
233
234/*
235 * View
236 */
237
238$form = new Form($db);
239$cronjob = new Cronjob($db);
240
241$title = $langs->trans("CronList");
242
243llxHeader('', $title, '', 0, 0, '', '', '', 'bodyforlist');
244
245$TTestNotAllowed = array();
246$sqlTest = 'SELECT rowid, test FROM '.MAIN_DB_PREFIX.'cronjob';
247$resultTest = $db->query($sqlTest);
248if ($resultTest) {
249 while ($objTest = $db->fetch_object($resultTest)) {
250 $veriftest = verifCond($objTest->test);
251 if (!$veriftest) {
252 $TTestNotAllowed[$objTest->rowid] = $objTest->rowid;
253 }
254 }
255}
256
257$sql = "SELECT";
258$sql .= " t.rowid,";
259$sql .= " t.tms,";
260$sql .= " t.datec,";
261$sql .= " t.jobtype,";
262$sql .= " t.label,";
263$sql .= " t.command,";
264$sql .= " t.classesname,";
265$sql .= " t.objectname,";
266$sql .= " t.methodename,";
267$sql .= " t.params,";
268$sql .= " t.md5params,";
269$sql .= " t.module_name,";
270$sql .= " t.priority,";
271$sql .= " t.processing,";
272$sql .= " t.datelastrun,";
273$sql .= " t.datenextrun,";
274$sql .= " t.dateend,";
275$sql .= " t.datestart,";
276$sql .= " t.lastresult,";
277$sql .= " t.datelastresult,";
278$sql .= " t.lastoutput,";
279$sql .= " t.unitfrequency,";
280$sql .= " t.frequency,";
281$sql .= " t.status,";
282$sql .= " t.fk_user_author,";
283$sql .= " t.fk_user_mod,";
284$sql .= " t.note,";
285$sql .= " t.maxrun,";
286$sql .= " t.nbrun,";
287$sql .= " t.libname,";
288$sql .= " t.test";
289$sql .= " FROM ".MAIN_DB_PREFIX."cronjob as t";
290$sql .= " WHERE entity IN (0,".$conf->entity.")";
291if (!empty($TTestNotAllowed)) {
292 $sql .= ' AND t.rowid NOT IN ('.$db->sanitize(implode(',', $TTestNotAllowed)).')';
293}
294if ($search_status >= 0 && $search_status < 2 && $search_status != '') {
295 $sql .= " AND t.status = ".(empty($search_status) ? '0' : '1');
296}
297if ($search_lastresult != '') {
298 $sql .= natural_search("t.lastresult", $search_lastresult, 1);
299}
300if (GETPOSTISSET('search_processing')) {
301 $sql .= " AND t.processing = ".((int) $search_processing);
302}
303// Manage filter
304if (is_array($filter) && count($filter) > 0) {
305 foreach ($filter as $key => $value) {
306 $sql .= " AND ".$key." LIKE '%".$db->escape($value)."%'";
307 }
308}
309if (!empty($search_module_name)) {
310 $sql .= natural_search("t.module_name", $search_module_name);
311}
312// Add where from extra fields
313include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_sql.tpl.php';
314// Add where from hooks
315$parameters = array();
316$reshook = $hookmanager->executeHooks('printFieldListWhere', $parameters); // Note that $action and $object may have been modified by hook
317$sql .= $hookmanager->resPrint;
318
319$sql .= $db->order($sortfield, $sortorder);
320// Count total nb of records
321$nbtotalofrecords = '';
322if (!getDolGlobalInt('MAIN_DISABLE_FULL_SCANLIST')) {
323 $result = $db->query($sql);
324 $nbtotalofrecords = $db->num_rows($result);
325 if (($page * $limit) > $nbtotalofrecords) { // if total resultset is smaller then paging size (filtering), goto and load page 0
326 $page = 0;
327 $offset = 0;
328 }
329}
330
331$sql .= $db->plimit($limit + 1, $offset);
332
333$result = $db->query($sql);
334if (!$result) {
335 dol_print_error($db);
336}
337
338$num = $db->num_rows($result);
339
340$arrayofselected = is_array($toselect) ? $toselect : array();
341
342$param = '';
343if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
344 $param .= '&contextpage='.urlencode($contextpage);
345}
346if ($limit > 0 && $limit != $conf->liste_limit) {
347 $param .= '&limit='.((int) $limit);
348}
349if ($search_status) {
350 $param .= '&search_status='.urlencode($search_status);
351}
352if ($search_label) {
353 $param .= '&search_label='.urlencode($search_label);
354}
355if ($search_module_name) {
356 $param .= '&search_module_name='.urlencode($search_module_name);
357}
358if ($search_lastresult) {
359 $param .= '&search_lastresult='.urlencode($search_lastresult);
360}
361if ($mode) {
362 $param .= '&mode='.urlencode($mode);
363}
364if ($optioncss != '') {
365 $param .= '&optioncss='.urlencode($optioncss);
366}
367// Add $param from extra fields
368include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
369
370$stringcurrentdate = $langs->trans("CurrentHour").': '.dol_print_date(dol_now(), 'dayhour');
371
372if ($action == 'execute') {
373 print $form->formconfirm($_SERVER['PHP_SELF']."?id=".$id.'&securitykey='.$securitykey.$param, $langs->trans("CronExecute"), $langs->trans("CronConfirmExecute"), "confirm_execute", '', '', 1);
374}
375
376if ($action == 'delete' && empty($toselect)) { // Used when we make a delete on 1 line (not used for mass delete)
377 print $form->formconfirm($_SERVER['PHP_SELF']."?id=".$id.$param, $langs->trans("CronDelete"), $langs->trans("CronConfirmDelete"), "confirm_delete", '', '', 1);
378}
379
380// List of mass actions available
381$arrayofmassactions = array(
382//'presend'=>img_picto('', 'email', 'class="pictofixedwidth"').$langs->trans("SendByMail"),
383//'builddoc'=>img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("PDFMerge"),
384 'enable' => img_picto('', 'check', 'class="pictofixedwidth"').$langs->trans("CronStatusActiveBtn"),
385 'disable' => img_picto('', 'uncheck', 'class="pictofixedwidth"').$langs->trans("CronStatusInactiveBtn"),
386);
387if ($user->hasRight('cron', 'delete')) {
388 $arrayofmassactions['predelete'] = img_picto('', 'delete', 'class="pictofixedwidth"').$langs->trans("Delete");
389}
390if (GETPOSTINT('nomassaction') || in_array($massaction, array('presend', 'predelete'))) {
391 $arrayofmassactions = array();
392}
393$massactionbutton = $form->selectMassAction('', $arrayofmassactions);
394
395if ($mode == 'modulesetup') {
396 $linkback = '<a href="'.DOL_URL_ROOT.'/admin/modules.php?restore_lastsearch_values=1">'.$langs->trans("BackToModuleList").'</a>';
397 print load_fiche_titre($langs->trans("CronSetup"), $linkback, 'title_setup');
398
399 // Configuration header
400 $head = cronadmin_prepare_head();
401}
402
403print '<form method="POST" id="searchFormList" action="'.$_SERVER["PHP_SELF"].'" name="search_form">'."\n";
404if ($optioncss != '') {
405 print '<input type="hidden" name="optioncss" value="'.$optioncss.'">';
406}
407print '<input type="hidden" name="token" value="'.newToken().'">';
408print '<input type="hidden" name="formfilteraction" id="formfilteraction" value="list">';
409print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
410print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
411print '<input type="hidden" name="page" value="'.$page.'">';
412print '<input type="hidden" name="contextpage" value="'.$contextpage.'">';
413print '<input type="hidden" name="mode" value="'.$mode.'">';
414
415// Line with explanation and button new
416$newcardbutton = '';
417$newcardbutton .= dolGetButtonTitle($langs->trans('New'), $langs->trans('CronCreateJob'), 'fa fa-plus-circle', DOL_URL_ROOT.'/cron/card.php?action=create&backtopage='.urlencode($_SERVER['PHP_SELF'].'?mode=modulesetup'), '', $user->hasRight('cron', 'create'));
418
419
420if ($mode == 'modulesetup') {
421 print dol_get_fiche_head($head, 'jobs', $langs->trans("Module2300Name"), -1, 'cron');
422
423 //print '<span class="opacitymedium">'.$langs->trans('CronInfo').'</span><br>';
424}
425
426
427print_barre_liste($title, $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, ($mode == 'modulesetup' ? '' : 'title_setup'), 0, $newcardbutton, '', $limit);
428
429// Add code for pre mass action (confirmation or email presend form)
430$topicmail = "SendCronRef";
431$modelmail = "cron";
432$objecttmp = new Cronjob($db);
433$trackid = 'cron'.$object->id;
434include DOL_DOCUMENT_ROOT.'/core/tpl/massactions_pre.tpl.php';
435
436$text = $langs->trans("HoursOnThisPageAreOnServerTZ").' '.$stringcurrentdate.'<br>';
437if (getDolGlobalString('CRON_WARNING_DELAY_HOURS')) {
438 $text .= $langs->trans("WarningCronDelayed", getDolGlobalString('CRON_WARNING_DELAY_HOURS'));
439}
440print info_admin($text);
441//print '<br>';
442
443//$varpage = empty($contextpage) ? $_SERVER["PHP_SELF"] : $contextpage;
444$selectedfields = '';
445//$selectedfields=$form->multiSelectArrayWithCheckbox('selectedfields', $arrayfields, $varpage); // This also change content of $arrayfields
446$selectedfields .= (count($arrayofmassactions) ? $form->showCheckAddButtons('checkforselect', 1) : '');
447
448print '<div class="div-table-responsive">';
449print '<table class="noborder liste">';
450
451print '<tr class="liste_titre_filter">';
452// Action column
453if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
454 print '<td class="liste_titre right">';
455 $searchpicto = $form->showFilterButtons();
456 print $searchpicto;
457 print '</td>';
458}
459print '<td class="liste_titre">&nbsp;</td>';
460print '<td class="liste_titre">';
461print '<input type="text" class="flat width75" name="search_label" value="'.$search_label.'">';
462print '</td>';
463//print '<td class="liste_titre">&nbsp;</td>';
464print '<td class="liste_titre"><input type="text" class="width50" name="search_module_name" value="'.$search_module_name.'"></td>';
465print '<td class="liste_titre">&nbsp;</td>';
466print '<td class="liste_titre">&nbsp;</td>';
467//print '<td class="liste_titre">&nbsp;</td>';
468//print '<td class="liste_titre">&nbsp;</td>';
469print '<td class="liste_titre">&nbsp;</td>';
470print '<td class="liste_titre">&nbsp;</td>';
471print '<td class="liste_titre">&nbsp;</td>';
472print '<td class="liste_titre center"><input type="text" class="width50" name="search_lastresult" value="'.$search_lastresult.'"></td>';
473print '<td class="liste_titre">&nbsp;</td>';
474print '<td class="liste_titre">&nbsp;</td>';
475print '<td class="liste_titre center">';
476print $form->selectarray('search_status', array('0' => $langs->trans("Disabled"), '1' => $langs->trans("Scheduled")), $search_status, 1, 0, 0, '', 0, 0, 0, '', 'search_status width100 onrightofpage');
477print '</td>';
478print '<td class="liste_titre">&nbsp;</td>';
479// Action column
480if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
481 print '<td class="liste_titre right">';
482 $searchpicto = $form->showFilterButtons();
483 print $searchpicto;
484 print '</td>';
485}
486print '</tr>';
487
488print '<tr class="liste_titre">';
489// Action column
490if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
491 print_liste_field_titre($selectedfields, $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'center maxwidthsearch ');
492}
493print_liste_field_titre("Ref", $_SERVER["PHP_SELF"], "t.rowid", "", $param, '', $sortfield, $sortorder);
494print_liste_field_titre("CronLabel", $_SERVER["PHP_SELF"], "t.label", "", $param, '', $sortfield, $sortorder);
495//print_liste_field_titre("Priority", $_SERVER["PHP_SELF"], "t.priority", "", $param, '', $sortfield, $sortorder);
496print_liste_field_titre("CronModule", $_SERVER["PHP_SELF"], "t.module_name", "", $param, '', $sortfield, $sortorder);
497print_liste_field_titre("", '', '', "", $param, '', $sortfield, $sortorder, 'tdoverflowmax50 ');
498print_liste_field_titre("CronFrequency", '', "", "", $param, '', $sortfield, $sortorder);
499//print_liste_field_titre("CronDtStart", $_SERVER["PHP_SELF"], "t.datestart", "", $param, 'align="center"', $sortfield, $sortorder);
500//print_liste_field_titre("CronDtEnd", $_SERVER["PHP_SELF"], "t.dateend", "", $param, 'align="center"', $sortfield, $sortorder);
501print_liste_field_titre("CronNbRun", $_SERVER["PHP_SELF"], "t.nbrun", "", $param, '', $sortfield, $sortorder, 'right tdoverflowmax50 maxwidth50imp ');
502print_liste_field_titre("CronDtLastLaunch", $_SERVER["PHP_SELF"], "t.datelastrun", "", $param, '', $sortfield, $sortorder, 'center tdoverflowmax100 ');
503print_liste_field_titre("Duration", $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'center ');
504print_liste_field_titre("CronLastResult", $_SERVER["PHP_SELF"], "t.lastresult", "", $param, '', $sortfield, $sortorder, 'center ');
505print_liste_field_titre("CronLastOutput", $_SERVER["PHP_SELF"], "t.lastoutput", "", $param, '', $sortfield, $sortorder);
506print_liste_field_titre("CronDtNextLaunch", $_SERVER["PHP_SELF"], "t.datenextrun", "", $param, '', $sortfield, $sortorder, 'center ');
507print_liste_field_titre("Status", $_SERVER["PHP_SELF"], "t.status,t.priority", "", $param, '', $sortfield, $sortorder, 'center ');
508print_liste_field_titre("", $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'center ');
509// Action column
510if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
511 print_liste_field_titre($selectedfields, $_SERVER["PHP_SELF"], "", "", $param, '', $sortfield, $sortorder, 'center maxwidthsearch ');
512}
513print "</tr>\n";
514
515
516if ($num > 0) {
517 // Loop on each job
518 $now = dol_now();
519 $i = 0;
520
521 while ($i < min($num, $limit)) {
522 $obj = $db->fetch_object($result);
523
524 if (empty($obj)) {
525 break;
526 }
527
528 $reg = array();
529 if (preg_match('/:(.*)$/', $obj->label, $reg)) {
530 $langs->load($reg[1]);
531 }
532
533 $object->id = $obj->rowid;
534 $object->ref = $obj->rowid;
535 $object->label = preg_replace('/:.*$/', '', $obj->label);
536 $object->status = $obj->status;
537 $object->priority = $obj->priority;
538 $object->processing = $obj->processing;
539 $object->lastresult = (string) $obj->lastresult;
540 $object->datestart = $db->jdate($obj->datestart);
541 $object->dateend = $db->jdate($obj->dateend);
542 $object->module_name = $obj->module_name;
543 $object->params = $obj->params;
544 $object->datelastrun = $db->jdate($obj->datelastrun);
545 $object->datenextrun = $db->jdate($obj->datenextrun);
546
547 $datelastrun = $db->jdate($obj->datelastrun);
548 $datelastresult = $db->jdate($obj->datelastresult);
549
550 print '<tr class="oddeven">';
551
552 // Action column
553 if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
554 print '<td class="nowraponall center">';
555 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
556 $selected = 0;
557 if (in_array($obj->rowid, $arrayofselected)) {
558 $selected = 1;
559 }
560 print '<input id="cb'.$obj->rowid.'" class="flat checkforselect valignmiddle" type="checkbox" name="toselect[]" value="'.$obj->rowid.'"'.($selected ? ' checked="checked"' : '').'>';
561 }
562 print '</td>';
563 }
564
565 // Ref
566 print '<td class="nowraponall">';
567 print $object->getNomUrl(1);
568 print '</td>';
569
570 // Label
571 print '<td class="minwidth125">';
572 if (!empty($object->label)) {
573 $object->ref = $langs->trans($object->label);
574 print '<div class="small twolinesmax minwidth150 maxwidth250 classfortooltip" title="'.dol_escape_htmltag($langs->trans($object->label), 0, 0).'">';
575 print $object->getNomUrl(0, '', 1);
576 print '</div>';
577 $object->ref = $obj->rowid;
578 } else {
579 //print $langs->trans('CronNone');
580 }
581 print '</td>';
582
583 // Priority
584 /*print '<td class="right">';
585 print dol_escape_htmltag($object->priority);
586 print '</td>';*/
587
588 // Module
589 print '<td>';
590 print dol_escape_htmltag($object->module_name);
591 print '</td>';
592
593 // Class/Method
594 print '<td class="nowraponall">';
595 if ($obj->jobtype == 'method') {
596 $text = img_picto('', 'code');
597 $texttoshow = '<b>'.$langs->trans("CronType_method").'</b><br><br>';
598 $texttoshow .= $langs->trans('CronModule').': '.$obj->module_name.'<br>';
599 $texttoshow .= $langs->trans('CronClass').': '.$obj->classesname.'<br>';
600 $texttoshow .= $langs->trans('CronObject').': '.$obj->objectname.'<br>';
601 $texttoshow .= $langs->trans('CronMethod').': '.$obj->methodename;
602 $texttoshow .= '<br>'.$langs->trans('CronArgs').': '.$obj->params;
603 $texttoshow .= '<br>'.$langs->trans('Comment').': '.$langs->trans($obj->note);
604 } elseif ($obj->jobtype == 'command') {
605 $text = img_picto('', 'terminal');
606 $texttoshow = '<b>'.$langs->trans('CronType_command').'</b><br><br>';
607 $texttoshow .= $langs->trans('CronCommand').': '.dol_trunc($obj->command);
608 $texttoshow .= '<br>'.$langs->trans('CronArgs').': '.$obj->params;
609 $texttoshow .= '<br>'.$langs->trans('Comment').': '.$langs->trans($obj->note);
610 }
611 print '<span class="classfortooltip" title="'.dol_escape_htmltag($texttoshow, 1, 1).'">'.$text.'</a>';
612 print '</td>';
613
614 // Frequency
615 $s = '';
616 if ($obj->unitfrequency == "60") {
617 $s = ($obj->frequency)." ".$langs->trans('MinuteShort');
618 } elseif ($obj->unitfrequency == "3600") {
619 $s = ($obj->frequency)." ".$langs->trans('HourShort');
620 } elseif ($obj->unitfrequency == "86400") {
621 $s = ($obj->frequency)." ".($obj->frequency > 1 ? $langs->trans('DurationDays') : $langs->trans('DurationDay'));
622 } elseif ($obj->unitfrequency == "604800") {
623 $s = ($obj->frequency)." ".($obj->frequency > 1 ? $langs->trans('DurationWeeks') : $langs->trans('DurationWeek'));
624 } elseif ($obj->unitfrequency == "2678400") {
625 $s = ($obj->frequency)." ".($obj->frequency > 1 ? $langs->trans('DurationMonths') : $langs->trans('DurationMonth'));
626 }
627 print '<td class="tdoverflowmax125 center" title="'.dol_escape_htmltag($s).'">';
628 print dol_escape_htmltag($s);
629 print '</td>';
630
631 /*
632 print '<td class="center">';
633 if (!empty($obj->datestart)) {
634 print dol_print_date($db->jdate($obj->datestart), 'dayhour', 'tzserver');
635 }
636 print '</td>';
637
638 print '<td class="center">';
639 if (!empty($obj->dateend)) {
640 print dol_print_date($db->jdate($obj->dateend), 'dayhour', 'tzserver');
641 }
642 print '</td>';
643 */
644
645 print '<td class="right">';
646 if (!empty($obj->nbrun)) {
647 print dol_escape_htmltag($obj->nbrun);
648 } else {
649 print '0';
650 }
651 if (!empty($obj->maxrun)) {
652 print ' <span class="'.$langs->trans("Max").'">/ '.dol_escape_htmltag($obj->maxrun).'</span>';
653 }
654 print '</td>';
655
656 $datefromto = (empty($datelastrun) ? '' : dol_print_date($datelastrun, 'dayhoursec', 'tzserver')).' - '.(empty($datelastresult) ? '' : dol_print_date($datelastresult, 'dayhoursec', 'tzserver'));
657
658 // Date start last run
659 print '<td class="center" title="'.dol_escape_htmltag($datefromto).'">';
660 if (!empty($datelastrun)) {
661 print dol_print_date($datelastrun, 'dayhoursec', 'tzserver');
662 }
663 print '</td>';
664
665 // Duration
666 print '<td class="center nowraponall" title="'.dol_escape_htmltag($datefromto).'">';
667 if (!empty($datelastresult) && ($datelastresult >= $datelastrun)) {
668 $nbseconds = max($datelastresult - $datelastrun, 1);
669 print $nbseconds.' '.$langs->trans("SecondShort");
670 }
671 print '</td>';
672
673 // Return code of last run
674 print '<td class="center tdlastresultcode" title="'.dol_escape_htmltag($obj->lastresult).'">';
675 if ($obj->lastresult != '') {
676 if (empty($obj->lastresult)) {
677 print $obj->lastresult; // Print '0'
678 } else {
679 print '<span class="error">'.dol_escape_htmltag(dol_trunc($obj->lastresult)).'</div>';
680 }
681 }
682 print '</td>';
683
684 // Output of last run
685 print '<td class="small minwidth150">';
686 if (!empty($obj->lastoutput)) {
687 print '<div class="twolinesmax classfortooltip" title="'.dol_escape_htmltag($obj->lastoutput, 1, 1).'">';
688 print dol_trunc(dolGetFirstLineOfText($obj->lastoutput, 2), 100);
689 print '</div>';
690 }
691 print '</td>';
692
693 // Next run date
694 print '<td class="center">';
695 if (!empty($obj->datenextrun)) {
696 $datenextrun = $db->jdate($obj->datenextrun);
697 if (empty($obj->status)) {
698 print '<span class="opacitymedium strikefordisabled">';
699 }
700 print dol_print_date($datenextrun, 'dayhoursec');
701 if ($obj->status == Cronjob::STATUS_ENABLED) {
702 if ($obj->maxrun && $obj->nbrun >= $obj->maxrun) {
703 print img_warning($langs->trans("MaxRunReached"));
704 } elseif ($datenextrun && $datenextrun < $now) {
705 print img_warning($langs->trans("Late"));
706 }
707 }
708 if (empty($obj->status)) {
709 print '</span>';
710 }
711 }
712 print '</td>';
713
714 // Status
715 print '<td class="center">';
716 print $object->getLibStatut(5);
717 print '</td>';
718
719 print '<td class="nowraponall right">';
720
721 $backtopage = urlencode($_SERVER["PHP_SELF"].'?'.$param.($sortfield ? '&sortfield='.$sortfield : '').($sortorder ? '&sortorder='.$sortorder : ''));
722 if ($user->hasRight('cron', 'create')) {
723 print '<a class="editfielda" href="'.DOL_URL_ROOT."/cron/card.php?id=".$obj->rowid.'&action=edit&token='.newToken().($sortfield ? '&sortfield='.$sortfield : '').($sortorder ? '&sortorder='.$sortorder : '').$param;
724 print "&backtopage=".$backtopage."\" title=\"".dol_escape_htmltag($langs->trans('Edit'))."\">".img_picto($langs->trans('Edit'), 'edit')."</a> &nbsp;";
725 }
726 if ($user->hasRight('cron', 'delete')) {
727 print '<a class="reposition" href="'.$_SERVER["PHP_SELF"]."?id=".$obj->rowid.'&action=delete&token='.newToken().($page ? '&page='.$page : '').($sortfield ? '&sortfield='.$sortfield : '').($sortorder ? '&sortorder='.$sortorder : '').$param;
728 print '" title="'.dol_escape_htmltag($langs->trans('CronDelete')).'">'.img_picto($langs->trans('CronDelete'), 'delete', '', false, 0, 0, '', 'marginleftonly').'</a> &nbsp; ';
729 } else {
730 print '<a href="#" title="'.dol_escape_htmltag($langs->trans('NotEnoughPermissions')).'">'.img_picto($langs->trans('NotEnoughPermissions'), 'delete', '', false, 0, 0, '', 'marginleftonly').'</a> &nbsp; ';
731 }
732 if ($user->hasRight('cron', 'execute')) {
733 if (!empty($obj->status)) {
734 print '<a class="reposition" href="'.$_SERVER["PHP_SELF"].'?id='.$obj->rowid.'&action=execute&token='.newToken();
735 print(!getDolGlobalString('CRON_KEY') ? '' : '&securitykey=' . getDolGlobalString('CRON_KEY'));
736 print($sortfield ? '&sortfield='.$sortfield : '');
737 print($sortorder ? '&sortorder='.$sortorder : '');
738 print $param."\" title=\"".dol_escape_htmltag($langs->trans('CronExecute'))."\">".img_picto($langs->trans('CronExecute'), "play", '', false, 0, 0, '', 'marginleftonly').'</a>';
739 } else {
740 print '<a href="#" class="cursordefault" title="'.dol_escape_htmltag($langs->trans('JobDisabled')).'">'.img_picto($langs->trans('JobDisabled'), "playdisabled", '', false, 0, 0, '', 'marginleftonly').'</a>';
741 }
742 } else {
743 print '<a href="#" class="cursornotallowed" title="'.dol_escape_htmltag($langs->trans('NotEnoughPermissions')).'">'.img_picto($langs->trans('NotEnoughPermissions'), "playdisabled", '', false, 0, 0, '', 'marginleftonly').'</a>';
744 }
745
746 print '</td>';
747
748 // Action column
749 if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
750 print '<td class="nowraponall center">';
751 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
752 $selected = 0;
753 if (in_array($obj->rowid, $arrayofselected)) {
754 $selected = 1;
755 }
756 print '<input id="cb'.$obj->rowid.'" class="flat checkforselect valignmiddle" type="checkbox" name="toselect[]" value="'.$obj->rowid.'"'.($selected ? ' checked="checked"' : '').'>';
757 }
758 print '</td>';
759 }
760
761 print '</tr>';
762
763 $i++;
764 }
765} else {
766 print '<tr><td colspan="16"><span class="opacitymedium">'.$langs->trans('CronNoJobs').'</span></td></tr>';
767}
768
769print '</table>';
770print '</div>';
771
772print '</from>';
773
774if ($mode == 'modulesetup') {
775 print dol_get_fiche_end();
776}
777
778
779llxFooter();
780
781$db->close();
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:58
if(!defined('NOREQUIRESOC')) if(!defined( 'NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined( 'NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined( 'NOREQUIREAJAX')) llxHeader()
Empty header.
Definition wrapper.php:55
llxFooter()
Empty footer.
Definition wrapper.php:69
Cron Job class.
Class to manage standard extra fields.
Class to manage generation of HTML components Only common components must be here.
cronadmin_prepare_head()
Return array of tabs to used on pages to setup cron module.
Definition cron.lib.php:31
verifCond($strToEvaluate, $onlysimplestring='1')
Verify if condition in string is ok or not.
load_fiche_titre($title, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='')
Load a title with picto.
img_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
GETPOSTINT($paramname, $method=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dolGetFirstLineOfText($text, $nboflines=1, $charset='UTF-8')
Return first line of text.
dol_get_fiche_head($links=array(), $active='', $title='', $notab=0, $picto='', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limittoshow=0, $moretabssuffix='', $dragdropfile=0)
Show tabs of a record.
dolGetButtonTitle($label, $helpText='', $iconClass='fa fa-file', $url='', $id='', $status=1, $params=array())
Function dolGetButtonTitle : this kind of buttons are used in title in list.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
natural_search($fields, $value, $mode=0, $nofirstand=0)
Generate natural SQL search string for a criteria (this criteria can be tested on one or several fiel...
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs=null, $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
newToken()
Return the value of token currently saved into session with name 'newtoken'.
print_liste_field_titre($name, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $tooltip="", $forcenowrapcolumntitle=0)
Show title line of an array.
print_barre_liste($title, $page, $file, $options='', $sortfield='', $sortorder='', $morehtmlcenter='', $num=-1, $totalnboflines='', $picto='generic', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limit=-1, $hideselectlimit=0, $hidenavigation=0, $pagenavastextinput=0, $morehtmlrightbeforearrow='')
Print a title with navigation controls for pagination.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0)
Set event messages in dol_events session object.
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
dol_trunc($string, $size=40, $trunc='right', $stringencoding='UTF-8', $nodot=0, $display=0)
Truncate a string to a particular length adding '…' if string larger than length.
getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin='1', $morecss='hideonsmartphone', $textfordropdown='', $picto='')
Show information in HTML for admin users or standard users.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Returns text escaped for inclusion in HTML alt or title or value tags, or into values of HTML input f...
accessforbidden($message='', $printheader=1, $printfooter=1, $showonlymessage=0, $params=null)
Show a message to say access is forbidden and stop program.