From 1059befa3995861f461b9eea47be3d18aee4ed9c Mon Sep 17 00:00:00 2001 From: acognet Date: Mon, 21 Jun 2021 16:34:40 +0200 Subject: [PATCH 1/8] =?UTF-8?q?N=C2=B04020=20-=20timeout=20on=20updating?= =?UTF-8?q?=20the=20hierarchical=20key=20during=20setup?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 1 + setup/compiler.class.inc.php | 24 +++++++++++++++++++++++- setup/runtimeenv.class.inc.php | 15 ++++++++++----- 3 files changed, 34 insertions(+), 6 deletions(-) diff --git a/.gitignore b/.gitignore index 92eb71a34..9b6fde01a 100644 --- a/.gitignore +++ b/.gitignore @@ -26,6 +26,7 @@ test/vendor/* !/data/.htaccess !/data/index.php !/data/web.config +!/data/.setup-rebuild-hkeys-never # iTop extensions /extensions/** diff --git a/setup/compiler.class.inc.php b/setup/compiler.class.inc.php index f541058f2..f52da6348 100644 --- a/setup/compiler.class.inc.php +++ b/setup/compiler.class.inc.php @@ -51,6 +51,14 @@ class DOMFormatException extends Exception */ class MFCompiler { + /** + * Path to the "calculate hKeys" file + * If this file is present, then we don't recalculate hkeys + * + * @var string + */ + public const REBUILD_HKEYS_NEVER= APPROOT.'data/.setup-rebuild-hkeys-never'; + /** @var \ModelFactory */ protected $oFactory; @@ -96,7 +104,21 @@ class MFCompiler { return $this->aLog; } - + + /** + * @return bool possible return values : + * * if flag is present true, false otherwise + * + * @uses \file_exists() + * @uses REBUILD_HKEYS_NEVER + * + * @since 2.7.5 + */ + public static function SkipRebuildHKeys(): bool + { + return (file_exists(static::REBUILD_HKEYS_NEVER)); + } + /** * Compile the data model into PHP files and data structures diff --git a/setup/runtimeenv.class.inc.php b/setup/runtimeenv.class.inc.php index a222fd98f..0c1602bd5 100644 --- a/setup/runtimeenv.class.inc.php +++ b/setup/runtimeenv.class.inc.php @@ -599,11 +599,16 @@ class RunTimeEnvironment $this->log_ok("Database structure successfully updated."); // Check (and update only if it seems needed) the hierarchical keys - ob_start(); - MetaModel::CheckHKeys(false /* bDiagnosticsOnly */, true /* bVerbose*/, true /* bForceUpdate */); // Since in 1.2-beta the detection was buggy, let's force the rebuilding of HKeys - $sFeedback = ob_get_clean(); - $this->log_ok("Hierchical keys rebuilt: $sFeedback"); - + if (MFCompiler::SkipRebuildHKeys()) { + $this->log_ok("Hierchical keys are NOT rebuilt due to the presence of the \"data/.setup-rebuild-hkeys-never\" file"); + } else { + ob_start(); + $this->log_ok("Start of rebuilt of hierchical keys. If you have problems with this step, you can skip it by creating a \".setup-rebuild-hkeys-never\" file in data"); + MetaModel::CheckHKeys(false /* bDiagnosticsOnly */, true /* bVerbose*/, true /* bForceUpdate */); // Since in 1.2-beta the detection was buggy, let's force the rebuilding of HKeys + $sFeedback = ob_get_clean(); + $this->log_ok("Hierchical keys rebuilt: $sFeedback"); + } + // Check (and fix) data sync configuration ob_start(); MetaModel::CheckDataSources(false /*$bDiagnostics*/, true/*$bVerbose*/); From 58e315d7f6b03e81fcdb11943b7ac10eebef268a Mon Sep 17 00:00:00 2001 From: acognet Date: Mon, 21 Jun 2021 17:16:08 +0200 Subject: [PATCH 2/8] =?UTF-8?q?N=C2=B04020=20-=20timeout=20on=20updating?= =?UTF-8?q?=20the=20hierarchical=20key=20during=20setup=20-=20fix=20git=20?= =?UTF-8?q?ignore?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 1 - 1 file changed, 1 deletion(-) diff --git a/.gitignore b/.gitignore index 9b6fde01a..92eb71a34 100644 --- a/.gitignore +++ b/.gitignore @@ -26,7 +26,6 @@ test/vendor/* !/data/.htaccess !/data/index.php !/data/web.config -!/data/.setup-rebuild-hkeys-never # iTop extensions /extensions/** From b1ca1f2630ef919024ea630e57d9d4a8a3406aea Mon Sep 17 00:00:00 2001 From: Eric Date: Tue, 22 Jun 2021 14:29:10 +0200 Subject: [PATCH 3/8] =?UTF-8?q?N=C2=B03513=20-=20ObjectFormManager=20:=20r?= =?UTF-8?q?emove=20transaction=20*=20Add=20automatic=20tests=20*=20Fix=20o?= =?UTF-8?q?bject=20consistency?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- core/cmdbsource.class.inc.php | 34 ++- core/dbobject.class.php | 17 +- test/core/{ => CMDBSource}/CMDBSourceTest.php | 5 - test/core/CMDBSource/DeadLockInjection.php | 63 +++++ test/core/CMDBSource/TransactionsTest.php | 247 ++++++++++++++++++ 5 files changed, 344 insertions(+), 22 deletions(-) rename test/core/{ => CMDBSource}/CMDBSourceTest.php (93%) create mode 100644 test/core/CMDBSource/DeadLockInjection.php create mode 100644 test/core/CMDBSource/TransactionsTest.php diff --git a/core/cmdbsource.class.inc.php b/core/cmdbsource.class.inc.php index 8b6cd837a..e1b4a1d79 100644 --- a/core/cmdbsource.class.inc.php +++ b/core/cmdbsource.class.inc.php @@ -154,6 +154,7 @@ class CMDBSource /** @var mysqli $m_oMysqli */ protected static $m_oMysqli; + protected static $oMySQLiForQuery; /** * @var int number of level for nested transactions : 0 if no transaction was ever opened, +1 for each 'START TRANSACTION' sent @@ -220,6 +221,7 @@ class CMDBSource self::$m_sDBTlsCA = empty($sTlsCA) ? null : $sTlsCA; self::$m_oMysqli = self::GetMysqliInstance($sServer, $sUser, $sPwd, $sSource, $bTlsEnabled, $sTlsCA, true); + self::SetMySQLiForQuery(self::$m_oMysqli); } /** @@ -237,8 +239,6 @@ class CMDBSource public static function GetMysqliInstance( $sDbHost, $sUser, $sPwd, $sSource = '', $bTlsEnabled = false, $sTlsCa = null, $bCheckTlsAfterConnection = false ) { - $oMysqli = null; - $sServer = null; $iPort = null; self::InitServerAndPort($sDbHost, $sServer, $iPort); @@ -536,6 +536,24 @@ class CMDBSource return self::$m_oMysqli; } + /** + * @return + */ + private static function GetMySQLiForQuery() + { + return self::$oMySQLiForQuery; + } + + + /** + * Used for test purpose (mysqli mock) + * @param $oMySQLi + */ + private static function SetMySQLiForQuery($oMySQLi) + { + self::$oMySQLiForQuery = $oMySQLi; + } + public static function GetErrNo() { if (self::$m_oMysqli->errno != 0) @@ -671,7 +689,7 @@ class CMDBSource */ private static function DBQuery($sSql) { - $sShortSQL = str_replace("\n", " ", substr($sSql, 0, 120)); + $sShortSQL = substr(preg_replace("/\s+/", " ", substr($sSql, 0, 180)), 0, 150); if (substr_compare($sShortSQL, "SELECT", 0, strlen("SELECT")) !== 0) { IssueLog::Trace("$sShortSQL", 'cmdbsource'); } @@ -679,7 +697,7 @@ class CMDBSource $oKPI = new ExecutionKPI(); try { - $oResult = self::$m_oMysqli->query($sSql); + $oResult = self::GetMySQLiForQuery()->query($sSql); } catch (mysqli_sql_exception $e) { @@ -959,7 +977,7 @@ class CMDBSource $oKPI = new ExecutionKPI(); try { - $oResult = self::$m_oMysqli->query($sSql); + $oResult = self::GetMySQLiForQuery()->query($sSql); } catch(mysqli_sql_exception $e) { @@ -999,7 +1017,7 @@ class CMDBSource $oKPI = new ExecutionKPI(); try { - $oResult = self::$m_oMysqli->query($sSql); + $oResult = self::GetMySQLiForQuery()->query($sSql); } catch(mysqli_sql_exception $e) { @@ -1081,7 +1099,7 @@ class CMDBSource { try { - $oResult = self::$m_oMysqli->query($sSql); + $oResult = self::GetMySQLiForQuery()->query($sSql); } catch(mysqli_sql_exception $e) { @@ -1568,7 +1586,7 @@ class CMDBSource $sSql = "SELECT * FROM `$sTable`"; try { - $oResult = self::$m_oMysqli->query($sSql); + $oResult = self::GetMySQLiForQuery()->query($sSql); } catch(mysqli_sql_exception $e) { diff --git a/core/dbobject.class.php b/core/dbobject.class.php index 6a4d23193..63914e0f7 100644 --- a/core/dbobject.class.php +++ b/core/dbobject.class.php @@ -2776,6 +2776,7 @@ abstract class DBObject implements iDisplay $this->DBWriteLinks(); $this->WriteExternalAttributes(); + $this->RecordObjCreation(); if ($bIsTransactionEnabled) { CMDBSource::Query('COMMIT'); @@ -2837,8 +2838,6 @@ abstract class DBObject implements iDisplay } } - $this->RecordObjCreation(); - return $this->m_iKey; } @@ -3250,13 +3249,6 @@ abstract class DBObject implements iDisplay $this->DBWriteLinks(); $this->WriteExternalAttributes(); - // following lines are resetting changes (so after this {@see DBObject::ListChanges()} won't return changes anymore) - // new values are already in the object (call {@see DBObject::Get()} to get them) - // call {@see DBObject::ListPreviousValuesForUpdatedAttributes()} to get changed fields and previous values - $this->m_bDirty = false; - $this->m_aTouchedAtt = array(); - $this->m_aModifiedAtt = array(); - if (count($aChanges) != 0) { $this->RecordAttChanges($aChanges, $aOriginalValues); @@ -3322,6 +3314,13 @@ abstract class DBObject implements iDisplay } } + // following lines are resetting changes (so after this {@see DBObject::ListChanges()} won't return changes anymore) + // new values are already in the object (call {@see DBObject::Get()} to get them) + // call {@see DBObject::ListPreviousValuesForUpdatedAttributes()} to get changed fields and previous values + $this->m_bDirty = false; + $this->m_aTouchedAtt = array(); + $this->m_aModifiedAtt = array(); + try { $this->AfterUpdate(); diff --git a/test/core/CMDBSourceTest.php b/test/core/CMDBSource/CMDBSourceTest.php similarity index 93% rename from test/core/CMDBSourceTest.php rename to test/core/CMDBSource/CMDBSourceTest.php index 229db18b5..a787c0316 100644 --- a/test/core/CMDBSourceTest.php +++ b/test/core/CMDBSource/CMDBSourceTest.php @@ -113,11 +113,6 @@ class CMDBSourceTest extends ItopTestCase "ENUM('value 1 (with parenthesis)','value 2') CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci", "enum('value 1 (with parenthesis)','value 3') CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci", ), - 'ENUM with different values, containing parenthesis' => array( - false, - "ENUM('value 1 ) with parenthesis)','value 2') CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci", - "enum('value 1 (with parenthesis)','value 3') CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci", - ), ); } } diff --git a/test/core/CMDBSource/DeadLockInjection.php b/test/core/CMDBSource/DeadLockInjection.php new file mode 100644 index 000000000..12aa2e4c6 --- /dev/null +++ b/test/core/CMDBSource/DeadLockInjection.php @@ -0,0 +1,63 @@ +bMustFail = true; + $this->iRequestCount = 0; + $this->iFailAt = $iFailAt; + $this->bShowRequest = true; + } + + /** + * @param bool $bShowRequest + */ + public function SetShowRequest($bShowRequest) + { + $this->bShowRequest = $bShowRequest; + } + + + public function query($sSQL) + { + if (utils::StartsWith($sSQL, "SELECT")) { + return; + } + if ($this->bShowRequest) { + $sShortSQL = substr(preg_replace("/\s+/", " ", substr($sSQL, 0, 180)), 0, 150); + echo "$sShortSQL\n"; + } + if (CMDBSource::IsInsideTransaction() && $this->bMustFail) { + $this->iRequestCount++; + if ($this->iRequestCount == $this->iFailAt) { + echo "Generating a FAKE DEADLOCK\n"; + IssueLog::Trace("Generating a FAKE DEADLOCK", 'cmdbsource'); + throw new MySQLException("FAKE DEADLOCK", [], new Exception("FAKE DEADLOCK", 1213)); + } + } + } +} \ No newline at end of file diff --git a/test/core/CMDBSource/TransactionsTest.php b/test/core/CMDBSource/TransactionsTest.php new file mode 100644 index 000000000..82594e578 --- /dev/null +++ b/test/core/CMDBSource/TransactionsTest.php @@ -0,0 +1,247 @@ +oMySQLiMock = new DeadLockInjection(); + + $oMockMysqli = $this->getMockBuilder('mysqli') + ->setMethods(['query']) + ->getMock(); + $oMockMysqli->expects($this->any()) + ->method('query') + ->will($this->returnCallback( + function ($sSql) use ($oInitialMysqli) { + $this->oMySQLiMock->query($sSql); + return $oInitialMysqli->query($sSql); + } + )); + + $this->InvokeNonPublicStaticMethod('CMDBSource', 'SetMySQLiForQuery', [$oMockMysqli]); + } + + /** + * Test DBInsertNoReload database transaction by provoking deadlock exceptions + * + * @dataProvider DBInsertProvider + * + * @param int $iFailAt Specify the request occurrence that fails + * @param bool $bIsInDB Indicates if the object must have been created or not + * + * @throws \ArchivedObjectException + * @throws \CoreCannotSaveObjectException + * @throws \CoreException + * @throws \CoreUnexpectedValue + * @throws \DeleteException + * @throws \MySQLException + * @throws \MySQLHasGoneAwayException + * @throws \OQLException + */ + public function testDBInsert($iFailAt, $bIsInDB) + { + // Create a UserRequest with 2 contacts + $oTicket = MetaModel::NewObject('UserRequest', [ + 'ref' => 'Test Ticket', + 'title' => 'Create OK', + 'description' => 'Create OK', + 'caller_id' => 15, + 'org_id' => 3, + ]); + $oLinkSet = $oTicket->Get('contacts_list'); + $oLinkSet->AddItem(MetaModel::NewObject('lnkContactToTicket', ['contact_id' => 6])); + $oLinkSet->AddItem(MetaModel::NewObject('lnkContactToTicket', ['contact_id' => 7])); + + $this->oMySQLiMock->SetFailAt($iFailAt); + $this->debug("---> DBInsert()"); + try { + $oTicket->DBWrite(); + } + catch (Exception $e) { + // If an exception occurs must be a deadlock + $this->assertTrue(CMDBSource::IsDeadlockException($e), $e->getMessage()); + } + + // Verify if the ticket is considered as saved in the database + $this->assertEquals($bIsInDB, !$oTicket->IsNew()); + + if (!$oTicket->IsNew()) { + $this->oMySQLiMock->SetShowRequest(false); + // Delete created objects + $oTicket->DBDelete(); + } + } + + public function DBInsertProvider() + { + return [ + "Normal case" => ['iFailAt' => -1, 'bIsInDB' => true], + "ticket" => ['iFailAt' => 1, 'bIsInDB' => false], + "ticket_request" => ['iFailAt' => 2, 'bIsInDB' => false], + "priv_change" => ['iFailAt' => 3, 'bIsInDB' => false], + "priv_changeop" => ['iFailAt' => 4, 'bIsInDB' => false], + "priv_changeop_create" => ['iFailAt' => 5, 'bIsInDB' => false], + "History 4" => ['iFailAt' => 6, 'bIsInDB' => false], + "History 5" => ['iFailAt' => 7, 'bIsInDB' => false], + "History 6" => ['iFailAt' => 8, 'bIsInDB' => false], + "History 7" => ['iFailAt' => 9, 'bIsInDB' => false], + "History 8" => ['iFailAt' => 10, 'bIsInDB' => false], + "History 9" => ['iFailAt' => 11, 'bIsInDB' => false], + "History 10" => ['iFailAt' => 12, 'bIsInDB' => false], + "History 11" => ['iFailAt' => 13, 'bIsInDB' => false], + "History 12" => ['iFailAt' => 14, 'bIsInDB' => false], + "History 13" => ['iFailAt' => 15, 'bIsInDB' => false], + "History 14" => ['iFailAt' => 16, 'bIsInDB' => false], + "History 15" => ['iFailAt' => 17, 'bIsInDB' => false], + "History 16" => ['iFailAt' => 18, 'bIsInDB' => false], + "History 17" => ['iFailAt' => 19, 'bIsInDB' => false], + "History 18" => ['iFailAt' => 20, 'bIsInDB' => false], + "History 19" => ['iFailAt' => 21, 'bIsInDB' => false], + "History 20" => ['iFailAt' => 22, 'bIsInDB' => false], + "History 21" => ['iFailAt' => 23, 'bIsInDB' => false], + "History 22" => ['iFailAt' => 24, 'bIsInDB' => false], + "History 23" => ['iFailAt' => 25, 'bIsInDB' => false], + "History 24" => ['iFailAt' => 26, 'bIsInDB' => false], + "History 25" => ['iFailAt' => 27, 'bIsInDB' => false], + "History 26" => ['iFailAt' => 28, 'bIsInDB' => false], + "History 27" => ['iFailAt' => 29, 'bIsInDB' => false], + "History 28" => ['iFailAt' => 30, 'bIsInDB' => false], + "History 29" => ['iFailAt' => 31, 'bIsInDB' => false], + "History 30" => ['iFailAt' => 32, 'bIsInDB' => false], + "History 31" => ['iFailAt' => 33, 'bIsInDB' => false], + "History 32" => ['iFailAt' => 34, 'bIsInDB' => false], + "History 33" => ['iFailAt' => 35, 'bIsInDB' => false], + "History 34" => ['iFailAt' => 36, 'bIsInDB' => false], + "History 35" => ['iFailAt' => 37, 'bIsInDB' => false], + "History 36" => ['iFailAt' => 38, 'bIsInDB' => false], + "History 37" => ['iFailAt' => 39, 'bIsInDB' => false], + "History 38" => ['iFailAt' => 40, 'bIsInDB' => false], + ]; + } + + /** + * Test DBUpdate database transaction by provoking deadlock exceptions + * + * @dataProvider DBUpdateProvider + * @param $iFailAt + * + * @throws \ArchivedObjectException + * @throws \CoreCannotSaveObjectException + * @throws \CoreException + * @throws \CoreUnexpectedValue + * @throws \DeleteException + * @throws \MySQLException + * @throws \MySQLHasGoneAwayException + * @throws \OQLException + */ + public function testDBUpdate($iFailAt, $bIsModified) + { + // Create a UserRequest into the database with 2 contacts + $oTicket = MetaModel::NewObject('UserRequest', [ + 'ref' => 'Test Ticket', + 'title' => 'Create OK', + 'description' => 'Create OK', + 'solution' => 'Create OK', + 'caller_id' => 15, + 'org_id' => 3, + ]); + $oLinkSet = $oTicket->Get('contacts_list'); + $oLinkSet->AddItem(MetaModel::NewObject('lnkContactToTicket', ['contact_id' => 6])); + $oLinkSet->AddItem(MetaModel::NewObject('lnkContactToTicket', ['contact_id' => 7])); + //$oTicket->Set('contacts_list', $oLinkSet); + + $this->oMySQLiMock->SetShowRequest(false); + $oTicket->DBWrite(); + + // Verify that the object is considered as saved in the database + $this->assertEquals(true, !$oTicket->IsNew()); + + // Reload from db + $oTicket = MetaModel::GetObject('UserRequest', $oTicket->GetKey()); + $oTicket->Set('description', 'Update OK'); + $oTicket->Set('solution', 'Test OK'); + $oLinkSet = $oTicket->Get('contacts_list'); + $oLinkSet->AddItem(MetaModel::NewObject('lnkContactToTicket', ['contact_id' => 8])); + $oTicket->Set('contacts_list', $oLinkSet); + + // Provoke an error during the update + $this->oMySQLiMock->SetFailAt($iFailAt); + $this->debug("---> DBUpdate()"); + try { + $oTicket->DBWrite(); + } + catch (Exception $e) { + // If an exception occurs must be a deadlock + $this->assertTrue(CMDBSource::IsDeadlockException($e)); + } + + // Verify if the ticket is considered as saved in the database + $this->assertEquals($bIsModified, $oTicket->IsModified()); + + // Reload from db after the update to check the value present in the database + $oTicket = MetaModel::GetObject('UserRequest', $oTicket->GetKey()); + if ($bIsModified) { + $this->assertEquals('Create OK', $oTicket->Get('solution')); + } else { + $this->assertEquals('Test OK', $oTicket->Get('solution')); + } + + if (!$oTicket->IsNew()) { + $this->oMySQLiMock->SetShowRequest(false); + // Delete created objects + $oTicket->DBDelete(); + } + } + + public function DBUpdateProvider() + { + return [ + "Normal case" => ['iFailAt' => -1, 'bIsModified' => false], + "ticket_request" => ['iFailAt' => 1, 'bIsModified' => true], + "lnkcontacttoticket" => ['iFailAt' => 2, 'bIsModified' => true], + "History 1" => ['iFailAt' => 3, 'bIsModified' => true], + "History 2" => ['iFailAt' => 4, 'bIsModified' => true], + "History 3" => ['iFailAt' => 5, 'bIsModified' => true], + "History 4" => ['iFailAt' => 6, 'bIsModified' => true], + "History 5" => ['iFailAt' => 7, 'bIsModified' => true], + "History 6" => ['iFailAt' => 8, 'bIsModified' => true], + "History 7" => ['iFailAt' => 9, 'bIsModified' => true], + "History 8" => ['iFailAt' => 10, 'bIsModified' => true], + "History 9" => ['iFailAt' => 11, 'bIsModified' => true], + "History 10" => ['iFailAt' => 12, 'bIsModified' => true], + "History 11" => ['iFailAt' => 13, 'bIsModified' => true], + "History 12" => ['iFailAt' => 14, 'bIsModified' => true], + "History 13" => ['iFailAt' => 15, 'bIsModified' => true], + ]; + } +} \ No newline at end of file From 5d994edd62724ce830d0f29a5fa147b9f008e9a0 Mon Sep 17 00:00:00 2001 From: Pierre Goiffon Date: Wed, 23 Jun 2021 17:26:34 +0200 Subject: [PATCH 4/8] =?UTF-8?q?N=C2=B04012=20Fix=20debug=20trace=20syntax?= =?UTF-8?q?=20Thanks=20@Molkobain=20!?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../portal/src/Controller/BrowseBrickController.php | 4 ++-- .../portal/src/Controller/ManageBrickController.php | 6 +++--- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php b/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php index 79b62448f..c7776c65a 100644 --- a/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php +++ b/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php @@ -442,8 +442,8 @@ class BrowseBrickController extends BrickController } IssueLog::Debug('Portal BrowseBrick query', 'portal', array( - 'portalId' => $sPortalId, - 'brickId' => $sBrickId, + 'sPortalId' => $sPortalId, + 'sBrickId' => $sBrickId, 'oql' => $oSet->GetFilter()->ToOQL(), )); diff --git a/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php b/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php index 5f1468651..7223abf49 100644 --- a/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php +++ b/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php @@ -815,9 +815,9 @@ class ManageBrickController extends BrickController } IssueLog::Debug('Portal ManageBrick query', 'portal', array( - 'portalId' => $sPortalId, - 'brickId' => $sBrickId, - 'groupingTab' => $sGroupingTab, + 'sPortalId' => $sPortalId, + 'sBrickId' => $sBrickId, + 'sGroupingTab' => $sGroupingTab, 'oql' => $oSet->GetFilter()->ToOQL(), 'aGroupingTabs' => $aGroupingTabs, )); From a940adc4ba459add8f0a9fd6645a09b3ea1af01a Mon Sep 17 00:00:00 2001 From: acognet Date: Thu, 24 Jun 2021 10:34:09 +0200 Subject: [PATCH 5/8] =?UTF-8?q?N=C2=B03678=20-=20Portal=20:=20a=20modifica?= =?UTF-8?q?tion=20of=20field=20cannot=20hide=20another=20one?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../portal/src/Form/ObjectFormManager.php | 26 +++++++++++++++++++ .../src/Helper/ObjectFormHandlerHelper.php | 5 ++-- js/form_handler.js | 9 ++++++- 3 files changed, 37 insertions(+), 3 deletions(-) diff --git a/datamodels/2.x/itop-portal-base/portal/src/Form/ObjectFormManager.php b/datamodels/2.x/itop-portal-base/portal/src/Form/ObjectFormManager.php index 0944c0bbd..3fac09f48 100644 --- a/datamodels/2.x/itop-portal-base/portal/src/Form/ObjectFormManager.php +++ b/datamodels/2.x/itop-portal-base/portal/src/Form/ObjectFormManager.php @@ -78,6 +78,12 @@ class ObjectFormManager extends FormManager protected $aFormProperties; /** @var array $aCallbackUrls */ protected $aCallbackUrls = array(); + /** + * List of hidden fields, used for form update (eg. remove them from the form regarding they dependencies) + * @var array $aHiddenFieldsId + * @since 2.7.5 + */ + protected $aHiddenFieldsId = array(); /** * Creates an instance of \Combodo\iTop\Portal\Form\ObjectFormManager from JSON data that must contain at least : @@ -941,6 +947,8 @@ class ObjectFormManager extends FormManager if($oField->GetHidden() === false) { $oForm->AddField($oField); + } else { + $this->aHiddenFieldsId[]=$oField->GetId(); } } @@ -1472,4 +1480,22 @@ class ObjectFormManager extends FormManager } return $oChangeOp; } + + /** + * @return array + * @since 2.7.5 + */ + public function GetHiddenFieldsId() + { + return $this->aHiddenFieldsId; + } + + /** + * @param array $aHiddenFieldsId + * @since 2.7.5 + */ + public function SetHiddenFieldsId($aHiddenFieldsId) + { + $this->aHiddenFieldsId = $aHiddenFieldsId; + } } diff --git a/datamodels/2.x/itop-portal-base/portal/src/Helper/ObjectFormHandlerHelper.php b/datamodels/2.x/itop-portal-base/portal/src/Helper/ObjectFormHandlerHelper.php index 62231c95f..d114b1b05 100644 --- a/datamodels/2.x/itop-portal-base/portal/src/Helper/ObjectFormHandlerHelper.php +++ b/datamodels/2.x/itop-portal-base/portal/src/Helper/ObjectFormHandlerHelper.php @@ -280,8 +280,8 @@ class ObjectFormHandlerHelper ->SetFormProperties($aFormProperties); $oFormManager->Build(); - - // Check the number of editable fields + $aFormData['hidden_fields'] = $oFormManager->GetHiddenFieldsId(); + // Check the number of editable fields $aFormData['editable_fields_count'] = $oFormManager->GetForm()->GetEditableFieldCount(); } else @@ -388,6 +388,7 @@ class ObjectFormHandlerHelper $aFormData['object_state'] = $oFormManager->GetObject()->GetState(); $aFormData['fieldset'] = $aFieldSetData; $aFormData['display_mode'] = (isset($aFormProperties['properties'])) ? $aFormProperties['properties']['display_mode'] : ApplicationHelper::FORM_DEFAULT_DISPLAY_MODE; + $aFormData['hidden_fields'] = $oFormManager->GetHiddenFieldsId(); // - Set a text to be copied on title if the object is not in creation if($sMode !== static::ENUM_MODE_CREATE && !empty($sObjectId)) { diff --git a/js/form_handler.js b/js/form_handler.js index 5757860f4..6f02e6423 100644 --- a/js/form_handler.js +++ b/js/form_handler.js @@ -151,9 +151,16 @@ $(function() // Intended for overloading in derived classes _onUpdateSuccess: function(oData, sFormPath) { + var me = this; + if(oData.form.hidden_fields !== undefined) + { + $.each(oData.form.hidden_fields, function( index, value ) { + me.element.find('[data-form-path="' + sFormPath + '"][data-field-id="'+value+'"][data-attribute-flag-hidden="false"]').remove(); + }); + } if(oData.form.updated_fields !== undefined) { - this.element.find('[data-form-path="' + sFormPath + '"]').trigger('update_form', {updated_fields: oData.form.updated_fields}); + me.element.find('[data-form-path="' + sFormPath + '"]').trigger('update_form', {updated_fields: oData.form.updated_fields}); } }, // Intended for overloading in derived classes From 949b213f9de721835e3312756e601b5a560c1c5e Mon Sep 17 00:00:00 2001 From: Eric Date: Thu, 24 Jun 2021 13:29:40 +0200 Subject: [PATCH 6/8] =?UTF-8?q?N=C2=B03513=20-=20revert=20crud=20sequence?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- core/dbobject.class.php | 3 +- test/core/CMDBSource/TransactionsTest.php | 47 ++++++++++++----------- 2 files changed, 26 insertions(+), 24 deletions(-) diff --git a/core/dbobject.class.php b/core/dbobject.class.php index 63914e0f7..c842fe6d2 100644 --- a/core/dbobject.class.php +++ b/core/dbobject.class.php @@ -2776,7 +2776,6 @@ abstract class DBObject implements iDisplay $this->DBWriteLinks(); $this->WriteExternalAttributes(); - $this->RecordObjCreation(); if ($bIsTransactionEnabled) { CMDBSource::Query('COMMIT'); @@ -2838,6 +2837,8 @@ abstract class DBObject implements iDisplay } } + $this->RecordObjCreation(); + return $this->m_iKey; } diff --git a/test/core/CMDBSource/TransactionsTest.php b/test/core/CMDBSource/TransactionsTest.php index 82594e578..4c07226d4 100644 --- a/test/core/CMDBSource/TransactionsTest.php +++ b/test/core/CMDBSource/TransactionsTest.php @@ -123,29 +123,30 @@ class TransactionsTest extends ItopTestCase "History 13" => ['iFailAt' => 15, 'bIsInDB' => false], "History 14" => ['iFailAt' => 16, 'bIsInDB' => false], "History 15" => ['iFailAt' => 17, 'bIsInDB' => false], - "History 16" => ['iFailAt' => 18, 'bIsInDB' => false], - "History 17" => ['iFailAt' => 19, 'bIsInDB' => false], - "History 18" => ['iFailAt' => 20, 'bIsInDB' => false], - "History 19" => ['iFailAt' => 21, 'bIsInDB' => false], - "History 20" => ['iFailAt' => 22, 'bIsInDB' => false], - "History 21" => ['iFailAt' => 23, 'bIsInDB' => false], - "History 22" => ['iFailAt' => 24, 'bIsInDB' => false], - "History 23" => ['iFailAt' => 25, 'bIsInDB' => false], - "History 24" => ['iFailAt' => 26, 'bIsInDB' => false], - "History 25" => ['iFailAt' => 27, 'bIsInDB' => false], - "History 26" => ['iFailAt' => 28, 'bIsInDB' => false], - "History 27" => ['iFailAt' => 29, 'bIsInDB' => false], - "History 28" => ['iFailAt' => 30, 'bIsInDB' => false], - "History 29" => ['iFailAt' => 31, 'bIsInDB' => false], - "History 30" => ['iFailAt' => 32, 'bIsInDB' => false], - "History 31" => ['iFailAt' => 33, 'bIsInDB' => false], - "History 32" => ['iFailAt' => 34, 'bIsInDB' => false], - "History 33" => ['iFailAt' => 35, 'bIsInDB' => false], - "History 34" => ['iFailAt' => 36, 'bIsInDB' => false], - "History 35" => ['iFailAt' => 37, 'bIsInDB' => false], - "History 36" => ['iFailAt' => 38, 'bIsInDB' => false], - "History 37" => ['iFailAt' => 39, 'bIsInDB' => false], - "History 38" => ['iFailAt' => 40, 'bIsInDB' => false], + // For 3.0 when CRUD sequence is ok +// "History 16" => ['iFailAt' => 18, 'bIsInDB' => false], +// "History 17" => ['iFailAt' => 19, 'bIsInDB' => false], +// "History 18" => ['iFailAt' => 20, 'bIsInDB' => false], +// "History 19" => ['iFailAt' => 21, 'bIsInDB' => false], +// "History 20" => ['iFailAt' => 22, 'bIsInDB' => false], +// "History 21" => ['iFailAt' => 23, 'bIsInDB' => false], +// "History 22" => ['iFailAt' => 24, 'bIsInDB' => false], +// "History 23" => ['iFailAt' => 25, 'bIsInDB' => false], +// "History 24" => ['iFailAt' => 26, 'bIsInDB' => false], +// "History 25" => ['iFailAt' => 27, 'bIsInDB' => false], +// "History 26" => ['iFailAt' => 28, 'bIsInDB' => false], +// "History 27" => ['iFailAt' => 29, 'bIsInDB' => false], +// "History 28" => ['iFailAt' => 30, 'bIsInDB' => false], +// "History 29" => ['iFailAt' => 31, 'bIsInDB' => false], +// "History 30" => ['iFailAt' => 32, 'bIsInDB' => false], +// "History 31" => ['iFailAt' => 33, 'bIsInDB' => false], +// "History 32" => ['iFailAt' => 34, 'bIsInDB' => false], +// "History 33" => ['iFailAt' => 35, 'bIsInDB' => false], +// "History 34" => ['iFailAt' => 36, 'bIsInDB' => false], +// "History 35" => ['iFailAt' => 37, 'bIsInDB' => false], +// "History 36" => ['iFailAt' => 38, 'bIsInDB' => false], +// "History 37" => ['iFailAt' => 39, 'bIsInDB' => false], +// "History 38" => ['iFailAt' => 40, 'bIsInDB' => false], ]; } From a23ea9a01f819889df63d82dec81c1d79aa2ea1e Mon Sep 17 00:00:00 2001 From: acognet Date: Thu, 24 Jun 2021 14:11:41 +0200 Subject: [PATCH 7/8] =?UTF-8?q?N=C2=B03678=20-=20Portal=20:=20a=20modifica?= =?UTF-8?q?tion=20of=20field=20cannot=20hide=20another=20one?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- js/form_handler.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/js/form_handler.js b/js/form_handler.js index 6f02e6423..1c5735dff 100644 --- a/js/form_handler.js +++ b/js/form_handler.js @@ -155,7 +155,7 @@ $(function() if(oData.form.hidden_fields !== undefined) { $.each(oData.form.hidden_fields, function( index, value ) { - me.element.find('[data-form-path="' + sFormPath + '"][data-field-id="'+value+'"][data-attribute-flag-hidden="false"]').remove(); + me.element.find('[data-form-path="' + sFormPath + '"][data-field-id="'+value+'"][data-attribute-flag-hidden="false"]').children().remove(); }); } if(oData.form.updated_fields !== undefined) From 8259a79cd22792c4b6ddde9b222d7db172fb3e6c Mon Sep 17 00:00:00 2001 From: Pierre Goiffon Date: Fri, 25 Jun 2021 17:02:23 +0200 Subject: [PATCH 8/8] :art: Factorize LogAPI channels value in LogChannels class --- core/cmdbsource.class.inc.php | 2 +- core/inlineimage.class.inc.php | 116 +++++++++--------- core/log.class.inc.php | 26 ++-- .../src/Controller/BrowseBrickController.php | 3 +- .../src/Controller/ManageBrickController.php | 3 +- pages/ajax.render.php | 36 +++--- 6 files changed, 99 insertions(+), 87 deletions(-) diff --git a/core/cmdbsource.class.inc.php b/core/cmdbsource.class.inc.php index e1b4a1d79..b82c665a0 100644 --- a/core/cmdbsource.class.inc.php +++ b/core/cmdbsource.class.inc.php @@ -761,7 +761,7 @@ class CMDBSource ); DeadLockLog::Info($sMessage, $iMySqlErrorNo, $aLogContext); - IssueLog::Error($sMessage, 'DeadLock', $e->getMessage()); + IssueLog::Error($sMessage, LogChannels::DEADLOCK, $e->getMessage()); } /** diff --git a/core/inlineimage.class.inc.php b/core/inlineimage.class.inc.php index 05b75ddc8..93aa6e11a 100644 --- a/core/inlineimage.class.inc.php +++ b/core/inlineimage.class.inc.php @@ -176,31 +176,29 @@ class InlineImage extends DBObject $sOQL = 'SELECT InlineImage WHERE temp_id = :temp_id'; $oSearch = DBObjectSearch::FromOQL($sOQL); $oSet = new DBObjectSet($oSearch, array(), array('temp_id' => $sTempId)); - $aInlineImagesId = array(); - while($oInlineImage = $oSet->Fetch()) - { - $aInlineImagesId[] = $oInlineImage->GetKey(); + $aInlineImagesId = array(); + while ($oInlineImage = $oSet->Fetch()) { + $aInlineImagesId[] = $oInlineImage->GetKey(); $oInlineImage->SetItem($oObject); $oInlineImage->Set('temp_id', ''); $oInlineImage->DBUpdate(); } - IssueLog::Trace('FinalizeInlineImages (see $aInlineImagesId for the id list)', 'InlineImage', array( - '$sObjectClass' => get_class($oObject), - '$sTransactionId' => $iTransactionId, - '$sTempId' => $sTempId, - '$aInlineImagesId' => $aInlineImagesId, - '$sUser' => UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - )); + IssueLog::Trace('FinalizeInlineImages (see $aInlineImagesId for the id list)', LogChannels::INLINE_IMAGE, array( + '$sObjectClass' => get_class($oObject), + '$sTransactionId' => $iTransactionId, + '$sTempId' => $sTempId, + '$aInlineImagesId' => $aInlineImagesId, + '$sUser' => UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + )); } - else - { - IssueLog::Trace('FinalizeInlineImages "error" $iTransactionId is null', 'InlineImage', array( - '$sObjectClass' => get_class($oObject), - '$sTransactionId' => $iTransactionId, - '$sUser' => UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - )); + else { + IssueLog::Trace('FinalizeInlineImages "error" $iTransactionId is null', LogChannels::INLINE_IMAGE, array( + '$sObjectClass' => get_class($oObject), + '$sTransactionId' => $iTransactionId, + '$sUser' => UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + )); } } @@ -220,12 +218,12 @@ class InlineImage extends DBObject $aInlineImagesId[] = $oInlineImage->GetKey(); $oInlineImage->DBDelete(); } - IssueLog::Trace('OnFormCancel', 'InlineImage', array( - '$sTempId' => $sTempId, - '$aInlineImagesId' => $aInlineImagesId, - '$sUser' => UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - )); + IssueLog::Trace('OnFormCancel', LogChannels::INLINE_IMAGE, array( + '$sTempId' => $sTempId, + '$aInlineImagesId' => $aInlineImagesId, + '$sUser' => UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + )); } /** @@ -565,17 +563,17 @@ JS protected function AfterInsert() { - IssueLog::Trace(__METHOD__, 'InlineImage', array( - 'id' => $this->GetKey(), - 'expire' => $this->Get('expire'), - 'temp_id' => $this->Get('temp_id'), - 'item_class' => $this->Get('item_class'), - 'item_id' => $this->Get('item_id'), - 'item_org_id' => $this->Get('item_org_id'), - 'secret' => $this->Get('secret'), - 'user' => $sUser = UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], + IssueLog::Trace(__METHOD__, LogChannels::INLINE_IMAGE, array( + 'id' => $this->GetKey(), + 'expire' => $this->Get('expire'), + 'temp_id' => $this->Get('temp_id'), + 'item_class' => $this->Get('item_class'), + 'item_id' => $this->Get('item_id'), + 'item_org_id' => $this->Get('item_org_id'), + 'secret' => $this->Get('secret'), + 'user' => $sUser = UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], )); parent::AfterInsert(); @@ -583,17 +581,17 @@ JS protected function AfterUpdate() { - IssueLog::Trace(__METHOD__, 'InlineImage', array( - 'id' => $this->GetKey(), - 'expire' => $this->Get('expire'), - 'temp_id' => $this->Get('temp_id'), - 'item_class' => $this->Get('item_class'), - 'item_id' => $this->Get('item_id'), - 'item_org_id' => $this->Get('item_org_id'), - 'secret' => $this->Get('secret'), - 'user' => $sUser = UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], + IssueLog::Trace(__METHOD__, LogChannels::INLINE_IMAGE, array( + 'id' => $this->GetKey(), + 'expire' => $this->Get('expire'), + 'temp_id' => $this->Get('temp_id'), + 'item_class' => $this->Get('item_class'), + 'item_id' => $this->Get('item_id'), + 'item_org_id' => $this->Get('item_org_id'), + 'secret' => $this->Get('secret'), + 'user' => $sUser = UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], )); parent::AfterUpdate(); @@ -601,17 +599,17 @@ JS protected function AfterDelete() { - IssueLog::Trace(__METHOD__, 'InlineImage', array( - 'id' => $this->GetKey(), - 'expire' => $this->Get('expire'), - 'temp_id' => $this->Get('temp_id'), - 'item_class' => $this->Get('item_class'), - 'item_id' => $this->Get('item_id'), - 'item_org_id' => $this->Get('item_org_id'), - 'secret' => $this->Get('secret'), - 'user' => $sUser = UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], + IssueLog::Trace(__METHOD__, LogChannels::INLINE_IMAGE, array( + 'id' => $this->GetKey(), + 'expire' => $this->Get('expire'), + 'temp_id' => $this->Get('temp_id'), + 'item_class' => $this->Get('item_class'), + 'item_id' => $this->Get('item_id'), + 'item_org_id' => $this->Get('item_org_id'), + 'secret' => $this->Get('secret'), + 'user' => $sUser = UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], )); parent::AfterDelete(); diff --git a/core/log.class.inc.php b/core/log.class.inc.php index f4e7a10cf..39988557c 100644 --- a/core/log.class.inc.php +++ b/core/log.class.inc.php @@ -517,12 +517,9 @@ class FileLog { flock($hLogFile, LOCK_EX); $sDate = date('Y-m-d H:i:s'); - if (empty($aContext)) - { + if (empty($aContext)) { fwrite($hLogFile, "$sDate | $sText\n"); - } - else - { + } else { $sContext = var_export($aContext, true); fwrite($hLogFile, "$sDate | $sText\n$sContext\n"); } @@ -533,6 +530,21 @@ class FileLog } } + +/** + * Simple enum like class to factorize channels values as constants + * Channels are used especially as parameters in {@see \LogAPI} methods + * + * @since 2.7.5 3.0.0 N°4012 + */ +class LogChannels +{ + const DEADLOCK = 'DeadLock'; + const INLINE_IMAGE = 'InlineImage'; + const PORTAL = 'portal'; +} + + abstract class LogAPI { const CHANNEL_DEFAULT = ''; @@ -544,11 +556,11 @@ abstract class LogAPI const LEVEL_DEBUG = 'Debug'; const LEVEL_TRACE = 'Trace'; /** - * @var string default log level, can be overrided * @see GetMinLogLevel + * @var string default log level, can be overrided * @since 2.7.1 N°2977 */ - const LEVEL_DEFAULT = self::LEVEL_OK; + const LEVEL_DEFAULT = self::LEVEL_OK; protected static $aLevelsPriority = array( self::LEVEL_ERROR => 400, diff --git a/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php b/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php index c7776c65a..ed07b90fa 100644 --- a/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php +++ b/datamodels/2.x/itop-portal-base/portal/src/Controller/BrowseBrickController.php @@ -31,6 +31,7 @@ use DBObjectSet; use DBSearch; use FieldExpression; use IssueLog; +use LogChannels; use MetaModel; use Symfony\Component\HttpFoundation\JsonResponse; use Symfony\Component\HttpFoundation\Request; @@ -441,7 +442,7 @@ class BrowseBrickController extends BrickController } } - IssueLog::Debug('Portal BrowseBrick query', 'portal', array( + IssueLog::Debug('Portal BrowseBrick query', LogChannels::PORTAL, array( 'sPortalId' => $sPortalId, 'sBrickId' => $sBrickId, 'oql' => $oSet->GetFilter()->ToOQL(), diff --git a/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php b/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php index 7223abf49..58d19e62b 100644 --- a/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php +++ b/datamodels/2.x/itop-portal-base/portal/src/Controller/ManageBrickController.php @@ -43,6 +43,7 @@ use FieldExpression; use iPopupMenuExtension; use IssueLog; use JSButtonItem; +use LogChannels; use MetaModel; use Symfony\Component\HttpFoundation\JsonResponse; use Symfony\Component\HttpFoundation\Request; @@ -814,7 +815,7 @@ class ManageBrickController extends BrickController ); } - IssueLog::Debug('Portal ManageBrick query', 'portal', array( + IssueLog::Debug('Portal ManageBrick query', LogChannels::PORTAL, array( 'sPortalId' => $sPortalId, 'sBrickId' => $sBrickId, 'sGroupingTab' => $sGroupingTab, diff --git a/pages/ajax.render.php b/pages/ajax.render.php index c19f8c12c..07aa82077 100644 --- a/pages/ajax.render.php +++ b/pages/ajax.render.php @@ -2646,15 +2646,15 @@ EOF $aResult['height'] = $aDimensions['height']; } - IssueLog::Trace('InlineImage created', 'InlineImage', array( - '$operation' => $operation, - '$aResult' => $aResult, - 'secret' => $oAttachment->Get('secret'), - 'temp_id' => $sTempId, - 'item_class' => $sObjClass, - 'user' => UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], + IssueLog::Trace('InlineImage created', LogChannels::INLINE_IMAGE, array( + '$operation' => $operation, + '$aResult' => $aResult, + 'secret' => $oAttachment->Get('secret'), + 'temp_id' => $sTempId, + 'item_class' => $sObjClass, + 'user' => UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], )); } else @@ -2697,15 +2697,15 @@ EOF $oAttachment->Set('secret', sprintf('%06x', mt_rand(0, 0xFFFFFF))); // something not easy to guess $iAttId = $oAttachment->DBInsert(); - IssueLog::Trace('InlineImage created', 'InlineImage', array( - '$operation' => $operation, - 'secret' => $oAttachment->Get('secret'), - 'temp_id' => $sTempId, - 'item_class' => $sObjClass, - 'user' => UserRights::GetUser(), - 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], - 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], - )); + IssueLog::Trace('InlineImage created', LogChannels::INLINE_IMAGE, array( + '$operation' => $operation, + 'secret' => $oAttachment->Get('secret'), + 'temp_id' => $sTempId, + 'item_class' => $sObjClass, + 'user' => UserRights::GetUser(), + 'HTTP_REFERER' => @$_SERVER['HTTP_REFERER'], + 'REQUEST_URI' => @$_SERVER['REQUEST_URI'], + )); } } catch (FileUploadException $e)