diff --git a/core/dbsearch.class.php b/core/dbsearch.class.php index c4af180c2..0544f0fc7 100644 --- a/core/dbsearch.class.php +++ b/core/dbsearch.class.php @@ -851,11 +851,11 @@ abstract class DBSearch return; } - if (count($aColumns) == 0) - { - $aColumns = array_keys(MetaModel::ListAttributeDefs($this->GetClass())); - // Add the standard id (as first column) - array_unshift($aColumns, 'id'); + if (count($aColumns) == 0) + { + $aColumns = array_keys(MetaModel::ListAttributeDefs($this->GetClass())); + // Add the standard id (as first column) + array_unshift($aColumns, 'id'); } $aQueryCols = CMDBSource::GetColumns($resQuery, $sSQL); @@ -885,6 +885,55 @@ abstract class DBSearch return $aRes; } + /** + * Selects a column ($sAttCode) from the specified class ($sClassAlias - default main class) of the DBsearch object and gives the result as an array + * @param string $sAttCode + * @param string|null $sClassAlias + * + * @return array + * @throws ConfigException + * @throws CoreException + * @throws MissingQueryArgument + * @throws MySQLException + * @throws MySQLHasGoneAwayException + */ + public function SelectAttributeToArray(string $sAttCode, ?string $sClassAlias = null):array + { + if(is_null($sClassAlias)) { + $sClassAlias = $this->GetClassAlias(); + } + + $sClass = $this->GetClass(); + if($sAttCode === 'id'){ + $aAttToLoad[$sClassAlias]=[]; + } else { + $aAttToLoad[$sClassAlias][$sAttCode] = MetaModel::GetAttributeDef($sClass, $sAttCode); + } + + $sSQL = $this->MakeSelectQuery([], [], $aAttToLoad); + $resQuery = CMDBSource::Query($sSQL); + if (!$resQuery) + { + return []; + } + + $sColName = $sClassAlias.$sAttCode; + + $aRes = []; + while ($aRow = CMDBSource::FetchArray($resQuery)) + { + $aMappedRow = array(); + if($sAttCode === 'id') { + $aMappedRow[$sAttCode] = $aRow[$sColName]; + } else { + $aMappedRow[$sAttCode] = $aAttToLoad[$sClassAlias][$sAttCode]->FromSQLToValue($aRow, $sColName); + } + $aRes[] = $aMappedRow; + } + CMDBSource::FreeResult($resQuery); + return $aRes; + } + //////////////////////////////////////////////////////////////////////////// // // Construction of the SQL queries diff --git a/core/userrights.class.inc.php b/core/userrights.class.inc.php index ae5d6026f..1dd824f99 100644 --- a/core/userrights.class.inc.php +++ b/core/userrights.class.inc.php @@ -162,7 +162,7 @@ abstract class UserRightsAddOnAPI $oSearchSharers->AllowAllData(); $oSearchSharers->AddCondition_ReferencedBy($oShareSearch, 'sharing_org_id'); $aSharers = array(); - foreach($oSearchSharers->ToDataArray(array('id')) as $aRow) + foreach($oSearchSharers->SelectAttributeToArray('id') as $aRow) { $aSharers[] = $aRow['id']; } @@ -187,7 +187,7 @@ abstract class UserRightsAddOnAPI $oOrgField = new FieldExpression('org_id', $sShareClass); $oSearchShares->AddConditionExpression(new BinaryExpression($oOrgField, 'IN', $oListExpr)); $aShared = array(); - foreach($oSearchShares->ToDataArray(array($sShareAttCode)) as $aRow) + foreach($oSearchShares->SelectAttributeToArray($sShareAttCode) as $aRow) { $aShared[] = $aRow[$sShareAttCode]; } diff --git a/pages/audit.php b/pages/audit.php index d6492f9a4..5aed36d67 100644 --- a/pages/audit.php +++ b/pages/audit.php @@ -114,7 +114,7 @@ function GetRuleResultFilter($iRuleId, $oDefinitionFilter, $oAppContext) { // The query returns only the valid elements, all the others are invalid // Warning : we're generating a `WHERE ID IN`... query, and this could be very slow if there are lots of id ! - $aValidRows = $oRuleFilter->ToDataArray(array('id')); + $aValidRows = $oRuleFilter->ToDataArray(array('id')); $aValidIds = array(); foreach($aValidRows as $aRow) { @@ -431,7 +431,7 @@ try } else { try { $oFilter = GetRuleResultFilter($oAuditRule->GetKey(), $oDefinitionFilter, $oAppContext); - $aErrors = $oFilter->ToDataArray(array('id')); + $aErrors = $oFilter->SelectAttributeToArray('id'); $iErrorsCount = count($aErrors); foreach ($aErrors as $aErrorRow) { $aObjectsWithErrors[$aErrorRow['id']] = true; @@ -471,7 +471,7 @@ try $oP->AddUiBlock($oErrorAlert); continue; } - + $oAuditCategoryPanelBlock->SetColorFromColorSemantic($sClass); $oAuditCategoryPanelBlock->AddCSSClass('ibo-audit--audit-category--panel'); $aData = []; @@ -490,7 +490,7 @@ try 'nb_err' => array('label' => Dict::S('UI:Audit:HeaderNbErrors'), 'description' => Dict::S('UI:Audit:HeaderNbErrors')), 'percentage_ok' => array('label' => Dict::S('UI:Audit:PercentageOk'), 'description' => Dict::S('UI:Audit:PercentageOk')), ); - + $oAttachmentTableBlock = DataTableUIBlockFactory::MakeForStaticData('', $aAttribs, $aData, null, [], "", array('pageLength' => -1)); $oAuditCategoryPanelBlock->AddSubBlock($oAttachmentTableBlock); $aAuditCategoryPanels[] = $oAuditCategoryPanelBlock; diff --git a/tests/php-unit-tests/unitary-tests/core/DBSearchTest.php b/tests/php-unit-tests/unitary-tests/core/DBSearchTest.php index 09265d8d4..8d5a9d4ef 100644 --- a/tests/php-unit-tests/unitary-tests/core/DBSearchTest.php +++ b/tests/php-unit-tests/unitary-tests/core/DBSearchTest.php @@ -746,30 +746,110 @@ class DBSearchTest extends ItopDataTestCase $oSearch->MakeSelectQuery(); self::assertTrue(true); } + /** + * @dataProvider QueriesProvider + * @param $sOQL + * + * @return void + */ + public function testQueries($sOQL) + { + $oSearch = DBSearch::FromOQL($sOQL); + $oSet = new DBObjectSet($oSearch); + if ($oSet->Count() > 0) { + $aSelectedAliases = array_keys($oSearch->GetSelectedClasses()); + $aFirstRow = $oSet->FetchAssoc(); + $aAliases = array_keys($aFirstRow); + $this->assertEquals($aSelectedAliases, $aAliases); + } + } - /** - * @dataProvider QueriesProvider - * @param $sOQL - * - * @return void - */ - public function testQueries($sOQL) - { - $oSearch = DBSearch::FromOQL($sOQL); - $oSet = new DBObjectSet($oSearch); - if ($oSet->Count() > 0) { - $aSelectedAliases = array_keys($oSearch->GetSelectedClasses()); - $aFirstRow = $oSet->FetchAssoc(); - $aAliases = array_keys($aFirstRow); - $this->assertEquals($aSelectedAliases, $aAliases); - } - } + public function QueriesProvider() + { + return [ + ['SELECT L,P FROM Person AS P JOIN Location AS L ON P.location_id=L.id'], + ['SELECT P,L FROM Person AS P JOIN Location AS L ON P.location_id=L.id'], + ]; + } + public function SelectAttributeToArrayProvider() + { + return array( + 'select id from FunctionalCI' => array( + 'SELECT FunctionalCI', + 'id', + ), + 'select name from FunctionalCI' => array( + 'SELECT FunctionalCI', + 'name', + ), + 'select org_id from FunctionalCI' => array( + 'SELECT FunctionalCI', + 'org_id', + ), + 'select organization_name from FunctionalCI' => array( + 'SELECT FunctionalCI', + 'organization_name', + ), + 'select business_criticity from FunctionalCI' => array( + 'SELECT FunctionalCI', + 'business_criticity', + ), + 'select org_id from FunctionalCI' => array( + 'SELECT FunctionalCI', + 'org_id', + ), + 'select email from Person' => array( + 'SELECT Person', + 'email', + ), + 'select phone from Person' => array( + 'SELECT Person', + 'phone', + ), + 'select picture from Person' => array( + 'SELECT Person', + 'picture', + ), + 'select description from Ticket' => array( + 'SELECT Ticket', + 'description', + ), + 'select start_date from Ticket' => array( + 'SELECT Ticket', + 'start_date', + ), + 'select private_log from Ticket' => array( + 'SELECT Ticket', + 'private_log', + ), + ); + } - public function QueriesProvider() - { - return [ - ['SELECT L,P FROM Person AS P JOIN Location AS L ON P.location_id=L.id'], - ['SELECT P,L FROM Person AS P JOIN Location AS L ON P.location_id=L.id'], - ]; - } -} + /** + * @dataProvider SelectAttributeToArrayProvider + * + * @return void + * @throws \ConfigException + * @throws \CoreException + * @throws \MissingQueryArgument + * @throws \MySQLException + * @throws \MySQLHasGoneAwayException + * @throws \OQLException + */ + public function testSelectAttributeToArray($sQuery, $sField){ + + $oSearch = \DBObjectSearch::FromOQL($sQuery); + $aResToDataArray=[]; + $oSet = new \DBObjectSet($oSearch); + while ($oRecord = $oSet->Fetch()) { + $aMappedRow[$sField] =$oRecord->Get($sField); + $aResToDataArray[] = $aMappedRow; + } + array_multisort (array_column($aResToDataArray, $sField), SORT_DESC, $aResToDataArray); + + $aResSelectColumnToArray = $oSearch->SelectAttributeToArray($sField); + array_multisort (array_column($aResSelectColumnToArray, $sField), SORT_DESC, $aResSelectColumnToArray); + + self::assertEquals( $aResToDataArray, $aResSelectColumnToArray, 'The array constructed using the OQL query and the result of testSelectAttributeToArray must be the same'); + } +} \ No newline at end of file