From 9b3b2e600f80823e222ce6e60f4952f5ea1dd848 Mon Sep 17 00:00:00 2001 From: alexis Algoud Date: Thu, 8 Jun 2017 17:52:02 +0200 Subject: [PATCH] init blockedlog trigger and hash store --- htdocs/core/class/blockedlog.class.php | 235 ++++++++++++++++++ ..._modBlockedlog_ActionsBlockedLog.class.php | 78 ++++++ .../install/mysql/migration/5.0.0-6.0.0.sql | 18 ++ 3 files changed, 331 insertions(+) create mode 100644 htdocs/core/class/blockedlog.class.php create mode 100644 htdocs/core/triggers/interface_50_modBlockedlog_ActionsBlockedLog.class.php diff --git a/htdocs/core/class/blockedlog.class.php b/htdocs/core/class/blockedlog.class.php new file mode 100644 index 00000000000..3e622c42dc4 --- /dev/null +++ b/htdocs/core/class/blockedlog.class.php @@ -0,0 +1,235 @@ +db =&$db; + + } + + public function create($user) { + + global $conf,$langs,$hookmanager; + + $langs->load('blockedlog'); + + $error=0; + + dol_syslog(get_class($this).'::create', LOG_DEBUG); + + // Clean parameters + $this->signature = $this->getSignatureRecursive(); + + + if (is_null($this->key_value1)) + { + $this->error=$langs->trans("BlockLogNeedKey1Value"); + dol_syslog($this->error, LOG_WARNING); + return -1; + } + + if(empty($this->element)) { + $this->error=$langs->trans("BlockLogNeedElement"); + dol_syslog($this->error, LOG_WARNING); + return -2; + } + + if(empty($this->action)) { + $this->error=$langs->trans("BlockLogNeedAction"); + dol_syslog($this->error, LOG_WARNING); + return -3; + } + + $this->fk_user = $user->id; + + $this->db->begin(); + + //TODO add fk_user; + + $sql = "INSERT INTO ".MAIN_DB_PREFIX."blockedlog ("; + $sql.= "action,"; + $sql.= " key_value1,"; + $sql.= " signature,"; + $sql.= " element,"; + $sql.= " fk_object,"; + $sql.= " certified,"; + $sql.= " entity"; + $sql.= ") VALUES ("; + $sql.= "'".$this->db->escape($this->action)."',"; + $sql.= "".$this->key_value1.","; + $sql.= "'".$this->db->escape($this->signature)."',"; + $sql.= "'".$this->db->escape($this->element)."',"; + $sql.= "".$this->fk_object.","; + $sql.= "'".($this->certified ? 1 : 0)."',"; + $sql.= $conf->entity; + $sql.= ")"; + + $res = $this->db->query($sql); + if ($res) + { + $id = $this->db->last_insert_id(MAIN_DB_PREFIX."blockedlog"); + + if ($id > 0) + { + $this->id = $id; + + } + else + { + $this->db->rollback(); + return -2; + } + } + else + { + $this->error=$this->db->error(); + $this->db->rollback(); + return -1; + } + + } + + private function crypt($value) { + + return md5($value); + + } + + public function checkSignature() { + + $signature = $this->getSignatureRecursive(); + + return ($signature === $this->signature); + + } + + private function getSignatureRecursive(){ + + $signature = $this->crypt( $this->action . $this->getSignature() . $this->key_value1 ); + + $logs = $this->getLog('payment', 0, 0, 'ASC') ; + if($logs!==false) { + foreach($logs as &$b) { + + if($this->id>0 && $b->id == $this->id) break; // on arrête sur un enregistrement précis pour recalculer une signature + + $b->updateValue(); // on récupère la valeur actuelle en base de l'élément enregistré + + $signature = $this->crypt($signature. $this->action . $b->signature . $b->key_value1); + } + } + return $signature; + + } + + public function getLog($element, $fk_object, $limit = 0, $order = 'DESC') { + global $conf,$cachedlogs ; + + if(empty($cachedlogs)) $cachedlogs=array(); + + + if($element=='payment') { + + $sql="SELECT rowid FROM ".MAIN_DB_PREFIX."blockedlog + WHERE entity=".$conf->entity." AND action LIKE '%PAYMENT%' + ORDER BY tms ".$order; + + } + else if($element=='payments_not_certified') { + $sql="SELECT rowid FROM ".MAIN_DB_PREFIX."blockedlog + WHERE entity=".$conf->entity." AND action LIKE '%PAYMENT%' AND certified = 0 + ORDER BY tms ".$order; + + } + else if($element=='payments_just_certified') { + $sql="SELECT rowid FROM ".MAIN_DB_PREFIX."blockedlog + WHERE entity=".$conf->entity." AND action LIKE '%PAYMENT%' AND certified = 1 + ORDER BY tms ".$order; + + } + else{ + $sql="SELECT rowid FROM ".MAIN_DB_PREFIX."blockedlog + WHERE element='".$element."' AND fk_object=".(int)$fk_object." + ORDER BY tms ".$order; + + } + + + if($limit > 0 )$sql.=' LIMIT '.$limit; + + $res = $this->db->query($sql); + + if($res) { + + $results=array(); + + while($obj = $this->db->fetch_object($res)) { + + if(!isset($cachedlogs[$obj->rowid])) { + $b=new BlockedLog($this->db); + $b->fetch($obj->rowid); + + $cachedlogs[$obj->rowid] = $b; + } + + $results[] = $cachedlogs[$obj->rowid]; + + } + + return $results; + } + else{ + return false; + } + } + + private function updateValue() { + + if($this->action === 'PAYMENT_CUSTOMER_CREATE' + || $this->action === 'PAYMENT_ADD_TO_BANK') { + $sql="SELECT amount FROM ".MAIN_DB_PREFIX."paiement WHERE rowid=".$this->fk_object; + + $res = $this->db->query($sql); + + if($res && $obj = $db->fetch_object($res)) { + $this->key_value1 = (double)$obj->amount; + } + } + + } + + + public function getSignature() { + global $db,$conf,$mysoc; + + if(empty($conf->global->BLOCKEDLOG_ENTITY_FINGERPRINT)) { // creation of a unique fingerprint + + require_once DOL_DOCUMENT_ROOT.'/core/lib/admin.lib.php'; + + $fingerprint = $this->crypt(print_r($mysoc,true).time().rand(0,1000)); + + dolibarr_set_const($db, 'BLOCKEDLOG_ENTITY_FINGERPRINT', $fingerprint, '',0,'Numeric Unique Fingerprint', $conf->entity); + + $conf->global->BLOCKEDLOG_ENTITY_FINGERPRINT= $fingerprint; + } + + return $conf->global->BLOCKEDLOG_ENTITY_FINGERPRINT; + } + +} + diff --git a/htdocs/core/triggers/interface_50_modBlockedlog_ActionsBlockedLog.class.php b/htdocs/core/triggers/interface_50_modBlockedlog_ActionsBlockedLog.class.php new file mode 100644 index 00000000000..3307e4216ea --- /dev/null +++ b/htdocs/core/triggers/interface_50_modBlockedlog_ActionsBlockedLog.class.php @@ -0,0 +1,78 @@ + + * Copyright (C) 2009-2011 Regis Houssin + * Copyright (C) 2011-2014 Juanjo Menent + * Copyright (C) 2013 Cedric GROSS + * Copyright (C) 2014 Marcos García + * Copyright (C) 2015 Bahfir Abbes + * + * 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 . + */ + +/** + * \file htdocs/core/triggers/interface_50_modAgenda_ActionsAuto.class.php + * \ingroup agenda + * \brief Trigger file for agenda module + */ + +require_once DOL_DOCUMENT_ROOT.'/core/triggers/dolibarrtriggers.class.php'; +require_once DOL_DOCUMENT_ROOT.'/core/class/blockedlog.class.php'; + +/** + * Class of triggered functions for agenda module + */ +class InterfaceActionsBlockedLog extends DolibarrTriggers +{ + public $family = 'system'; + public $description = "Triggers of this module add blocklog."; + public $version = self::VERSION_DOLIBARR; + public $picto = 'system'; + + /** + * Function called on Dolibarrr payment or invoice event. + * + * @param string $action Event action code + * @param Object $object Object + * @param User $user Object user + * @param Translate $langs Object langs + * @param conf $conf Object conf + * @return int <0 if KO, 0 if no triggered ran, >0 if OK + */ + public function runTrigger($action, $object, User $user, Translate $langs, Conf $conf) + { + // Do not log events not enabled for this action + if (empty($conf->blockedlog->enabled)) { + return 0; + } + + $b=new BlockedLog($this->db); + $b->element = $object->element; + $b->action = $action; + $b->fk_object = $object->id; + $b->key_value1 = 0; + + $res = $b->create($user); + if($res<0) { + setEventMessage($b->error,'errors'); + + return -1; + } + else { + return 1; + } + + + } + +} diff --git a/htdocs/install/mysql/migration/5.0.0-6.0.0.sql b/htdocs/install/mysql/migration/5.0.0-6.0.0.sql index 85b9d3106cf..786becac0ba 100644 --- a/htdocs/install/mysql/migration/5.0.0-6.0.0.sql +++ b/htdocs/install/mysql/migration/5.0.0-6.0.0.sql @@ -395,3 +395,21 @@ ALTER TABLE llx_usergroup_rights DROP INDEX fk_usergroup; ALTER TABLE llx_usergroup_rights ADD UNIQUE INDEX uk_usergroup_rights (entity, fk_usergroup, fk_id); ALTER TABLE llx_usergroup_rights ADD CONSTRAINT fk_usergroup_rights_fk_usergroup FOREIGN KEY (fk_usergroup) REFERENCES llx_usergroup (rowid); +CREATE TABLE llx_blockedlog +( + rowid integer AUTO_INCREMENT, + tms timestamp, + action varchar(50), + key_value1 real NOT NULL, + signature varchar(32) NOT NULL, + element varchar(50), + fk_object integer, + entity integer, + certified integer, + PRIMARY KEY (rowid), + KEY signature (signature), + KEY fk_object_element (fk_object,element), + KEY entity (entity), + KEY entity_action (entity,action), + KEY entity_action_certified (entity,action,certified) +)