diff --git a/htdocs/blockedlog/class/blockedlog.class.php b/htdocs/blockedlog/class/blockedlog.class.php index 46820f95ea37a..ef209ae6b8549 100644 --- a/htdocs/blockedlog/class/blockedlog.class.php +++ b/htdocs/blockedlog/class/blockedlog.class.php @@ -1088,23 +1088,47 @@ public function getPreviousHash($withlock = 0, $beforeid = 0) $previoussignature = ''; - $sql = "SELECT rowid, signature FROM ".MAIN_DB_PREFIX."blockedlog"; - $sql .= " WHERE entity = ".((int) $conf->entity); + // Fast search of previous record by searching with beforeid - 1. This is very fast and will work 99% of time. if ($beforeid) { - $sql .= " AND rowid < ".(int) $beforeid; + $sql = "SELECT rowid, signature FROM ".MAIN_DB_PREFIX."blockedlog"; + $sql .= " WHERE entity = ".((int) $conf->entity); + $sql .= " AND rowid = ".((int) $beforeid - 1); + $sql .= ($withlock ? " FOR UPDATE " : ""); + + $resql = $this->db->query($sql); + if ($resql) { + $obj = $this->db->fetch_object($resql); + if ($obj) { + $previoussignature = $obj->signature; + } + } else { + dol_print_error($this->db); + exit; + } } - $sql .= " ORDER BY rowid DESC LIMIT 1"; - $sql .= ($withlock ? " FOR UPDATE " : ""); - $resql = $this->db->query($sql); - if ($resql) { - $obj = $this->db->fetch_object($resql); - if ($obj) { - $previoussignature = $obj->signature; + if (empty($previoussignature)) { + $sql = "SELECT rowid, signature FROM ".MAIN_DB_PREFIX."blockedlog"; + if ($beforeid) { + $sql.= $this->db->hintindex('entity_rowid', 1); + } + $sql .= " WHERE entity = ".((int) $conf->entity); + if ($beforeid) { + $sql .= " AND rowid < ".(int) $beforeid; + } + $sql .= " ORDER BY rowid DESC LIMIT 1"; + $sql .= ($withlock ? " FOR UPDATE " : ""); + + $resql = $this->db->query($sql); + if ($resql) { + $obj = $this->db->fetch_object($resql); + if ($obj) { + $previoussignature = $obj->signature; + } + } else { + dol_print_error($this->db); + exit; } - } else { - dol_print_error($this->db); - exit; } if (empty($previoussignature)) { diff --git a/htdocs/core/db/DoliDB.class.php b/htdocs/core/db/DoliDB.class.php index a73b664965445..1a898e9c61800 100644 --- a/htdocs/core/db/DoliDB.class.php +++ b/htdocs/core/db/DoliDB.class.php @@ -122,9 +122,10 @@ public function stddevpop($nameoffield) * Return SQL string to force an index * * @param string $nameofindex Name of index + * @param int $mode 0=Use, 1=Force * @return string SQL string */ - public function hintindex($nameofindex) + public function hintindex($nameofindex, $mode = 1) { return ''; } diff --git a/htdocs/core/db/mysqli.class.php b/htdocs/core/db/mysqli.class.php index 7a20d8027a6f7..6fd6a86061c77 100644 --- a/htdocs/core/db/mysqli.class.php +++ b/htdocs/core/db/mysqli.class.php @@ -200,11 +200,12 @@ public function __construct($type, $host, $user, $pass, $name = '', $port = 0) * Return SQL string to force an index * * @param string $nameofindex Name of index + * @param int $mode 0=Use, 1=Force * @return string SQL string */ - public function hintindex($nameofindex) + public function hintindex($nameofindex, $mode = 1) { - return " FORCE INDEX(".preg_replace('/[^a-z0-9_]/', '', $nameofindex).")"; + return " ".($mode == 1 ? 'FORCE' : 'USE')." INDEX(".preg_replace('/[^a-z0-9_]/', '', $nameofindex).")"; } diff --git a/htdocs/install/mysql/migration/20.0.0-21.0.0.sql b/htdocs/install/mysql/migration/20.0.0-21.0.0.sql index d4d36ba7da46e..5281bc760f1a1 100644 --- a/htdocs/install/mysql/migration/20.0.0-21.0.0.sql +++ b/htdocs/install/mysql/migration/20.0.0-21.0.0.sql @@ -51,6 +51,9 @@ ALTER TABLE llx_hrm_evaluation MODIFY COLUMN modelpdf varchar(255) DEFAULT NULL; -- V21 migration +ALTER TABLE llx_blockedlog DROP INDEX entity_action; +ALTER TABLE llx_blockedlog ADD INDEX entity_rowid (entity, rowid); + ALTER TABLE llx_ecm_files MODIFY COLUMN description varchar(255); ALTER TABLE llx_ecm_files MODIFY COLUMN cover varchar(32); ALTER TABLE llx_ecm_files ADD COLUMN content text; diff --git a/htdocs/install/mysql/tables/llx_blockedlog.key.sql b/htdocs/install/mysql/tables/llx_blockedlog.key.sql index 4312a056894a4..065be82aba1a9 100644 --- a/htdocs/install/mysql/tables/llx_blockedlog.key.sql +++ b/htdocs/install/mysql/tables/llx_blockedlog.key.sql @@ -1,6 +1,25 @@ +-- =================================================================== +-- Copyright (C) 2024 Laurent Destailleur +-- +-- This program is free software; you can redistribute it and/or modify +-- it under the terms of the GNU General Public License as published by +-- the Free Software Foundation; either version 3 of the License, or +-- (at your option) any later version. +-- +-- This program is distributed in the hope that it will be useful, +-- but WITHOUT ANY WARRANTY; without even the implied warranty of +-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +-- GNU General Public License for more details. +-- +-- You should have received a copy of the GNU General Public License +-- along with this program. If not, see . +-- +-- =================================================================== + ALTER TABLE llx_blockedlog ADD INDEX signature (signature); ALTER TABLE llx_blockedlog ADD INDEX fk_object_element (fk_object,element); ALTER TABLE llx_blockedlog ADD INDEX entity (entity); -ALTER TABLE llx_blockedlog ADD INDEX fk_user (fk_user); -ALTER TABLE llx_blockedlog ADD INDEX entity_action (entity,action); +ALTER TABLE llx_blockedlog ADD INDEX fk_user (fk_user); ALTER TABLE llx_blockedlog ADD INDEX entity_action_certified (entity,action,certified); + +ALTER TABLE llx_blockedlog ADD INDEX entity_rowid (entity, rowid); -- for the "SELECT rowid, signature FROM llx_blockedlog FORCE INDEX entity_rowid WHERE entity = x AND rowid < z ORDER BY rowid DESC"