From ee7b5da64aec642f101dff00492b00dca2e3b9db Mon Sep 17 00:00:00 2001 From: "Fabio B. Silva" Date: Sun, 1 Jan 2012 15:02:28 -0200 Subject: [PATCH] start work --- .../ORM/Query/AST/NewObjectExpression.php | 60 +++++++++++++++++++ lib/Doctrine/ORM/Query/Lexer.php | 1 + lib/Doctrine/ORM/Query/Parser.php | 35 +++++++++++ .../Doctrine/Tests/Models/CMS/CmsUserDTO.php | 17 ++++++ .../ORM/Query/SelectSqlGenerationTest.php | 12 ++++ 5 files changed, 125 insertions(+) create mode 100644 lib/Doctrine/ORM/Query/AST/NewObjectExpression.php create mode 100644 tests/Doctrine/Tests/Models/CMS/CmsUserDTO.php diff --git a/lib/Doctrine/ORM/Query/AST/NewObjectExpression.php b/lib/Doctrine/ORM/Query/AST/NewObjectExpression.php new file mode 100644 index 000000000..1642b6bfe --- /dev/null +++ b/lib/Doctrine/ORM/Query/AST/NewObjectExpression.php @@ -0,0 +1,60 @@ +. + */ + +namespace Doctrine\ORM\Query\AST; + +/** + * NewObjectExpression ::= "NEW" IdentificationVariable "(" SimpleSelectExpression {"," SimpleSelectExpression}* ")" + * + * @license http://www.opensource.org/licenses/lgpl-license.php LGPL + * @link www.doctrine-project.org + * @since 2.3 + * @author Fabio B. Silva + */ +class NewObjectExpression extends Node +{ + /** + * @var string + */ + public $identificationVariable; + + /** + * @var array + */ + public $fieldSet; + + /** + * @param type $identificationVariable + * @param array $fieldSet + */ + public function __construct($identificationVariable, array $fieldSet) + { + $this->identificationVariable = $identificationVariable; + $this->fieldSet = $fieldSet; + } + + /** + * @param \Doctrine\ORM\Query\SqlWalker $sqlWalker + * @return string + */ + public function dispatch($sqlWalker) + { + return $sqlWalker->walkNewObject($this); + } +} \ No newline at end of file diff --git a/lib/Doctrine/ORM/Query/Lexer.php b/lib/Doctrine/ORM/Query/Lexer.php index beafa7dee..4692b6ae8 100644 --- a/lib/Doctrine/ORM/Query/Lexer.php +++ b/lib/Doctrine/ORM/Query/Lexer.php @@ -108,6 +108,7 @@ class Lexer extends \Doctrine\Common\Lexer const T_WHERE = 154; const T_WITH = 155; const T_PARTIAL = 156; + const T_NEW = 157; /** * Creates a new query scanner object. diff --git a/lib/Doctrine/ORM/Query/Parser.php b/lib/Doctrine/ORM/Query/Parser.php index ac6ad6f3e..14d6c34f0 100644 --- a/lib/Doctrine/ORM/Query/Parser.php +++ b/lib/Doctrine/ORM/Query/Parser.php @@ -1629,6 +1629,35 @@ class Parser return $partialObjectExpression; } + /** + * NewObjectExpression ::= "NEW" IdentificationVariable "(" SimpleSelectExpression {"," SimpleSelectExpression}* ")" + * @return \Doctrine\ORM\Query\AST\NewObjectExpression + */ + public function NewObjectExpression() + { + $this->match(Lexer::T_NEW); + $this->match(Lexer::T_IDENTIFIER); + + $identificationVariable = $this->_lexer->token['value']; + + $this->match(Lexer::T_OPEN_PARENTHESIS); + + $fieldSet[] = $this->SimpleSelectExpression(); + while ($this->_lexer->isNextToken(Lexer::T_COMMA)) { + $this->match(Lexer::T_COMMA); + + $fieldSet[] = $this->SimpleSelectExpression(); + } + + $this->match(Lexer::T_CLOSE_PARENTHESIS); + + $expression = new AST\NewObjectExpression($identificationVariable, $fieldSet); + + // @TODO : Defer NewObjectExpression validation + throw new \BadMethodCallException("Not complete yet !"); + return $expression; + } + /** * IndexBy ::= "INDEX" "BY" StateFieldPathExpression * @@ -1953,6 +1982,12 @@ class Parser $expression = $this->SimpleArithmeticExpression(); break; + // NewObjectExpression (New ClassName(id, name)) + case ($lookaheadType === Lexer::T_NEW): + $expression = $this->NewObjectExpression(); + //$identVariable = $expression->identificationVariable; + break; + default: $this->syntaxError( 'IdentificationVariable | ScalarExpression | AggregateExpression | FunctionDeclaration | PartialObjectExpression | "(" Subselect ")" | CaseExpression', diff --git a/tests/Doctrine/Tests/Models/CMS/CmsUserDTO.php b/tests/Doctrine/Tests/Models/CMS/CmsUserDTO.php new file mode 100644 index 000000000..78398f863 --- /dev/null +++ b/tests/Doctrine/Tests/Models/CMS/CmsUserDTO.php @@ -0,0 +1,17 @@ +name = $name; + $this->email = $email; + $this->city = $city; + } +} \ No newline at end of file diff --git a/tests/Doctrine/Tests/ORM/Query/SelectSqlGenerationTest.php b/tests/Doctrine/Tests/ORM/Query/SelectSqlGenerationTest.php index fa5b06d82..232a86ea7 100644 --- a/tests/Doctrine/Tests/ORM/Query/SelectSqlGenerationTest.php +++ b/tests/Doctrine/Tests/ORM/Query/SelectSqlGenerationTest.php @@ -1555,6 +1555,18 @@ class SelectSqlGenerationTest extends \Doctrine\Tests\OrmTestCase ); } + /** + * @group DDC-1574 + */ + public function testSupportsNewOperator() + { + $this->markTestIncomplete('not complete yet !'); + $this->assertSqlGeneration( + 'SELECT new Doctrine\Tests\Models\CMS\CmsUser(u.name, e.email, a.city) FROM Doctrine\Tests\Models\CMS\CmsUser u JOIN u.email e JOIN u.address a', + 'SELECT c0_.name AS name0, c1_.email AS email1, c2_.city AS city2 FROM cms_users c0_ INNER JOIN cms_emails c1_ ON c0_.email_id = c1_.id INNER JOIN cms_addresses c2_ ON c0_.id = c2_.user_id' + ); + } + public function testCustomTypeValueSql() { if (DBALType::hasType('negative_to_positive')) {