dolibarr  17.0.4
blockedlog_list.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2017 ATM Consulting <contact@atm-consulting.fr>
3  * Copyright (C) 2017-2018 Laurent Destailleur <eldy@destailleur.fr>
4  * Copyright (C) 2018 Frédéric France <frederic.france@netlogic.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 
27 // Load Dolibarr environment
28 require '../../main.inc.php';
29 require_once DOL_DOCUMENT_ROOT.'/blockedlog/lib/blockedlog.lib.php';
30 require_once DOL_DOCUMENT_ROOT.'/blockedlog/class/blockedlog.class.php';
31 require_once DOL_DOCUMENT_ROOT.'/blockedlog/class/authority.class.php';
32 require_once DOL_DOCUMENT_ROOT.'/core/lib/admin.lib.php';
33 require_once DOL_DOCUMENT_ROOT.'/core/lib/date.lib.php';
34 
35 // Load translation files required by the page
36 $langs->loadLangs(array('admin', 'bills', 'blockedlog', 'other'));
37 
38 // Access Control
39 if ((!$user->admin && empty($user->rights->blockedlog->read)) || empty($conf->blockedlog->enabled)) {
41 }
42 
43 // Get Parameters
44 $action = GETPOST('action', 'aZ09');
45 $contextpage = GETPOST('contextpage', 'aZ') ?GETPOST('contextpage', 'aZ') : 'blockedloglist'; // To manage different context of search
46 $backtopage = GETPOST('backtopage', 'alpha'); // Go back to a dedicated page
47 $optioncss = GETPOST('optioncss', 'aZ'); // Option for the css output (always '' except when 'print')
48 
49 $search_showonlyerrors = GETPOST('search_showonlyerrors', 'int');
50 if ($search_showonlyerrors < 0) {
51  $search_showonlyerrors = 0;
52 }
53 
54 $search_startyear = GETPOST('search_startyear', 'int');
55 $search_startmonth = GETPOST('search_startmonth', 'int');
56 $search_startday = GETPOST('search_startday', 'int');
57 $search_endyear = GETPOST('search_endyear', 'int');
58 $search_endmonth = GETPOST('search_endmonth', 'int');
59 $search_endday = GETPOST('search_endday', 'int');
60 $search_id = GETPOST('search_id', 'alpha');
61 $search_fk_user = GETPOST('search_fk_user', 'intcomma');
62 $search_start = -1;
63 if ($search_startyear != '') {
64  $search_start = dol_mktime(0, 0, 0, $search_startmonth, $search_startday, $search_startyear);
65 }
66 $search_end = -1;
67 if (GETPOST('search_endyear') != '') {
68  $search_end = dol_mktime(23, 59, 59, GETPOST('search_endmonth'), GETPOST('search_endday'), GETPOST('search_endyear'));
69 }
70 $search_code = GETPOST('search_code', 'alpha');
71 $search_ref = GETPOST('search_ref', 'alpha');
72 $search_amount = GETPOST('search_amount', 'alpha');
73 
74 if (($search_start == -1 || empty($search_start)) && !GETPOSTISSET('search_startmonth')) {
75  $search_start = dol_time_plus_duree(dol_now(), '-1', 'w');
76 }
77 
78 // Load variable for pagination
79 $limit = GETPOST('limit', 'int') ?GETPOST('limit', 'int') : $conf->liste_limit;
80 $sortfield = GETPOST('sortfield', 'aZ09comma');
81 $sortorder = GETPOST('sortorder', 'aZ09comma');
82 $page = GETPOSTISSET('pageplusone') ? (GETPOST('pageplusone') - 1) : GETPOST("page", 'int');
83 if (empty($page) || $page == -1) {
84  $page = 0;
85 } // If $page is not defined, or '' or -1
86 $offset = $limit * $page;
87 $pageprev = $page - 1;
88 $pagenext = $page + 1;
89 
90 if (empty($sortfield)) {
91  $sortfield = 'rowid';
92 }
93 if (empty($sortorder)) {
94  $sortorder = 'DESC';
95 }
96 
97 $block_static = new BlockedLog($db);
98 $block_static->loadTrackedEvents();
99 
100 $result = restrictedArea($user, 'blockedlog', 0, '');
101 
102 // Execution Time
103 $max_execution_time_for_importexport = (empty($conf->global->EXPORT_MAX_EXECUTION_TIME) ? 300 : $conf->global->EXPORT_MAX_EXECUTION_TIME); // 5mn if not defined
104 $max_time = @ini_get("max_execution_time");
105 if ($max_time && $max_time < $max_execution_time_for_importexport) {
106  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.");
107  @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
108 }
109 
110 
111 /*
112  * Actions
113  */
114 
115 // Purge search criteria
116 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
117  $search_id = '';
118  $search_fk_user = '';
119  $search_start = -1;
120  $search_end = -1;
121  $search_code = '';
122  $search_ref = '';
123  $search_amount = '';
124  $search_showonlyerrors = 0;
125  $toselect = array();
126  $search_array_options = array();
127 }
128 
129 if ($action === 'downloadblockchain') {
130  $auth = new BlockedLogAuthority($db);
131 
132  $bc = $auth->getLocalBlockChain();
133 
134  header('Content-Type: application/octet-stream');
135  header("Content-Transfer-Encoding: Binary");
136  header("Content-disposition: attachment; filename=\"".$auth->signature.".certif\"");
137 
138  echo $bc;
139 
140  exit;
141 } elseif (GETPOST('downloadcsv', 'alpha')) {
142  $error = 0;
143 
144  $previoushash = '';
145  $firstid = '';
146 
147  if (!$error) {
148  // Get ID of first line
149  $sql = "SELECT rowid,date_creation,tms,user_fullname,action,amounts,element,fk_object,date_object,ref_object,signature,fk_user,object_data";
150  $sql .= " FROM ".MAIN_DB_PREFIX."blockedlog";
151  $sql .= " WHERE entity = ".$conf->entity;
152  if (GETPOST('monthtoexport', 'int') > 0 || GETPOST('yeartoexport', 'int') > 0) {
153  $dates = dol_get_first_day(GETPOST('yeartoexport', 'int'), GETPOST('monthtoexport', 'int') ?GETPOST('monthtoexport', 'int') : 1);
154  $datee = dol_get_last_day(GETPOST('yeartoexport', 'int'), GETPOST('monthtoexport', 'int') ?GETPOST('monthtoexport', 'int') : 12);
155  $sql .= " AND date_creation BETWEEN '".$db->idate($dates)."' AND '".$db->idate($datee)."'";
156  }
157  $sql .= " ORDER BY rowid ASC"; // Required so we get the first one
158  $sql .= $db->plimit(1);
159 
160  $res = $db->query($sql);
161  if ($res) {
162  // Make the first fetch to get first line
163  $obj = $db->fetch_object($res);
164  if ($obj) {
165  $previoushash = $block_static->getPreviousHash(0, $obj->rowid);
166  $firstid = $obj->rowid;
167  } else { // If not data found for filter, we do not need previoushash neither firstid
168  $previoushash = 'nodata';
169  $firstid = '';
170  }
171  } else {
172  $error++;
173  setEventMessages($db->lasterror, null, 'errors');
174  }
175  }
176 
177  if (!$error) {
178  // Now restart request with all data = no limit(1) in sql request
179  $sql = "SELECT rowid,date_creation,tms,user_fullname,action,amounts,element,fk_object,date_object,ref_object,signature,fk_user,object_data";
180  $sql .= " FROM ".MAIN_DB_PREFIX."blockedlog";
181  $sql .= " WHERE entity = ".$conf->entity;
182  if (GETPOST('monthtoexport', 'int') > 0 || GETPOST('yeartoexport', 'int') > 0) {
183  $dates = dol_get_first_day(GETPOST('yeartoexport', 'int'), GETPOST('monthtoexport', 'int') ?GETPOST('monthtoexport', 'int') : 1);
184  $datee = dol_get_last_day(GETPOST('yeartoexport', 'int'), GETPOST('monthtoexport', 'int') ?GETPOST('monthtoexport', 'int') : 12);
185  $sql .= " AND date_creation BETWEEN '".$db->idate($dates)."' AND '".$db->idate($datee)."'";
186  }
187  $sql .= " ORDER BY rowid ASC"; // Required so later we can use the parameter $previoushash of checkSignature()
188 
189  $res = $db->query($sql);
190  if ($res) {
191  header('Content-Type: application/octet-stream');
192  header("Content-Transfer-Encoding: Binary");
193  header("Content-disposition: attachment; filename=\"unalterable-log-archive-".$dolibarr_main_db_name."-".(GETPOST('yeartoexport', 'int') > 0 ? GETPOST('yeartoexport', 'int').(GETPOST('monthtoexport', 'int') > 0 ?sprintf("%02d", GETPOST('monthtoexport', 'int')) : '').'-' : '').$previoushash.".csv\"");
194 
195  print $langs->transnoentities('Id')
196  .';'.$langs->transnoentities('Date')
197  .';'.$langs->transnoentities('User')
198  .';'.$langs->transnoentities('Action')
199  .';'.$langs->transnoentities('Element')
200  .';'.$langs->transnoentities('Amounts')
201  .';'.$langs->transnoentities('ObjectId')
202  .';'.$langs->transnoentities('Date')
203  .';'.$langs->transnoentities('Ref')
204  .';'.$langs->transnoentities('Fingerprint')
205  .';'.$langs->transnoentities('Status')
206  .';'.$langs->transnoentities('Note')
207  .';'.$langs->transnoentities('FullData')
208  ."\n";
209 
210  $loweridinerror = 0;
211  $i = 0;
212 
213  while ($obj = $db->fetch_object($res)) {
214  // We set here all data used into signature calculation (see checkSignature method) and more
215  // IMPORTANT: We must have here, the same rule for transformation of data than into the fetch method (db->jdate for date, ...)
216  $block_static->id = $obj->rowid;
217  $block_static->date_creation = $db->jdate($obj->date_creation);
218  $block_static->date_modification = $db->jdate($obj->tms);
219  $block_static->action = $obj->action;
220  $block_static->fk_object = $obj->fk_object;
221  $block_static->element = $obj->element;
222  $block_static->amounts = (double) $obj->amounts;
223  $block_static->ref_object = $obj->ref_object;
224  $block_static->date_object = $db->jdate($obj->date_object);
225  $block_static->user_fullname = $obj->user_fullname;
226  $block_static->fk_user = $obj->fk_user;
227  $block_static->signature = $obj->signature;
228  $block_static->object_data = $block_static->dolDecodeBlockedData($obj->object_data);
229 
230  $checksignature = $block_static->checkSignature($previoushash); // If $previoushash is not defined, checkSignature will search it
231 
232  if ($checksignature) {
233  $statusofrecord = 'Valid';
234  if ($loweridinerror > 0) {
235  $statusofrecordnote = 'ValidButFoundAPreviousKO';
236  } else {
237  $statusofrecordnote = '';
238  }
239  } else {
240  $statusofrecord = 'KO';
241  $statusofrecordnote = 'LineCorruptedOrNotMatchingPreviousOne';
242  $loweridinerror = $obj->rowid;
243  }
244 
245  if ($i == 0) {
246  $statusofrecordnote = $langs->trans("PreviousFingerprint").': '.$previoushash.($statusofrecordnote ? ' - '.$statusofrecordnote : '');
247  }
248  print $obj->rowid;
249  print ';'.$obj->date_creation;
250  print ';"'.str_replace('"', '""', $obj->user_fullname).'"';
251  print ';'.$obj->action;
252  print ';'.$obj->element;
253  print ';'.$obj->amounts;
254  print ';'.$obj->fk_object;
255  print ';'.$obj->date_object;
256  print ';"'.str_replace('"', '""', $obj->ref_object).'"';
257  print ';'.$obj->signature;
258  print ';'.$statusofrecord;
259  print ';'.$statusofrecordnote;
260  print ';"'.str_replace('"', '""', $obj->object_data).'"';
261  print "\n";
262 
263  // Set new previous hash for next fetch
264  $previoushash = $obj->signature;
265 
266  $i++;
267  }
268 
269  exit;
270  } else {
271  setEventMessages($db->lasterror, null, 'errors');
272  }
273  }
274 }
275 
276 
277 /*
278  * View
279  */
280 
281 $form = new Form($db);
282 
283 if (GETPOST('withtab', 'alpha')) {
284  $title = $langs->trans("ModuleSetup").' '.$langs->trans('BlockedLog');
285 } else {
286  $title = $langs->trans("BrowseBlockedLog");
287 }
288 $help_url="EN:Module_Unalterable_Archives_-_Logs|FR:Module_Archives_-_Logs_Inaltérable";
289 
290 llxHeader('', $title, $help_url);
291 
292 $MAXLINES = 10000;
293 
294 $blocks = $block_static->getLog('all', $search_id, $MAXLINES, $sortfield, $sortorder, $search_fk_user, $search_start, $search_end, $search_ref, $search_amount, $search_code);
295 if (!is_array($blocks)) {
296  if ($blocks == -2) {
297  setEventMessages($langs->trans("TooManyRecordToScanRestrictFilters", $MAXLINES), null, 'errors');
298  } else {
299  dol_print_error($block_static->db, $block_static->error, $block_static->errors);
300  exit;
301  }
302 }
303 
304 $linkback = '';
305 if (GETPOST('withtab', 'alpha')) {
306  $linkback = '<a href="'.($backtopage ? $backtopage : DOL_URL_ROOT.'/admin/modules.php').'">'.$langs->trans("BackToModuleList").'</a>';
307 }
308 
309 print load_fiche_titre($title, $linkback);
310 
311 if (GETPOST('withtab', 'alpha')) {
313  print dol_get_fiche_head($head, 'fingerprints', '', -1);
314 }
315 
316 print '<span class="opacitymedium hideonsmartphone">'.$langs->trans("FingerprintsDesc")."<br></span>\n";
317 
318 print '<br>';
319 
320 $param = '';
321 if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
322  $param .= '&contextpage='.urlencode($contextpage);
323 }
324 if ($limit > 0 && $limit != $conf->liste_limit) {
325  $param .= '&limit='.urlencode($limit);
326 }
327 if ($search_id != '') {
328  $param .= '&search_id='.urlencode($search_id);
329 }
330 if ($search_fk_user > 0) {
331  $param .= '&search_fk_user='.urlencode($search_fk_user);
332 }
333 if ($search_startyear > 0) {
334  $param .= '&search_startyear='.urlencode($search_startyear);
335 }
336 if ($search_startmonth > 0) {
337  $param .= '&search_startmonth='.urlencode($search_startmonth);
338 }
339 if ($search_startday > 0) {
340  $param .= '&search_startday='.urlencode($search_startday);
341 }
342 if ($search_endyear > 0) {
343  $param .= '&search_endyear='.urlencode($search_endyear);
344 }
345 if ($search_endmonth > 0) {
346  $param .= '&search_endmonth='.urlencode($search_endmonth);
347 }
348 if ($search_endday > 0) {
349  $param .= '&search_endday='.urlencode($search_endday);
350 }
351 if ($search_showonlyerrors > 0) {
352  $param .= '&search_showonlyerrors='.urlencode($search_showonlyerrors);
353 }
354 if ($optioncss != '') {
355  $param .= '&optioncss='.urlencode($optioncss);
356 }
357 if (GETPOST('withtab', 'alpha')) {
358  $param .= '&withtab='.urlencode(GETPOST('withtab', 'alpha'));
359 }
360 
361 // Add $param from extra fields
362 //include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
363 
364 print '<form method="POST" id="searchFormList" action="'.$_SERVER["PHP_SELF"].'">';
365 print '<input type="hidden" name="token" value="'.newToken().'">';
366 
367 print '<div class="right">';
368 print $langs->trans("RestrictYearToExport").': ';
369 $smonth = GETPOST('monthtoexport', 'int');
370 // Month
371 $retstring = '';
372 $retstring .= '<select class="flat valignmiddle maxwidth75imp marginrightonly" id="monthtoexport" name="monthtoexport">';
373 $retstring .= '<option value="0" selected>&nbsp;</option>';
374 for ($month = 1; $month <= 12; $month++) {
375  $retstring .= '<option value="'.$month.'"'.($month == $smonth ? ' selected' : '').'>';
376  $retstring .= dol_print_date(mktime(12, 0, 0, $month, 1, 2000), "%b");
377  $retstring .= "</option>";
378 }
379 $retstring .= "</select>";
380 print $retstring;
381 print '<input type="text" name="yeartoexport" class="valignmiddle maxwidth50imp" value="'.GETPOST('yeartoexport', 'int').'">';
382 print '<input type="hidden" name="withtab" value="'.GETPOST('withtab', 'alpha').'">';
383 print '<input type="submit" name="downloadcsv" class="button" value="'.$langs->trans('DownloadLogCSV').'">';
384 if (!empty($conf->global->BLOCKEDLOG_USE_REMOTE_AUTHORITY)) {
385  print ' | <a href="?action=downloadblockchain'.(GETPOST('withtab', 'alpha') ? '&withtab='.GETPOST('withtab', 'alpha') : '').'">'.$langs->trans('DownloadBlockChain').'</a>';
386 }
387 print ' </div><br>';
388 
389 print '</form>';
390 
391 print '<form method="POST" id="searchFormList" action="'.$_SERVER["PHP_SELF"].'">';
392 
393 print '<div class="div-table-responsive">'; // You can use div-table-responsive-no-min if you dont need reserved height for your table
394 
395 if ($optioncss != '') {
396  print '<input type="hidden" name="optioncss" value="'.$optioncss.'">';
397 }
398 print '<input type="hidden" name="token" value="'.newToken().'">';
399 print '<input type="hidden" name="formfilteraction" id="formfilteraction" value="list">';
400 print '<input type="hidden" name="action" value="list">';
401 print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
402 print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
403 print '<input type="hidden" name="page" value="'.$page.'">';
404 print '<input type="hidden" name="contextpage" value="'.$contextpage.'">';
405 print '<input type="hidden" name="withtab" value="'.GETPOST('withtab', 'alpha').'">';
406 
407 print '<table class="noborder centpercent">';
408 
409 // Line of filters
410 print '<tr class="liste_titre_filter">';
411 
412 print '<td class="liste_titre"><input type="text" class="maxwidth50" name="search_id" value="'.dol_escape_htmltag($search_id).'"></td>';
413 
414 print '<td class="liste_titre">';
415 //print $langs->trans("from").': ';
416 print $form->selectDate($search_start, 'search_start');
417 //print '<br>';
418 //print $langs->trans("to").': ';
419 print $form->selectDate($search_end, 'search_end');
420 print '</td>';
421 
422 // User
423 print '<td class="liste_titre">';
424 print $form->select_dolusers($search_fk_user, 'search_fk_user', 1, null, 0, '', '', 0, 0, 0, '', 0, '', 'maxwidth200');
425 
426 print '</td>';
427 
428 // Actions code
429 $langs->load("blockedlog");
430 print '<td class="liste_titre">';
431 print $form->selectarray('search_code', $block_static->trackedevents, $search_code, 1, 0, 0, '', 1, 0, 0, 'ASC', 'maxwidth200', 1);
432 print '</td>';
433 
434 // Ref
435 print '<td class="liste_titre"><input type="text" class="maxwidth50" name="search_ref" value="'.dol_escape_htmltag($search_ref).'"></td>';
436 
437 // Link to ref
438 print '<td class="liste_titre"></td>';
439 
440 // Amount
441 print '<td class="liste_titre right"><input type="text" class="maxwidth50" name="search_amount" value="'.dol_escape_htmltag($search_amount).'"></td>';
442 
443 // Full data
444 print '<td class="liste_titre"></td>';
445 
446 // Fingerprint
447 print '<td class="liste_titre"></td>';
448 
449 // Status
450 print '<td class="liste_titre">';
451 $array = array("1" => "OnlyNonValid");
452 print $form->selectarray('search_showonlyerrors', $array, $search_showonlyerrors, 1, 0, 0, '', 1, 0, 0, 'ASC', 'search_status maxwidth200 onrightofpage', 1);
453 print '</td>';
454 
455 // Status note
456 print '<td class="liste_titre"></td>';
457 
458 // Action column
459 print '<td class="liste_titre" align="middle">';
460 $searchpicto = $form->showFilterButtons();
461 print $searchpicto;
462 print '</td>';
463 
464 print '</tr>';
465 
466 print '<tr class="liste_titre">';
467 print getTitleFieldOfList($langs->trans('#'), 0, $_SERVER["PHP_SELF"], 'rowid', '', $param, '', $sortfield, $sortorder, 'minwidth50 ')."\n";
468 print getTitleFieldOfList($langs->trans('Date'), 0, $_SERVER["PHP_SELF"], 'date_creation', '', $param, '', $sortfield, $sortorder, '')."\n";
469 print getTitleFieldOfList($langs->trans('Author'), 0, $_SERVER["PHP_SELF"], 'user_fullname', '', $param, '', $sortfield, $sortorder, '')."\n";
470 print getTitleFieldOfList($langs->trans('Action'), 0, $_SERVER["PHP_SELF"], '', '', $param, '', $sortfield, $sortorder, '')."\n";
471 print getTitleFieldOfList($langs->trans('Ref'), 0, $_SERVER["PHP_SELF"], 'ref_object', '', $param, '', $sortfield, $sortorder, '')."\n";
472 print getTitleFieldOfList('', 0, $_SERVER["PHP_SELF"], '', '', $param, '', $sortfield, $sortorder, '')."\n";
473 print getTitleFieldOfList($langs->trans('Amount'), 0, $_SERVER["PHP_SELF"], '', '', $param, 'class="right"', $sortfield, $sortorder, '')."\n";
474 print getTitleFieldOfList($langs->trans('DataOfArchivedEvent'), 0, $_SERVER["PHP_SELF"], '', '', $param, 'align="center"', $sortfield, $sortorder, '')."\n";
475 print getTitleFieldOfList($langs->trans('Fingerprint'), 0, $_SERVER["PHP_SELF"], '', '', $param, '', $sortfield, $sortorder, '')."\n";
476 print getTitleFieldOfList($langs->trans('Status'), 0, $_SERVER["PHP_SELF"], '', '', $param, 'align="center"', $sortfield, $sortorder, '')."\n";
477 print getTitleFieldOfList('', 0, $_SERVER["PHP_SELF"], '', '', $param, 'align="center"', $sortfield, $sortorder, '')."\n";
478 print getTitleFieldOfList('<span id="blockchainstatus"></span>', 0, $_SERVER["PHP_SELF"], '', '', $param, 'align="center"', $sortfield, $sortorder, '')."\n";
479 print '</tr>';
480 
481 if (!empty($conf->global->BLOCKEDLOG_SCAN_ALL_FOR_LOWERIDINERROR)) {
482  // This is version that is faster but require more memory and report errors that are outside the filter range
483 
484  // TODO Make a full scan of table in reverse order of id of $block, so we can use the parameter $previoushash into checkSignature to save requests
485  // to find the $loweridinerror.
486 } else {
487  // This is version that optimize the memory (but will not report errors that are outside the filter range)
488  $loweridinerror = 0;
489  $checkresult = array();
490  $checkdetail = array();
491  if (is_array($blocks)) {
492  foreach ($blocks as &$block) {
493  $tmpcheckresult = $block->checkSignature('', 1); // Note: this make a sql request at each call, we can't avoid this as the sorting order is various
494 
495  $checksignature = $tmpcheckresult['checkresult'];
496 
497  $checkresult[$block->id] = $checksignature; // false if error
498  $checkdetail[$block->id] = $tmpcheckresult;
499 
500  if (!$checksignature) {
501  if (empty($loweridinerror)) {
502  $loweridinerror = $block->id;
503  } else {
504  $loweridinerror = min($loweridinerror, $block->id);
505  }
506  }
507  }
508  }
509 }
510 
511 if (is_array($blocks)) {
512  $nbshown = 0;
513  $MAXFORSHOWLINK = 100;
514  $object_link = '';
515 
516  foreach ($blocks as &$block) {
517  //if (empty($search_showonlyerrors) || ! $checkresult[$block->id] || ($loweridinerror && $block->id >= $loweridinerror))
518  if (empty($search_showonlyerrors) || !$checkresult[$block->id]) {
519  $nbshown++;
520 
521  if ($nbshown < $MAXFORSHOWLINK) { // For performance and memory purpose, we get/show the link of objects only for the 100 first output
522  $object_link = $block->getObjectLink();
523  } else {
524  $object_link = $block->element.'/'.$block->fk_object;
525  }
526 
527  print '<tr class="oddeven">';
528 
529  // ID
530  print '<td>'.dol_escape_htmltag($block->id).'</td>';
531 
532  // Date
533  print '<td class="nowraponall">'.dol_print_date($block->date_creation, 'dayhour').'</td>';
534 
535  // User
536  print '<td>';
537  //print $block->getUser()
538  print dol_escape_htmltag($block->user_fullname);
539  print '</td>';
540 
541  // Action
542  print '<td class="tdoverflowmax250" title="'.dol_escape_htmltag($langs->trans('log'.$block->action)).'">'.$langs->trans('log'.$block->action).'</td>';
543 
544  // Ref
545  print '<td class="nowraponall">';
546  print $block->ref_object;
547  print '</td>';
548 
549  // Link to source object
550  print '<td'.(preg_match('/<a/', $object_link) ? ' class="nowrap"' : '').'><!-- object_link -->'.$object_link.'</td>';
551 
552  // Amount
553  print '<td class="right nowraponall">'.price($block->amounts).'</td>';
554 
555  // Details link
556  print '<td align="center"><a href="#" data-blockid="'.$block->id.'" rel="show-info">'.img_info($langs->trans('ShowDetails')).'</a></td>';
557 
558  // Fingerprint
559  print '<td class="nowrap">';
560  $texttoshow = $langs->trans("Fingerprint").' - '.$langs->trans("Saved").':<br>'.$block->signature;
561  $texttoshow .= '<br><br>'.$langs->trans("Fingerprint").' - Recalculated sha256(previoushash * data):<br>'.$checkdetail[$block->id]['calculatedsignature'];
562  $texttoshow .= '<br><span class="opacitymedium">'.$langs->trans("PreviousHash").'='.$checkdetail[$block->id]['previoushash'].'</span>';
563  //$texttoshow .= '<br>keyforsignature='.$checkdetail[$block->id]['keyforsignature'];
564  print $form->textwithpicto(dol_trunc($block->signature, '8'), $texttoshow, 1, 'help', '', 0, 2, 'fingerprint'.$block->id);
565  print '</td>';
566 
567  // Status
568  print '<td class="center">';
569  if (!$checkresult[$block->id] || ($loweridinerror && $block->id >= $loweridinerror)) { // If error
570  if ($checkresult[$block->id]) {
571  print '<span class="badge badge-status4 badge-status" title="'.$langs->trans('OkCheckFingerprintValidityButChainIsKo').'">OK</span>';
572  } else {
573  print '<span class="badge badge-status8 badge-status" title="'.$langs->trans('KoCheckFingerprintValidity').'">KO</span>';
574  }
575  } else {
576  print '<span class="badge badge-status4 badge-status" title="'.$langs->trans('OkCheckFingerprintValidity').'">OK</span>';
577  }
578  print '</td>';
579 
580  // Note
581  print '<td class="center">';
582  if (!$checkresult[$block->id] || ($loweridinerror && $block->id >= $loweridinerror)) { // If error
583  if ($checkresult[$block->id]) {
584  print $form->textwithpicto('', $langs->trans('OkCheckFingerprintValidityButChainIsKo'));
585  }
586  }
587 
588  if (!empty($conf->global->BLOCKEDLOG_USE_REMOTE_AUTHORITY) && !empty($conf->global->BLOCKEDLOG_AUTHORITY_URL)) {
589  print ' '.($block->certified ? img_picto($langs->trans('AddedByAuthority'), 'info') : img_picto($langs->trans('NotAddedByAuthorityYet'), 'info_black'));
590  }
591  print '</td>';
592 
593  print '<td></td>';
594 
595  print '</tr>';
596  }
597  }
598 
599  if ($nbshown == 0) {
600  print '<tr><td colspan="12"><span class="opacitymedium">'.$langs->trans("NoRecordFound").'</span></td></tr>';
601  }
602 }
603 
604 print '</table>';
605 
606 print '</div>';
607 
608 print '</form>';
609 
610 // Javascript to manage the showinfo popup
611 print '<script type="text/javascript">
612 
613 jQuery(document).ready(function () {
614  jQuery("#dialogforpopup").dialog(
615  { closeOnEscape: true, classes: { "ui-dialog": "highlight" },
616  maxHeight: window.innerHeight-60, height: window.innerHeight-60, width: '.($conf->browser->layout == 'phone' ? 400 : 700).',
617  modal: true,
618  autoOpen: false }).css("z-index: 5000");
619 
620  $("a[rel=show-info]").click(function() {
621 
622  console.log("We click on tooltip, we open popup and get content using an ajax call");
623 
624  var fk_block = $(this).attr("data-blockid");
625 
626  $.ajax({
627  method: "GET",
628  data: { token: \''.currentToken().'\' },
629  url: "'.DOL_URL_ROOT.'/blockedlog/ajax/block-info.php?id="+fk_block,
630  dataType: "html"
631  }).done(function(data) {
632  jQuery("#dialogforpopup").html(data);
633  });
634 
635  jQuery("#dialogforpopup").dialog("open");
636  });
637 })
638 </script>'."\n";
639 
640 
641 if (!empty($conf->global->BLOCKEDLOG_USE_REMOTE_AUTHORITY) && !empty($conf->global->BLOCKEDLOG_AUTHORITY_URL)) {
642  ?>
643  <script type="text/javascript">
644 
645  $.ajax({
646  method: "GET",
647  data: { token: '<?php echo currentToken() ?>' },
648  url: '<?php echo DOL_URL_ROOT.'/blockedlog/ajax/check_signature.php' ?>',
649  dataType: 'html'
650  }).done(function(data) {
651  if(data == 'hashisok') {
652  $('#blockchainstatus').html('<?php echo $langs->trans('AuthorityReconizeFingerprintConformity').' '.img_picto($langs->trans('SignatureOK'), 'on') ?>');
653  }
654  else{
655  $('#blockchainstatus').html('<?php echo $langs->trans('AuthorityDidntReconizeFingerprintConformity').' '.img_picto($langs->trans('SignatureKO'), 'off') ?>');
656  }
657 
658  });
659 
660  </script>
661  <?php
662 }
663 
664 if (GETPOST('withtab', 'alpha')) {
665  print dol_get_fiche_end();
666 }
667 
668 print '<br><br>';
669 
670 // End of page
671 llxFooter();
672 $db->close();
if(GETPOST('button_removefilter_x', 'alpha')||GETPOST('button_removefilter.x', 'alpha')||GETPOST('button_removefilter', 'alpha')) if(GETPOST('button_search_x', 'alpha')||GETPOST('button_search.x', 'alpha')||GETPOST('button_search', 'alpha')) if($action=="save" &&empty($cancel)) $help_url
View.
Definition: agenda.php:118
if(!defined('NOREQUIRESOC')) if(!defined('NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined('NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined('NOREQUIREAJAX')) llxHeader()
Empty header.
Definition: wrapper.php:56
blockedlogadmin_prepare_head()
Define head array for tabs of blockedlog tools setup pages.
Class to manage certif authority.
Class to manage Blocked Log.
Class to manage generation of HTML components Only common components must be here.
if($cancel &&! $id) if($action=='add' &&! $cancel) if($action=='delete') if($id) $form
Actions.
Definition: card.php:143
dol_get_first_day($year, $month=1, $gm=false)
Return GMT time for first day of a month or year.
Definition: date.lib.php:575
dol_time_plus_duree($time, $duration_value, $duration_unit, $ruleforendofmonth=0)
Add a delay to a date.
Definition: date.lib.php:121
dol_get_last_day($year, $month=12, $gm=false)
Return GMT time for last day of a month or year.
Definition: date.lib.php:594
dol_mktime($hour, $minute, $second, $month, $day, $year, $gm='auto', $check=1)
Return a timestamp date built from detailed informations (by default a local PHP server timestamp) Re...
load_fiche_titre($titre, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='')
Load a title with picto.
dol_get_fiche_head($links=array(), $active='', $title='', $notab=0, $picto='', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limittoshow=0, $moretabssuffix='')
Show tabs of a record.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0)
Returns text escaped for inclusion in HTML alt or title tags, or into values of HTML input fields.
dol_print_error($db='', $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
currentToken()
Return the value of token currently saved into session with name 'token'.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='')
Set event messages in dol_events session object.
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_now($mode='auto')
Return date for now.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
getTitleFieldOfList($name, $thead=0, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $disablesortlink=0, $tooltip='', $forcenowrapcolumntitle=0)
Get title line of an array.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
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.
GETPOSTISSET($paramname)
Return true if we are in a context of submitting the parameter $paramname from a POST of a form.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
img_info($titlealt='default')
Show info logo.
restrictedArea(User $user, $features, $object=0, $tableandshare='', $feature2='', $dbt_keyfield='fk_soc', $dbt_select='rowid', $isdraft=0, $mode=0)
Check permissions of a user to show a page and an object.
accessforbidden($message='', $printheader=1, $printfooter=1, $showonlymessage=0, $params=null)
Show a message to say access is forbidden and stop program.