3 namespace Doctrine\Tests\ORM\Hydration;
5 use Doctrine\Tests\Mocks\HydratorMockStatement;
6 use Doctrine\ORM\Query\ResultSetMapping;
8 require_once __DIR__ . '/../../TestInit.php';
10 class ArrayHydratorTest extends HydrationTestCase
12 public function provideDataForUserEntityResult()
21 * SELECT PARTIAL u.{id, name}
22 * FROM Doctrine\Tests\Models\CMS\CmsUser u
24 public function testSimpleEntityQuery()
26 $rsm = new ResultSetMapping;
27 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u');
28 $rsm->addFieldResult('u', 'u__id', 'id');
29 $rsm->addFieldResult('u', 'u__name', 'name');
43 $stmt = new HydratorMockStatement($resultSet);
44 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
45 $result = $hydrator->hydrateAll($stmt, $rsm);
47 $this->assertEquals(2, count($result));
49 $this->assertTrue(is_array($result));
51 $this->assertEquals(1, $result[0]['id']);
52 $this->assertEquals('romanb', $result[0]['name']);
54 $this->assertEquals(2, $result[1]['id']);
55 $this->assertEquals('jwage', $result[1]['name']);
59 * SELECT PARTIAL u.{id, name} AS user
60 * FROM Doctrine\Tests\Models\CMS\CmsUser u
62 public function testSimpleEntityQueryWithAliasedUserEntity()
64 $rsm = new ResultSetMapping;
65 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', 'user');
66 $rsm->addFieldResult('u', 'u__id', 'id');
67 $rsm->addFieldResult('u', 'u__name', 'name');
81 $stmt = new HydratorMockStatement($resultSet);
82 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
83 $result = $hydrator->hydrateAll($stmt, $rsm);
85 $this->assertEquals(2, count($result));
87 $this->assertTrue(is_array($result));
89 $this->assertArrayHasKey('user', $result[0]);
90 $this->assertEquals(1, $result[0]['user']['id']);
91 $this->assertEquals('romanb', $result[0]['user']['name']);
93 $this->assertArrayHasKey('user', $result[1]);
94 $this->assertEquals(2, $result[1]['user']['id']);
95 $this->assertEquals('jwage', $result[1]['user']['name']);
99 * SELECT PARTIAL u.{id, name}, PARTIAL a.{id, topic}
100 * FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
102 public function testSimpleMultipleRootEntityQuery()
104 $rsm = new ResultSetMapping;
105 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u');
106 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsArticle', 'a');
107 $rsm->addFieldResult('u', 'u__id', 'id');
108 $rsm->addFieldResult('u', 'u__name', 'name');
109 $rsm->addFieldResult('a', 'a__id', 'id');
110 $rsm->addFieldResult('a', 'a__topic', 'topic');
116 'u__name' => 'romanb',
118 'a__topic' => 'Cool things.'
122 'u__name' => 'jwage',
124 'a__topic' => 'Cool things II.'
128 $stmt = new HydratorMockStatement($resultSet);
129 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
130 $result = $hydrator->hydrateAll($stmt, $rsm);
132 $this->assertEquals(4, count($result));
134 $this->assertEquals(1, $result[0]['id']);
135 $this->assertEquals('romanb', $result[0]['name']);
137 $this->assertEquals(1, $result[1]['id']);
138 $this->assertEquals('Cool things.', $result[1]['topic']);
140 $this->assertEquals(2, $result[2]['id']);
141 $this->assertEquals('jwage', $result[2]['name']);
143 $this->assertEquals(2, $result[3]['id']);
144 $this->assertEquals('Cool things II.', $result[3]['topic']);
148 * SELECT PARTIAL u.{id, name} AS user, PARTIAL a.{id, topic}
149 * FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
151 public function testSimpleMultipleRootEntityQueryWithAliasedUserEntity()
153 $rsm = new ResultSetMapping;
154 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', 'user');
155 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsArticle', 'a');
156 $rsm->addFieldResult('u', 'u__id', 'id');
157 $rsm->addFieldResult('u', 'u__name', 'name');
158 $rsm->addFieldResult('a', 'a__id', 'id');
159 $rsm->addFieldResult('a', 'a__topic', 'topic');
165 'u__name' => 'romanb',
167 'a__topic' => 'Cool things.'
171 'u__name' => 'jwage',
173 'a__topic' => 'Cool things II.'
177 $stmt = new HydratorMockStatement($resultSet);
178 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
179 $result = $hydrator->hydrateAll($stmt, $rsm);
181 $this->assertEquals(4, count($result));
183 $this->assertArrayHasKey('user', $result[0]);
184 $this->assertEquals(1, $result[0]['user']['id']);
185 $this->assertEquals('romanb', $result[0]['user']['name']);
187 $this->assertArrayHasKey(0, $result[1]);
188 $this->assertEquals(1, $result[1][0]['id']);
189 $this->assertEquals('Cool things.', $result[1][0]['topic']);
191 $this->assertArrayHasKey('user', $result[2]);
192 $this->assertEquals(2, $result[2]['user']['id']);
193 $this->assertEquals('jwage', $result[2]['user']['name']);
195 $this->assertArrayHasKey(0, $result[3]);
196 $this->assertEquals(2, $result[3][0]['id']);
197 $this->assertEquals('Cool things II.', $result[3][0]['topic']);
201 * SELECT PARTIAL u.{id, name}, PARTIAL a.{id, topic} AS article
202 * FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
204 public function testSimpleMultipleRootEntityQueryWithAliasedArticleEntity()
206 $rsm = new ResultSetMapping;
207 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u');
208 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsArticle', 'a', 'article');
209 $rsm->addFieldResult('u', 'u__id', 'id');
210 $rsm->addFieldResult('u', 'u__name', 'name');
211 $rsm->addFieldResult('a', 'a__id', 'id');
212 $rsm->addFieldResult('a', 'a__topic', 'topic');
218 'u__name' => 'romanb',
220 'a__topic' => 'Cool things.'
224 'u__name' => 'jwage',
226 'a__topic' => 'Cool things II.'
230 $stmt = new HydratorMockStatement($resultSet);
231 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
232 $result = $hydrator->hydrateAll($stmt, $rsm);
234 $this->assertEquals(4, count($result));
236 $this->assertArrayHasKey(0, $result[0]);
237 $this->assertEquals(1, $result[0][0]['id']);
238 $this->assertEquals('romanb', $result[0][0]['name']);
240 $this->assertArrayHasKey('article', $result[1]);
241 $this->assertEquals(1, $result[1]['article']['id']);
242 $this->assertEquals('Cool things.', $result[1]['article']['topic']);
244 $this->assertArrayHasKey(0, $result[2]);
245 $this->assertEquals(2, $result[2][0]['id']);
246 $this->assertEquals('jwage', $result[2][0]['name']);
248 $this->assertArrayHasKey('article', $result[3]);
249 $this->assertEquals(2, $result[3]['article']['id']);
250 $this->assertEquals('Cool things II.', $result[3]['article']['topic']);
254 * SELECT PARTIAL u.{id, name} AS user, PARTIAL a.{id, topic} AS article
255 * FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
257 public function testSimpleMultipleRootEntityQueryWithAliasedEntities()
259 $rsm = new ResultSetMapping;
260 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', 'user');
261 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsArticle', 'a', 'article');
262 $rsm->addFieldResult('u', 'u__id', 'id');
263 $rsm->addFieldResult('u', 'u__name', 'name');
264 $rsm->addFieldResult('a', 'a__id', 'id');
265 $rsm->addFieldResult('a', 'a__topic', 'topic');
271 'u__name' => 'romanb',
273 'a__topic' => 'Cool things.'
277 'u__name' => 'jwage',
279 'a__topic' => 'Cool things II.'
283 $stmt = new HydratorMockStatement($resultSet);
284 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
285 $result = $hydrator->hydrateAll($stmt, $rsm);
287 $this->assertEquals(4, count($result));
289 $this->assertArrayHasKey('user', $result[0]);
290 $this->assertEquals(1, $result[0]['user']['id']);
291 $this->assertEquals('romanb', $result[0]['user']['name']);
293 $this->assertArrayHasKey('article', $result[1]);
294 $this->assertEquals(1, $result[1]['article']['id']);
295 $this->assertEquals('Cool things.', $result[1]['article']['topic']);
297 $this->assertArrayHasKey('user', $result[2]);
298 $this->assertEquals(2, $result[2]['user']['id']);
299 $this->assertEquals('jwage', $result[2]['user']['name']);
301 $this->assertArrayHasKey('article', $result[3]);
302 $this->assertEquals(2, $result[3]['article']['id']);
303 $this->assertEquals('Cool things II.', $result[3]['article']['topic']);
307 * SELECT PARTIAL u.{id, status}, COUNT(p.phonenumber) AS numPhones
308 * FROM Doctrine\Tests\Models\CMS\CmsUser u
309 * JOIN u.phonenumbers p
310 * GROUP BY u.status, u.id
312 * @dataProvider provideDataForUserEntityResult
314 public function testMixedQueryNormalJoin($userEntityKey)
316 $rsm = new ResultSetMapping;
317 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', $userEntityKey ?: null);
318 $rsm->addFieldResult('u', 'u__id', 'id');
319 $rsm->addFieldResult('u', 'u__status', 'status');
320 $rsm->addScalarResult('sclr0', 'numPhones');
327 'u__status' => 'developer',
332 'u__status' => 'developer',
337 $stmt = new HydratorMockStatement($resultSet);
338 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
339 $result = $hydrator->hydrateAll($stmt, $rsm);
341 $this->assertEquals(2, count($result));
342 $this->assertTrue(is_array($result));
343 $this->assertTrue(is_array($result[0]));
344 $this->assertTrue(is_array($result[1]));
346 // first user => 2 phonenumbers
347 $this->assertArrayHasKey($userEntityKey, $result[0]);
348 $this->assertEquals(2, $result[0]['numPhones']);
350 // second user => 1 phonenumber
351 $this->assertArrayHasKey($userEntityKey, $result[1]);
352 $this->assertEquals(1, $result[1]['numPhones']);
356 * SELECT PARTIAL u.{id, status}, PARTIAL p.{phonenumber}, UPPER(u.name) AS nameUpper
357 * FROM Doctrine\Tests\Models\CMS\CmsUser u
358 * JOIN u.phonenumbers p
360 * @dataProvider provideDataForUserEntityResult
362 public function testMixedQueryFetchJoin($userEntityKey)
364 $rsm = new ResultSetMapping;
365 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', $userEntityKey ?: null);
366 $rsm->addJoinedEntityResult(
367 'Doctrine\Tests\Models\CMS\CmsPhonenumber',
372 $rsm->addFieldResult('u', 'u__id', 'id');
373 $rsm->addFieldResult('u', 'u__status', 'status');
374 $rsm->addScalarResult('sclr0', 'nameUpper');
375 $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
382 'u__status' => 'developer',
384 'p__phonenumber' => '42',
388 'u__status' => 'developer',
390 'p__phonenumber' => '43',
394 'u__status' => 'developer',
396 'p__phonenumber' => '91'
400 $stmt = new HydratorMockStatement($resultSet);
401 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
402 $result = $hydrator->hydrateAll($stmt, $rsm);
404 $this->assertEquals(2, count($result));
406 $this->assertTrue(is_array($result));
407 $this->assertTrue(is_array($result[0]));
408 $this->assertTrue(is_array($result[1]));
410 // first user => 2 phonenumbers
411 $this->assertEquals(2, count($result[0][$userEntityKey]['phonenumbers']));
412 $this->assertEquals('ROMANB', $result[0]['nameUpper']);
414 // second user => 1 phonenumber
415 $this->assertEquals(1, count($result[1][$userEntityKey]['phonenumbers']));
416 $this->assertEquals('JWAGE', $result[1]['nameUpper']);
418 $this->assertEquals(42, $result[0][$userEntityKey]['phonenumbers'][0]['phonenumber']);
419 $this->assertEquals(43, $result[0][$userEntityKey]['phonenumbers'][1]['phonenumber']);
420 $this->assertEquals(91, $result[1][$userEntityKey]['phonenumbers'][0]['phonenumber']);
424 * SELECT PARTIAL u.{id, status}, UPPER(u.name) nameUpper
425 * FROM Doctrine\Tests\Models\CMS\CmsUser u
427 * JOIN u.phonenumbers p
428 * INDEX BY p.phonenumber
430 * @dataProvider provideDataForUserEntityResult
432 public function testMixedQueryFetchJoinCustomIndex($userEntityKey)
434 $rsm = new ResultSetMapping;
435 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', $userEntityKey ?: null);
436 $rsm->addJoinedEntityResult(
437 'Doctrine\Tests\Models\CMS\CmsPhonenumber',
442 $rsm->addFieldResult('u', 'u__id', 'id');
443 $rsm->addFieldResult('u', 'u__status', 'status');
444 $rsm->addScalarResult('sclr0', 'nameUpper');
445 $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
446 $rsm->addIndexBy('u', 'id');
447 $rsm->addIndexBy('p', 'phonenumber');
454 'u__status' => 'developer',
456 'p__phonenumber' => '42',
460 'u__status' => 'developer',
462 'p__phonenumber' => '43',
466 'u__status' => 'developer',
468 'p__phonenumber' => '91'
473 $stmt = new HydratorMockStatement($resultSet);
474 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
475 $result = $hydrator->hydrateAll($stmt, $rsm);
477 $this->assertEquals(2, count($result));
479 $this->assertTrue(is_array($result));
480 $this->assertTrue(is_array($result[1]));
481 $this->assertTrue(is_array($result[2]));
483 // test the scalar values
484 $this->assertEquals('ROMANB', $result[1]['nameUpper']);
485 $this->assertEquals('JWAGE', $result[2]['nameUpper']);
487 // first user => 2 phonenumbers. notice the custom indexing by user id
488 $this->assertEquals(2, count($result[1][$userEntityKey]['phonenumbers']));
490 // second user => 1 phonenumber. notice the custom indexing by user id
491 $this->assertEquals(1, count($result[2][$userEntityKey]['phonenumbers']));
493 // test the custom indexing of the phonenumbers
494 $this->assertTrue(isset($result[1][$userEntityKey]['phonenumbers']['42']));
495 $this->assertTrue(isset($result[1][$userEntityKey]['phonenumbers']['43']));
496 $this->assertTrue(isset($result[2][$userEntityKey]['phonenumbers']['91']));
500 * select u.id, u.status, p.phonenumber, upper(u.name) nameUpper, a.id, a.topic
502 * join u.phonenumbers p
505 * select u.id, u.status, p.phonenumber, upper(u.name) as u__0, a.id, a.topic
507 * inner join PHONENUMBERS p ON u.id = p.user_id
508 * inner join ARTICLES a ON u.id = a.user_id
510 public function testMixedQueryMultipleFetchJoin()
512 $rsm = new ResultSetMapping;
513 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u');
514 $rsm->addJoinedEntityResult(
515 'Doctrine\Tests\Models\CMS\CmsPhonenumber',
520 $rsm->addJoinedEntityResult(
521 'Doctrine\Tests\Models\CMS\CmsArticle',
526 $rsm->addFieldResult('u', 'u__id', 'id');
527 $rsm->addFieldResult('u', 'u__status', 'status');
528 $rsm->addScalarResult('sclr0', 'nameUpper');
529 $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
530 $rsm->addFieldResult('a', 'a__id', 'id');
531 $rsm->addFieldResult('a', 'a__topic', 'topic');
538 'u__status' => 'developer',
540 'p__phonenumber' => '42',
542 'a__topic' => 'Getting things done!'
546 'u__status' => 'developer',
548 'p__phonenumber' => '43',
550 'a__topic' => 'Getting things done!'
554 'u__status' => 'developer',
556 'p__phonenumber' => '42',
558 'a__topic' => 'ZendCon'
562 'u__status' => 'developer',
564 'p__phonenumber' => '43',
566 'a__topic' => 'ZendCon'
570 'u__status' => 'developer',
572 'p__phonenumber' => '91',
578 'u__status' => 'developer',
580 'p__phonenumber' => '91',
586 $stmt = new HydratorMockStatement($resultSet);
587 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
588 $result = $hydrator->hydrateAll($stmt, $rsm);
590 $this->assertEquals(2, count($result));
591 $this->assertTrue(is_array($result));
592 $this->assertTrue(is_array($result[0]));
593 $this->assertTrue(is_array($result[1]));
594 // first user => 2 phonenumbers, 2 articles
595 $this->assertEquals(2, count($result[0][0]['phonenumbers']));
596 $this->assertEquals(2, count($result[0][0]['articles']));
597 $this->assertEquals('ROMANB', $result[0]['nameUpper']);
598 // second user => 1 phonenumber, 2 articles
599 $this->assertEquals(1, count($result[1][0]['phonenumbers']));
600 $this->assertEquals(2, count($result[1][0]['articles']));
601 $this->assertEquals('JWAGE', $result[1]['nameUpper']);
603 $this->assertEquals(42, $result[0][0]['phonenumbers'][0]['phonenumber']);
604 $this->assertEquals(43, $result[0][0]['phonenumbers'][1]['phonenumber']);
605 $this->assertEquals(91, $result[1][0]['phonenumbers'][0]['phonenumber']);
607 $this->assertEquals('Getting things done!', $result[0][0]['articles'][0]['topic']);
608 $this->assertEquals('ZendCon', $result[0][0]['articles'][1]['topic']);
609 $this->assertEquals('LINQ', $result[1][0]['articles'][0]['topic']);
610 $this->assertEquals('PHP6', $result[1][0]['articles'][1]['topic']);
614 * select u.id, u.status, p.phonenumber, upper(u.name) nameUpper, a.id, a.topic,
617 * join u.phonenumbers p
619 * left join a.comments c
621 * select u.id, u.status, p.phonenumber, upper(u.name) as u__0, a.id, a.topic,
624 * inner join PHONENUMBERS p ON u.id = p.user_id
625 * inner join ARTICLES a ON u.id = a.user_id
626 * left outer join COMMENTS c ON a.id = c.article_id
628 public function testMixedQueryMultipleDeepMixedFetchJoin()
631 $rsm = new ResultSetMapping;
632 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u');
633 $rsm->addJoinedEntityResult(
634 'Doctrine\Tests\Models\CMS\CmsPhonenumber',
639 $rsm->addJoinedEntityResult(
640 'Doctrine\Tests\Models\CMS\CmsArticle',
645 $rsm->addJoinedEntityResult(
646 'Doctrine\Tests\Models\CMS\CmsComment',
651 $rsm->addFieldResult('u', 'u__id', 'id');
652 $rsm->addFieldResult('u', 'u__status', 'status');
653 $rsm->addScalarResult('sclr0', 'nameUpper');
654 $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
655 $rsm->addFieldResult('a', 'a__id', 'id');
656 $rsm->addFieldResult('a', 'a__topic', 'topic');
657 $rsm->addFieldResult('c', 'c__id', 'id');
658 $rsm->addFieldResult('c', 'c__topic', 'topic');
665 'u__status' => 'developer',
667 'p__phonenumber' => '42',
669 'a__topic' => 'Getting things done!',
671 'c__topic' => 'First!'
675 'u__status' => 'developer',
677 'p__phonenumber' => '43',
679 'a__topic' => 'Getting things done!',
681 'c__topic' => 'First!'
685 'u__status' => 'developer',
687 'p__phonenumber' => '42',
689 'a__topic' => 'ZendCon',
695 'u__status' => 'developer',
697 'p__phonenumber' => '43',
699 'a__topic' => 'ZendCon',
705 'u__status' => 'developer',
707 'p__phonenumber' => '91',
709 'a__topic' => 'LINQ',
715 'u__status' => 'developer',
717 'p__phonenumber' => '91',
719 'a__topic' => 'PHP6',
725 $stmt = new HydratorMockStatement($resultSet);
726 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
727 $result = $hydrator->hydrateAll($stmt, $rsm);
729 $this->assertEquals(2, count($result));
730 $this->assertTrue(is_array($result));
731 $this->assertTrue(is_array($result[0]));
732 $this->assertTrue(is_array($result[1]));
734 // first user => 2 phonenumbers, 2 articles, 1 comment on first article
735 $this->assertEquals(2, count($result[0][0]['phonenumbers']));
736 $this->assertEquals(2, count($result[0][0]['articles']));
737 $this->assertEquals(1, count($result[0][0]['articles'][0]['comments']));
738 $this->assertEquals('ROMANB', $result[0]['nameUpper']);
739 // second user => 1 phonenumber, 2 articles, no comments
740 $this->assertEquals(1, count($result[1][0]['phonenumbers']));
741 $this->assertEquals(2, count($result[1][0]['articles']));
742 $this->assertEquals('JWAGE', $result[1]['nameUpper']);
744 $this->assertEquals(42, $result[0][0]['phonenumbers'][0]['phonenumber']);
745 $this->assertEquals(43, $result[0][0]['phonenumbers'][1]['phonenumber']);
746 $this->assertEquals(91, $result[1][0]['phonenumbers'][0]['phonenumber']);
748 $this->assertEquals('Getting things done!', $result[0][0]['articles'][0]['topic']);
749 $this->assertEquals('ZendCon', $result[0][0]['articles'][1]['topic']);
750 $this->assertEquals('LINQ', $result[1][0]['articles'][0]['topic']);
751 $this->assertEquals('PHP6', $result[1][0]['articles'][1]['topic']);
753 $this->assertEquals('First!', $result[0][0]['articles'][0]['comments'][0]['topic']);
755 $this->assertTrue(isset($result[0][0]['articles'][0]['comments']));
757 // empty comment collections
758 $this->assertTrue(is_array($result[0][0]['articles'][1]['comments']));
759 $this->assertEquals(0, count($result[0][0]['articles'][1]['comments']));
760 $this->assertTrue(is_array($result[1][0]['articles'][0]['comments']));
761 $this->assertEquals(0, count($result[1][0]['articles'][0]['comments']));
762 $this->assertTrue(is_array($result[1][0]['articles'][1]['comments']));
763 $this->assertEquals(0, count($result[1][0]['articles'][1]['comments']));
767 * Tests that the hydrator does not rely on a particular order of the rows
771 * select c.id, c.position, c.name, b.id, b.position
772 * from \Doctrine\Tests\Models\Forum\ForumCategory c inner join c.boards b
773 * order by c.position asc, b.position asc
775 * Checks whether the boards are correctly assigned to the categories.
777 * The 'evil' result set that confuses the object population is displayed below.
779 * c.id | c.position | c.name | boardPos | b.id | b.category_id (just for clarity)
780 * 1 | 0 | First | 0 | 1 | 1
781 * 2 | 0 | Second | 0 | 2 | 2 <--
782 * 1 | 0 | First | 1 | 3 | 1
783 * 1 | 0 | First | 2 | 4 | 1
785 public function testEntityQueryCustomResultSetOrder()
787 $rsm = new ResultSetMapping;
788 $rsm->addEntityResult('Doctrine\Tests\Models\Forum\ForumCategory', 'c');
789 $rsm->addJoinedEntityResult(
790 'Doctrine\Tests\Models\Forum\ForumBoard',
796 $rsm->addFieldResult('c', 'c__id', 'id');
797 $rsm->addFieldResult('c', 'c__position', 'position');
798 $rsm->addFieldResult('c', 'c__name', 'name');
799 $rsm->addFieldResult('b', 'b__id', 'id');
800 $rsm->addFieldResult('b', 'b__position', 'position');
806 'c__position' => '0',
807 'c__name' => 'First',
809 'b__position' => '0',
810 //'b__category_id' => '1'
814 'c__position' => '0',
815 'c__name' => 'Second',
817 'b__position' => '0',
818 //'b__category_id' => '2'
822 'c__position' => '0',
823 'c__name' => 'First',
825 'b__position' => '1',
826 //'b__category_id' => '1'
830 'c__position' => '0',
831 'c__name' => 'First',
833 'b__position' => '2',
834 //'b__category_id' => '1'
838 $stmt = new HydratorMockStatement($resultSet);
839 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
840 $result = $hydrator->hydrateAll($stmt, $rsm);
842 $this->assertEquals(2, count($result));
843 $this->assertTrue(is_array($result));
844 $this->assertTrue(is_array($result[0]));
845 $this->assertTrue(is_array($result[1]));
846 $this->assertTrue(isset($result[0]['boards']));
847 $this->assertEquals(3, count($result[0]['boards']));
848 $this->assertTrue(isset($result[1]['boards']));
849 $this->assertEquals(1, count($result[1]['boards']));
853 * SELECT PARTIAL u.{id,status}, a.id, a.topic, c.id as cid, c.topic as ctopic
854 * FROM Doctrine\Tests\Models\CMS\CmsUser u
855 * LEFT JOIN u.articles a
856 * LEFT JOIN a.comments c
858 * @dataProvider provideDataForUserEntityResult
860 public function testChainedJoinWithScalars($entityKey)
862 $rsm = new ResultSetMapping;
863 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', $entityKey ?: null);
864 $rsm->addFieldResult('u', 'u__id', 'id');
865 $rsm->addFieldResult('u', 'u__status', 'status');
866 $rsm->addScalarResult('a__id', 'id');
867 $rsm->addScalarResult('a__topic', 'topic');
868 $rsm->addScalarResult('c__id', 'cid');
869 $rsm->addScalarResult('c__topic', 'ctopic');
876 'u__status' => 'developer',
878 'a__topic' => 'The First',
880 'c__topic' => 'First Comment'
884 'u__status' => 'developer',
886 'a__topic' => 'The First',
888 'c__topic' => 'Second Comment'
892 'u__status' => 'developer',
894 'a__topic' => 'The Answer',
900 $stmt = new HydratorMockStatement($resultSet);
901 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
902 $result = $hydrator->hydrateAll($stmt, $rsm);
904 $this->assertEquals(3, count($result));
906 $this->assertEquals(2, count($result[0][$entityKey])); // User array
907 $this->assertEquals(1, $result[0]['id']);
908 $this->assertEquals('The First', $result[0]['topic']);
909 $this->assertEquals(1, $result[0]['cid']);
910 $this->assertEquals('First Comment', $result[0]['ctopic']);
912 $this->assertEquals(2, count($result[1][$entityKey])); // User array, duplicated
913 $this->assertEquals(1, $result[1]['id']); // duplicated
914 $this->assertEquals('The First', $result[1]['topic']); // duplicated
915 $this->assertEquals(2, $result[1]['cid']);
916 $this->assertEquals('Second Comment', $result[1]['ctopic']);
918 $this->assertEquals(2, count($result[2][$entityKey])); // User array, duplicated
919 $this->assertEquals(42, $result[2]['id']);
920 $this->assertEquals('The Answer', $result[2]['topic']);
921 $this->assertNull($result[2]['cid']);
922 $this->assertNull($result[2]['ctopic']);
926 * SELECT PARTIAL u.{id, status}
927 * FROM Doctrine\Tests\Models\CMS\CmsUser u
929 public function testResultIteration()
931 $rsm = new ResultSetMapping;
932 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u');
933 $rsm->addFieldResult('u', 'u__id', 'id');
934 $rsm->addFieldResult('u', 'u__name', 'name');
940 'u__name' => 'romanb'
948 $stmt = new HydratorMockStatement($resultSet);
949 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
950 $iterator = $hydrator->iterate($stmt, $rsm);
953 while (($row = $iterator->next()) !== false) {
954 $this->assertEquals(1, count($row));
955 $this->assertTrue(is_array($row[0]));
958 $this->assertEquals(1, $row[0]['id']);
959 $this->assertEquals('romanb', $row[0]['name']);
960 } else if ($rowNum == 1) {
961 $this->assertEquals(2, $row[0]['id']);
962 $this->assertEquals('jwage', $row[0]['name']);
970 * SELECT PARTIAL u.{id, status}
971 * FROM Doctrine\Tests\Models\CMS\CmsUser u
973 public function testResultIterationWithAliasedUserEntity()
975 $rsm = new ResultSetMapping;
976 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', 'user');
977 $rsm->addFieldResult('u', 'u__id', 'id');
978 $rsm->addFieldResult('u', 'u__name', 'name');
984 'u__name' => 'romanb'
992 $stmt = new HydratorMockStatement($resultSet);
993 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
994 $iterator = $hydrator->iterate($stmt, $rsm);
997 while (($row = $iterator->next()) !== false) {
998 $this->assertEquals(1, count($row));
999 $this->assertArrayHasKey(0, $row);
1000 $this->assertArrayHasKey('user', $row[0]);
1003 $this->assertEquals(1, $row[0]['user']['id']);
1004 $this->assertEquals('romanb', $row[0]['user']['name']);
1005 } else if ($rowNum == 1) {
1006 $this->assertEquals(2, $row[0]['user']['id']);
1007 $this->assertEquals('jwage', $row[0]['user']['name']);
1015 * SELECT PARTIAL u.{id, name}
1016 * FROM Doctrine\Tests\Models\CMS\CmsUser u
1020 public function testSkipUnknownColumns()
1022 $rsm = new ResultSetMapping;
1023 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u');
1024 $rsm->addFieldResult('u', 'u__id', 'id');
1025 $rsm->addFieldResult('u', 'u__name', 'name');
1031 'u__name' => 'romanb',
1032 'foo' => 'bar', // unknown!
1036 $stmt = new HydratorMockStatement($resultSet);
1037 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
1038 $result = $hydrator->hydrateAll($stmt, $rsm);
1040 $this->assertEquals(1, count($result));
1041 $this->assertArrayHasKey('id', $result[0]);
1042 $this->assertArrayHasKey('name', $result[0]);
1043 $this->assertArrayNotHasKey('foo', $result[0]);
1047 * SELECT PARTIAL u.{id, status}, UPPER(u.name) AS nameUpper
1048 * FROM Doctrine\Tests\Models\CMS\CmsUser u
1051 * @dataProvider provideDataForUserEntityResult
1053 public function testMissingIdForRootEntity($userEntityKey)
1055 $rsm = new ResultSetMapping;
1056 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', $userEntityKey ?: null);
1057 $rsm->addFieldResult('u', 'u__id', 'id');
1058 $rsm->addFieldResult('u', 'u__status', 'status');
1059 $rsm->addScalarResult('sclr0', 'nameUpper');
1066 'u__status' => 'developer',
1067 'sclr0' => 'ROMANB',
1071 'u__status' => null,
1072 'sclr0' => 'ROMANB',
1076 'u__status' => 'developer',
1081 'u__status' => null,
1086 $stmt = new HydratorMockStatement($resultSet);
1087 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
1088 $result = $hydrator->hydrateAll($stmt, $rsm);
1090 $this->assertEquals(4, count($result), "Should hydrate four results.");
1092 $this->assertEquals('ROMANB', $result[0]['nameUpper']);
1093 $this->assertEquals('ROMANB', $result[1]['nameUpper']);
1094 $this->assertEquals('JWAGE', $result[2]['nameUpper']);
1095 $this->assertEquals('JWAGE', $result[3]['nameUpper']);
1097 $this->assertEquals(array('id' => 1, 'status' => 'developer'), $result[0][$userEntityKey]);
1098 $this->assertNull($result[1][$userEntityKey]);
1099 $this->assertEquals(array('id' => 2, 'status' => 'developer'), $result[2][$userEntityKey]);
1100 $this->assertNull($result[3][$userEntityKey]);
1104 * SELECT PARTIAL u.{id, status}, UPPER(u.name) AS nameUpper
1105 * FROM Doctrine\Tests\Models\CMS\CmsUser u
1109 * @dataProvider provideDataForUserEntityResult
1111 public function testIndexByAndMixedResult($userEntityKey)
1113 $rsm = new ResultSetMapping;
1114 $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', $userEntityKey ?: null);
1115 $rsm->addFieldResult('u', 'u__id', 'id');
1116 $rsm->addFieldResult('u', 'u__status', 'status');
1117 $rsm->addScalarResult('sclr0', 'nameUpper');
1118 $rsm->addIndexBy('u', 'id');
1125 'u__status' => 'developer',
1126 'sclr0' => 'ROMANB',
1130 'u__status' => 'developer',
1135 $stmt = new HydratorMockStatement($resultSet);
1136 $hydrator = new \Doctrine\ORM\Internal\Hydration\ArrayHydrator($this->_em);
1137 $result = $hydrator->hydrateAll($stmt, $rsm);
1139 $this->assertEquals(2, count($result));
1141 $this->assertTrue(isset($result[1]));
1142 $this->assertEquals(1, $result[1][$userEntityKey]['id']);
1144 $this->assertTrue(isset($result[2]));
1145 $this->assertEquals(2, $result[2][$userEntityKey]['id']);