[DDC-349] Add support for specifying precedence in joins in DQL Created: 18/Feb/10 Updated: 01/May/13 |
|
| Status: | Open |
| Project: | Doctrine 2 - ORM |
| Component/s: | DQL |
| Affects Version/s: | 2.0-ALPHA4 |
| Fix Version/s: | None |
| Security Level: | All |
| Type: | Improvement | Priority: | Major |
| Reporter: | Dennis Verspuij | Assignee: | Roman S. Borschel |
| Resolution: | Unresolved | Votes: | 1 |
| Labels: | None | ||
| Attachments: |
|
||||||||
| Issue Links: |
|
||||||||
| Description |
|
This request is in followup to my doctrine-user message "Doctrine 2.0: Nested joins'. As a short example the following is a SQL statement with a nested join, where the nesting is absolutely necessary to return only a's together with either both b's and c's or no b's and c's at all: SELECT * In order for Doctrine 2 to support this the BNF should be something like: This would allow DQL like: SELECT A, B, C What further needs to be done is that the DQL parser loosly couples the ConditionalExpression to any of the previously parsed JoinAssociationPathExpression's instead of tieing it explicitely to the JoinAssociationPathExpression that preceedes it according to the old BNF notation. The new BNF should however not require any changes to the hydrator. Therefore I have the feeling that improving the DQL parser for nested joins does not require extensive work, while the benefit of running these kind of queries is considerable. As an extra substantiation here are links to (BNF) FROM clause documentations of the RDBMS's that Doctrine 2 supports, they all show support for nested joins: I surely hope you will consider implementing this improvement because it would save me and others from the hassle of writing raw SQL queries or executing multiple (thus slow) queries in DQL for doing the same. Thanks anyway for the great product so far! |
| Comments |
| Comment by Guilherme Blanco [ 13/Apr/10 ] |
|
This seems to be a valid issue to me. This implementation is the actual solution to associations retrieval that are inherited (type joined). Example: /** Joined */
class Base {}
class Foo extends Base {}
class Bar {
public $foo;
}
// This causes the CTI to link as INNER JOIN, which makes the result become 0
// il if you have no Foo's defined (although it should ignore this)
$q = $this->_em->createQuery('SELECT b, f FROM Bar b LEFT JOIN b.foo f');
|
| Comment by Roman S. Borschel [ 13/Apr/10 ] |
|
Yes, this is a possible solution for |
| Comment by Roman S. Borschel [ 13/Apr/10 ] |
|
So, no, this has nothing to do with |
| Comment by Roman S. Borschel [ 13/Apr/10 ] |
|
On a side note I would still like to know/see the following for this issue:
So far, my stance on this issue is: 1) It doesnt make sense (semantically) in DQL Thus I am currently leaning towards "Wont fix" for this issue. |
| Comment by Dennis Verspuij [ 13/Apr/10 ] |
|
Hi Roman. I understand your doubts, and I have been breaking my head over SELECT A.id, A.username, A.balance, COALESCE(SUM(B.stake), 0) AS sumstake, COUNT(B.id) AS nrbets But let's put it another way. I would also like this feature to be supported in DQL Btw, I recall to have successfully used the nested join syntax in HQL (.NET Hibernate) Furthermore, in reply to your stances: Well, this is it, can't find any more words to promote and make you enthusiastic.... lol. |
| Comment by Dennis Verspuij [ 13/Apr/10 ] |
|
Ok, I have not given up yet... Imagine a book store that sells books of various authors and keeps track of those sales. SELECT A., B., S.* In DQL it would then be something like: SELECT A., B., S.* If the database would contain thousands of books, but sales for just a I have attached a test casefor a similar query, though without the additional One last note, you shouldn't be afraid that nesting joins is not in the P.S. I had a hard time finding out how to run the test cases, I could not find |
| Comment by Dennis Verspuij [ 13/Apr/10 ] |
|
Test case as SVN patch using a parenthesized join. |
| Comment by Roman S. Borschel [ 29/May/10 ] |
|
@"The need for native queries partly reverts the benefits Doctrine offers in the first place." That is something I hugely disagree with. Neither SQL abstraction, nor database vendor independence is the main purpose of an ORM like Doctrine 2. We could rip out DQL and any other querying mechanism except a basic find() (and lazy-loading, of course), only providing the native query facility and even only supporting MySQL and would still retain all the core ORM functionality. NativeQuery is one of the best and core "features" of the project. It is even the foundation for DQL. A DQL query is nothing more than an additional (beautiful) abstraction but what comes out is a native query + a ResultSetMapping, the same thing you can build yourself in the first place, even using the mapping metadata to construct the query. Nothing forces you to hardcode table and column names in native queries if you don't want that. Just use the mapping metadata, DQL does the same. SQL abstraction and database vendor independence is icing on the cake, not the heart of the ORM. |