@@ -575,6 +575,14 @@ public function walkEntityIdentificationVariable(string $identVariable): string
575
575
return implode (', ' , $ sqlParts );
576
576
}
577
577
578
+ /**
579
+ * Walks down an EntityAsDtoArgumentExpression AST node, thereby generating the appropriate SQL.
580
+ */
581
+ public function walkEntityAsDtoArgumentExpression (AST \EntityAsDtoArgumentExpression $ expr ): string
582
+ {
583
+ return implode (', ' , $ this ->walkObjectExpression ($ expr ->expression , [], $ expr ->identificationVariable ?: null ));
584
+ }
585
+
578
586
/**
579
587
* Walks down an IdentificationVariable (no AST node associated), thereby generating the SQL.
580
588
*/
@@ -1356,84 +1364,95 @@ public function walkSelectExpression(AST\SelectExpression $selectExpression): st
1356
1364
$ partialFieldSet = [];
1357
1365
}
1358
1366
1359
- $ class = $ this ->getMetadataForDqlAlias ($ dqlAlias );
1360
- $ resultAlias = $ selectExpression -> fieldIdentificationVariable ?: null ;
1367
+ $ sql .= implode ( ' , ' , $ this ->walkObjectExpression ($ dqlAlias, $ partialFieldSet , $ selectExpression -> fieldIdentificationVariable ?: null ) );
1368
+ }
1361
1369
1362
- if (! isset ($ this ->selectedClasses [$ dqlAlias ])) {
1363
- $ this ->selectedClasses [$ dqlAlias ] = [
1364
- 'class ' => $ class ,
1365
- 'dqlAlias ' => $ dqlAlias ,
1366
- 'resultAlias ' => $ resultAlias ,
1367
- ];
1368
- }
1370
+ return $ sql ;
1371
+ }
1369
1372
1370
- $ sqlParts = [];
1373
+ /**
1374
+ * Walks down an Object Expression AST node and return Sql Parts
1375
+ *
1376
+ * @param mixed[] $partialFieldSet
1377
+ *
1378
+ * @return string[]
1379
+ */
1380
+ public function walkObjectExpression (string $ dqlAlias , array $ partialFieldSet , string |null $ resultAlias ): array
1381
+ {
1382
+ $ class = $ this ->getMetadataForDqlAlias ($ dqlAlias );
1371
1383
1372
- // Select all fields from the queried class
1373
- foreach ($ class ->fieldMappings as $ fieldName => $ mapping ) {
1374
- if ($ partialFieldSet && ! in_array ($ fieldName , $ partialFieldSet , true )) {
1375
- continue ;
1376
- }
1384
+ if (! isset ($ this ->selectedClasses [$ dqlAlias ])) {
1385
+ $ this ->selectedClasses [$ dqlAlias ] = [
1386
+ 'class ' => $ class ,
1387
+ 'dqlAlias ' => $ dqlAlias ,
1388
+ 'resultAlias ' => $ resultAlias ,
1389
+ ];
1390
+ }
1377
1391
1378
- $ tableName = isset ($ mapping ->inherited )
1379
- ? $ this ->em ->getClassMetadata ($ mapping ->inherited )->getTableName ()
1380
- : $ class ->getTableName ();
1392
+ $ sqlParts = [];
1381
1393
1382
- $ sqlTableAlias = $ this ->getSQLTableAlias ($ tableName , $ dqlAlias );
1383
- $ columnAlias = $ this ->getSQLColumnAlias ($ mapping ->columnName );
1384
- $ quotedColumnName = $ this ->quoteStrategy ->getColumnName ($ fieldName , $ class , $ this ->platform );
1394
+ // Select all fields from the queried class
1395
+ foreach ($ class ->fieldMappings as $ fieldName => $ mapping ) {
1396
+ if ($ partialFieldSet && ! in_array ($ fieldName , $ partialFieldSet , true )) {
1397
+ continue ;
1398
+ }
1385
1399
1386
- $ col = $ sqlTableAlias . '. ' . $ quotedColumnName ;
1400
+ $ tableName = isset ($ mapping ->inherited )
1401
+ ? $ this ->em ->getClassMetadata ($ mapping ->inherited )->getTableName ()
1402
+ : $ class ->getTableName ();
1387
1403
1388
- $ type = Type::getType ($ mapping ->type );
1389
- $ col = $ type ->convertToPHPValueSQL ($ col , $ this ->platform );
1404
+ $ sqlTableAlias = $ this ->getSQLTableAlias ($ tableName , $ dqlAlias );
1405
+ $ columnAlias = $ this ->getSQLColumnAlias ($ mapping ->columnName );
1406
+ $ quotedColumnName = $ this ->quoteStrategy ->getColumnName ($ fieldName , $ class , $ this ->platform );
1390
1407
1391
- $ sqlParts [] = $ col . ' AS ' . $ columnAlias ;
1408
+ $ col = $ sqlTableAlias . '. ' . $ quotedColumnName ;
1392
1409
1393
- $ this ->scalarResultAliasMap [$ resultAlias ][] = $ columnAlias ;
1410
+ $ type = Type::getType ($ mapping ->type );
1411
+ $ col = $ type ->convertToPHPValueSQL ($ col , $ this ->platform );
1394
1412
1395
- $ this -> rsm -> addFieldResult ( $ dqlAlias , $ columnAlias, $ fieldName , $ class -> name ) ;
1413
+ $ sqlParts [] = $ col . ' AS ' . $ columnAlias ;
1396
1414
1397
- if (! empty ($ mapping ->enumType )) {
1398
- $ this ->rsm ->addEnumResult ($ columnAlias , $ mapping ->enumType );
1399
- }
1400
- }
1415
+ $ this ->scalarResultAliasMap [$ resultAlias ][] = $ columnAlias ;
1401
1416
1402
- // Add any additional fields of subclasses (excluding inherited fields)
1403
- // 1) on Single Table Inheritance: always, since its marginal overhead
1404
- // 2) on Class Table Inheritance only if partial objects are disallowed,
1405
- // since it requires outer joining subtables.
1406
- if ($ class ->isInheritanceTypeSingleTable () || ! $ this ->query ->getHint (Query::HINT_FORCE_PARTIAL_LOAD )) {
1407
- foreach ($ class ->subClasses as $ subClassName ) {
1408
- $ subClass = $ this ->em ->getClassMetadata ($ subClassName );
1409
- $ sqlTableAlias = $ this ->getSQLTableAlias ($ subClass ->getTableName (), $ dqlAlias );
1417
+ $ this ->rsm ->addFieldResult ($ dqlAlias , $ columnAlias , $ fieldName , $ class ->name );
1410
1418
1411
- foreach ( $ subClass -> fieldMappings as $ fieldName => $ mapping ) {
1412
- if ( isset ( $ mapping -> inherited ) || ( $ partialFieldSet && ! in_array ( $ fieldName , $ partialFieldSet , true ))) {
1413
- continue ;
1414
- }
1419
+ if (! empty ( $ mapping -> enumType ) ) {
1420
+ $ this -> rsm -> addEnumResult ( $ columnAlias , $ mapping -> enumType );
1421
+ }
1422
+ }
1415
1423
1416
- $ columnAlias = $ this ->getSQLColumnAlias ($ mapping ->columnName );
1417
- $ quotedColumnName = $ this ->quoteStrategy ->getColumnName ($ fieldName , $ subClass , $ this ->platform );
1424
+ // Add any additional fields of subclasses (excluding inherited fields)
1425
+ // 1) on Single Table Inheritance: always, since its marginal overhead
1426
+ // 2) on Class Table Inheritance only if partial objects are disallowed,
1427
+ // since it requires outer joining subtables.
1428
+ if ($ class ->isInheritanceTypeSingleTable () || ! $ this ->query ->getHint (Query::HINT_FORCE_PARTIAL_LOAD )) {
1429
+ foreach ($ class ->subClasses as $ subClassName ) {
1430
+ $ subClass = $ this ->em ->getClassMetadata ($ subClassName );
1431
+ $ sqlTableAlias = $ this ->getSQLTableAlias ($ subClass ->getTableName (), $ dqlAlias );
1432
+
1433
+ foreach ($ subClass ->fieldMappings as $ fieldName => $ mapping ) {
1434
+ if (isset ($ mapping ->inherited ) || ($ partialFieldSet && ! in_array ($ fieldName , $ partialFieldSet , true ))) {
1435
+ continue ;
1436
+ }
1437
+
1438
+ $ columnAlias = $ this ->getSQLColumnAlias ($ mapping ->columnName );
1439
+ $ quotedColumnName = $ this ->quoteStrategy ->getColumnName ($ fieldName , $ subClass , $ this ->platform );
1418
1440
1419
- $ col = $ sqlTableAlias . '. ' . $ quotedColumnName ;
1441
+ $ col = $ sqlTableAlias . '. ' . $ quotedColumnName ;
1420
1442
1421
- $ type = Type::getType ($ mapping ->type );
1422
- $ col = $ type ->convertToPHPValueSQL ($ col , $ this ->platform );
1443
+ $ type = Type::getType ($ mapping ->type );
1444
+ $ col = $ type ->convertToPHPValueSQL ($ col , $ this ->platform );
1423
1445
1424
- $ sqlParts [] = $ col . ' AS ' . $ columnAlias ;
1446
+ $ sqlParts [] = $ col . ' AS ' . $ columnAlias ;
1425
1447
1426
- $ this ->scalarResultAliasMap [$ resultAlias ][] = $ columnAlias ;
1448
+ $ this ->scalarResultAliasMap [$ resultAlias ][] = $ columnAlias ;
1427
1449
1428
- $ this ->rsm ->addFieldResult ($ dqlAlias , $ columnAlias , $ fieldName , $ subClassName );
1429
- }
1430
- }
1450
+ $ this ->rsm ->addFieldResult ($ dqlAlias , $ columnAlias , $ fieldName , $ subClassName );
1431
1451
}
1432
-
1433
- $ sql .= implode (', ' , $ sqlParts );
1452
+ }
1434
1453
}
1435
1454
1436
- return $ sql ;
1455
+ return $ sqlParts ;
1437
1456
}
1438
1457
1439
1458
public function walkQuantifiedExpression (AST \QuantifiedExpression $ qExpr ): string
@@ -1549,6 +1568,14 @@ public function walkNewObject(AST\NewObjectExpression $newObjectExpression, stri
1549
1568
$ sqlSelectExpressions [] = trim ($ e ->dispatch ($ this )) . ' AS ' . $ columnAlias ;
1550
1569
break ;
1551
1570
1571
+ case $ e instanceof AST \EntityAsDtoArgumentExpression:
1572
+ $ alias = $ e ->identificationVariable ?: $ columnAlias ;
1573
+ $ this ->rsm ->nestedNewObjectArguments [$ columnAlias ] = ['ownerIndex ' => $ objIndex , 'argIndex ' => $ argIndex , 'argAlias ' => $ alias ];
1574
+ $ this ->rsm ->nestedEntities [$ alias ] = ['parent ' => $ objIndex , 'argIndex ' => $ argIndex , 'type ' => 'entity ' ];
1575
+
1576
+ $ sqlSelectExpressions [] = trim ($ e ->dispatch ($ this ));
1577
+ break ;
1578
+
1552
1579
default :
1553
1580
$ sqlSelectExpressions [] = trim ($ e ->dispatch ($ this )) . ' AS ' . $ columnAlias ;
1554
1581
break ;
0 commit comments