From bc024d9ed0c4e291428bd3843644cfb605167e09 Mon Sep 17 00:00:00 2001 From: Eric Date: Tue, 2 Feb 2021 17:30:03 +0100 Subject: [PATCH] =?UTF-8?q?N=C2=B03660=20-=20Fix=20JOIN=20without=20condit?= =?UTF-8?q?ion=20on=20child=20joined=20table=20is=20ignored?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- core/legacy/dbobjectsearchlegacy.class.php | 13 ++++++ core/oqlclasstreebuilder.class.inc.php | 9 ++++ test/core/OQLTest.php | 53 ++++++++++++++++++++++ 3 files changed, 75 insertions(+) diff --git a/core/legacy/dbobjectsearchlegacy.class.php b/core/legacy/dbobjectsearchlegacy.class.php index 24e67db2c..f4d3e5e93 100644 --- a/core/legacy/dbobjectsearchlegacy.class.php +++ b/core/legacy/dbobjectsearchlegacy.class.php @@ -2602,5 +2602,18 @@ class DBObjectSearch extends DBSearch return $oExpression; } + /** + * @param array $aAttCodes array of attCodes to search into + * @param string $sNeedle one word to be searched + * + * @throws \CoreException + */ + public function AddCondition_FullTextOnAttributes(array $aAttCodes, $sNeedle) + { + } + public function ListParameters() + { + return $this->GetCriteria()->ListParameters(); + } } diff --git a/core/oqlclasstreebuilder.class.inc.php b/core/oqlclasstreebuilder.class.inc.php index a397ab3db..236f9d684 100644 --- a/core/oqlclasstreebuilder.class.inc.php +++ b/core/oqlclasstreebuilder.class.inc.php @@ -294,6 +294,15 @@ class OQLClassTreeBuilder $oClassExpr = new FieldExpression($sClassAttCode, $this->sClassAlias); $oClassRestriction = new BinaryExpression($oClassExpr, 'IN', $oClassListExpr); $oQBContextExpressions->AddCondition($oClassRestriction); + } elseif (($oKeyAttDef instanceof AttributeExternalKey) && $sKeyClass != $oKeyAttDef->GetTargetClass()) { + $sClassAttCode = 'finalclass'; + if (MetaModel::IsValidAttCode($sKeyClass, $sClassAttCode)) { + $oClassListExpr = ListExpression::FromScalars(MetaModel::EnumChildClasses($sKeyClass, + ENUM_CHILD_CLASSES_ALL)); + $oClassExpr = new FieldExpression($sClassAttCode, $sKeyClassAlias); + $oClassRestriction = new BinaryExpression($oClassExpr, 'IN', $oClassListExpr); + $oQBContextExpressions->AddCondition($oClassRestriction); + } } // Translate prior to recursing diff --git a/test/core/OQLTest.php b/test/core/OQLTest.php index d7b3939a3..d419f46b3 100644 --- a/test/core/OQLTest.php +++ b/test/core/OQLTest.php @@ -15,7 +15,10 @@ use Combodo\iTop\Test\UnitTest\ItopDataTestCase; use DBObjectSearch; use DBSearch; use Exception; +use MetaModel; use OqlInterpreter; +use QueryBuilderContext; +use SQLObjectQueryBuilder; use utils; /** @@ -401,4 +404,54 @@ class OQLTest extends ItopDataTestCase ); } + + /** + * @dataProvider GetOQLClassTreeProvider + * @param $sOQL + * @param $sExpectedOQL + */ + public function testGetOQLClassTree($sOQL, $sExpectedOQL) + { + $oFilter = DBSearch::FromOQL($sOQL); + $aCountAttToLoad = array(); + $sMainClass = null; + foreach ($oFilter->GetSelectedClasses() as $sClassAlias => $sClass) + { + $aCountAttToLoad[$sClassAlias] = array(); + if (empty($sMainClass)) + { + $sMainClass = $sClass; + } + } + $aModifierProperties = MetaModel::MakeModifierProperties($oFilter); + $oSQLObjectQueryBuilder = new SQLObjectQueryBuilder($oFilter); + $oBuild = new QueryBuilderContext($oFilter, $aModifierProperties, null, null, null, $aCountAttToLoad); + $sResultOQL = $oSQLObjectQueryBuilder->DebugOQLClassTree($oBuild); + + static::assertEquals($sExpectedOQL, $sResultOQL); + } + + public function GetOQLClassTreeProvider() + { + return [ + 'Bug 3660 1' => [ + "SELECT UserRequest AS U + JOIN lnkContactToTicket AS l ON l.ticket_id=U.id + JOIN Team AS T ON l.contact_id=T.id", + "SELECT `U` FROM `UserRequest` AS `U` + INNER JOIN `lnkContactToTicket` AS `l` + ON `U`.`id` = `l`.`ticket_id` + INNER JOIN `Contact` AS `T_Contact` + ON `l`.`contact_id` = `T_Contact`.`id`", + ], + 'Bug 3660 2' => [ + "SELECT UserRequest AS U + JOIN lnkContactToTicket AS l ON l.ticket_id=U.id + JOIN Contact AS C ON l.contact_id=C.id", + "SELECT `U` FROM `UserRequest` AS `U` + INNER JOIN `lnkContactToTicket` AS `l` + ON `U`.`id` = `l`.`ticket_id`", + ], + ]; + } }