Failed Conditions
Pull Request — master (#7885)
by Šimon
06:26
created

testMixedQueryFetchJoinCustomIndex()   A

Complexity

Conditions 2
Paths 1

Size

Total Lines 68
Code Lines 43

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 43
nc 1
nop 1
dl 0
loc 68
rs 9.232
c 0
b 0
f 0

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
declare(strict_types=1);
4
5
namespace Doctrine\Tests\ORM\Hydration;
6
7
use Doctrine\DBAL\Types\Type;
8
use Doctrine\ORM\Internal\Hydration\ObjectHydrator;
9
use Doctrine\ORM\Mapping\FetchMode;
10
use Doctrine\ORM\PersistentCollection;
11
use Doctrine\ORM\Proxy\Factory\ProxyFactory;
12
use Doctrine\ORM\Query;
13
use Doctrine\ORM\Query\ResultSetMapping;
14
use Doctrine\Tests\Mocks\HydratorMockStatement;
15
use Doctrine\Tests\Models\CMS\CmsAddress;
16
use Doctrine\Tests\Models\CMS\CmsArticle;
17
use Doctrine\Tests\Models\CMS\CmsComment;
18
use Doctrine\Tests\Models\CMS\CmsGroup;
19
use Doctrine\Tests\Models\CMS\CmsPhonenumber;
20
use Doctrine\Tests\Models\CMS\CmsUser;
21
use Doctrine\Tests\Models\Company\CompanyEmployee;
22
use Doctrine\Tests\Models\Company\CompanyFixContract;
23
use Doctrine\Tests\Models\Company\CompanyPerson;
24
use Doctrine\Tests\Models\ECommerce\ECommerceProduct;
25
use Doctrine\Tests\Models\ECommerce\ECommerceShipping;
26
use Doctrine\Tests\Models\Forum\ForumBoard;
27
use Doctrine\Tests\Models\Forum\ForumCategory;
28
use Doctrine\Tests\Models\Hydration\EntityWithArrayDefaultArrayValueM2M;
29
use Doctrine\Tests\Models\Hydration\SimpleEntity;
30
use ProxyManager\Configuration;
31
use ProxyManager\Factory\LazyLoadingGhostFactory;
32
33
class ObjectHydratorTest extends HydrationTestCase
34
{
35
    public function provideDataForUserEntityResult()
36
    {
37
        return [
38
            [0],
39
            ['user'],
40
        ];
41
    }
42
43
    public function provideDataForMultipleRootEntityResult()
44
    {
45
        return [
46
            [0, 0],
47
            ['user', 0],
48
            [0, 'article'],
49
            ['user', 'article'],
50
        ];
51
    }
52
53
    public function provideDataForProductEntityResult()
54
    {
55
        return [
56
            [0],
57
            ['product'],
58
        ];
59
    }
60
61
    /**
62
     * SELECT PARTIAL u.{id,name}
63
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
64
     */
65
    public function testSimpleEntityQuery() : void
66
    {
67
        $rsm = new ResultSetMapping();
68
        $rsm->addEntityResult(CmsUser::class, 'u');
69
        $rsm->addFieldResult('u', 'u__id', 'id');
70
        $rsm->addFieldResult('u', 'u__name', 'name');
71
72
        // Faked result set
73
        $resultSet = [
74
            [
75
                'u__id' => '1',
76
                'u__name' => 'romanb',
77
            ],
78
            [
79
                'u__id' => '2',
80
                'u__name' => 'jwage',
81
            ],
82
        ];
83
84
        $stmt     = new HydratorMockStatement($resultSet);
85
        $hydrator = new ObjectHydrator($this->em);
86
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
87
88
        self::assertCount(2, $result);
89
90
        self::assertInstanceOf(CmsUser::class, $result[0]);
91
        self::assertInstanceOf(CmsUser::class, $result[1]);
92
93
        self::assertEquals(1, $result[0]->id);
94
        self::assertEquals('romanb', $result[0]->name);
95
96
        self::assertEquals(2, $result[1]->id);
97
        self::assertEquals('jwage', $result[1]->name);
98
    }
99
100
    /**
101
     * SELECT PARTIAL u.{id,name} AS user
102
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
103
     */
104
    public function testSimpleEntityQueryWithAliasedUserEntity() : void
105
    {
106
        $rsm = new ResultSetMapping();
107
        $rsm->addEntityResult(CmsUser::class, 'u', 'user');
108
        $rsm->addFieldResult('u', 'u__id', 'id');
109
        $rsm->addFieldResult('u', 'u__name', 'name');
110
111
        // Faked result set
112
        $resultSet = [
113
            [
114
                'u__id' => '1',
115
                'u__name' => 'romanb',
116
            ],
117
            [
118
                'u__id' => '2',
119
                'u__name' => 'jwage',
120
            ],
121
        ];
122
123
        $stmt     = new HydratorMockStatement($resultSet);
124
        $hydrator = new ObjectHydrator($this->em);
125
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
126
127
        self::assertCount(2, $result);
128
129
        self::assertArrayHasKey('user', $result[0]);
130
        self::assertInstanceOf(CmsUser::class, $result[0]['user']);
131
132
        self::assertArrayHasKey('user', $result[1]);
133
        self::assertInstanceOf(CmsUser::class, $result[1]['user']);
134
135
        self::assertEquals(1, $result[0]['user']->id);
136
        self::assertEquals('romanb', $result[0]['user']->name);
137
138
        self::assertEquals(2, $result[1]['user']->id);
139
        self::assertEquals('jwage', $result[1]['user']->name);
140
    }
141
142
    /**
143
     * SELECT PARTIAL u.{id, name}, PARTIAL a.{id, topic}
144
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
145
     */
146
    public function testSimpleMultipleRootEntityQuery() : void
147
    {
148
        $rsm = new ResultSetMapping();
149
        $rsm->addEntityResult(CmsUser::class, 'u');
150
        $rsm->addEntityResult(CmsArticle::class, 'a');
151
        $rsm->addFieldResult('u', 'u__id', 'id');
152
        $rsm->addFieldResult('u', 'u__name', 'name');
153
        $rsm->addFieldResult('a', 'a__id', 'id');
154
        $rsm->addFieldResult('a', 'a__topic', 'topic');
155
156
        // Faked result set
157
        $resultSet = [
158
            [
159
                'u__id' => '1',
160
                'u__name' => 'romanb',
161
                'a__id' => '1',
162
                'a__topic' => 'Cool things.',
163
            ],
164
            [
165
                'u__id' => '2',
166
                'u__name' => 'jwage',
167
                'a__id' => '2',
168
                'a__topic' => 'Cool things II.',
169
            ],
170
        ];
171
172
        $stmt     = new HydratorMockStatement($resultSet);
173
        $hydrator = new ObjectHydrator($this->em);
174
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
175
176
        self::assertCount(4, $result);
177
178
        self::assertInstanceOf(CmsUser::class, $result[0]);
179
        self::assertInstanceOf(CmsArticle::class, $result[1]);
180
        self::assertInstanceOf(CmsUser::class, $result[2]);
181
        self::assertInstanceOf(CmsArticle::class, $result[3]);
182
183
        self::assertEquals(1, $result[0]->id);
184
        self::assertEquals('romanb', $result[0]->name);
185
186
        self::assertEquals(1, $result[1]->id);
187
        self::assertEquals('Cool things.', $result[1]->topic);
188
189
        self::assertEquals(2, $result[2]->id);
190
        self::assertEquals('jwage', $result[2]->name);
191
192
        self::assertEquals(2, $result[3]->id);
193
        self::assertEquals('Cool things II.', $result[3]->topic);
194
    }
195
196
    /**
197
     * SELECT PARTIAL u.{id, name} AS user, PARTIAL a.{id, topic}
198
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
199
     */
200
    public function testSimpleMultipleRootEntityQueryWithAliasedUserEntity() : void
201
    {
202
        $rsm = new ResultSetMapping();
203
        $rsm->addEntityResult(CmsUser::class, 'u', 'user');
204
        $rsm->addEntityResult(CmsArticle::class, 'a');
205
        $rsm->addFieldResult('u', 'u__id', 'id');
206
        $rsm->addFieldResult('u', 'u__name', 'name');
207
        $rsm->addFieldResult('a', 'a__id', 'id');
208
        $rsm->addFieldResult('a', 'a__topic', 'topic');
209
210
        // Faked result set
211
        $resultSet = [
212
            [
213
                'u__id' => '1',
214
                'u__name' => 'romanb',
215
                'a__id' => '1',
216
                'a__topic' => 'Cool things.',
217
            ],
218
            [
219
                'u__id' => '2',
220
                'u__name' => 'jwage',
221
                'a__id' => '2',
222
                'a__topic' => 'Cool things II.',
223
            ],
224
        ];
225
226
        $stmt     = new HydratorMockStatement($resultSet);
227
        $hydrator = new ObjectHydrator($this->em);
228
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
229
230
        self::assertCount(4, $result);
231
232
        self::assertArrayHasKey('user', $result[0]);
233
        self::assertArrayNotHasKey(0, $result[0]);
234
        self::assertInstanceOf(CmsUser::class, $result[0]['user']);
235
        self::assertEquals(1, $result[0]['user']->id);
236
        self::assertEquals('romanb', $result[0]['user']->name);
237
238
        self::assertArrayHasKey(0, $result[1]);
239
        self::assertArrayNotHasKey('user', $result[1]);
240
        self::assertInstanceOf(CmsArticle::class, $result[1][0]);
241
        self::assertEquals(1, $result[1][0]->id);
242
        self::assertEquals('Cool things.', $result[1][0]->topic);
243
244
        self::assertArrayHasKey('user', $result[2]);
245
        self::assertArrayNotHasKey(0, $result[2]);
246
        self::assertInstanceOf(CmsUser::class, $result[2]['user']);
247
        self::assertEquals(2, $result[2]['user']->id);
248
        self::assertEquals('jwage', $result[2]['user']->name);
249
250
        self::assertArrayHasKey(0, $result[3]);
251
        self::assertArrayNotHasKey('user', $result[3]);
252
        self::assertInstanceOf(CmsArticle::class, $result[3][0]);
253
        self::assertEquals(2, $result[3][0]->id);
254
        self::assertEquals('Cool things II.', $result[3][0]->topic);
255
    }
256
257
    /**
258
     * SELECT PARTIAL u.{id, name}, PARTIAL a.{id, topic} AS article
259
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
260
     */
261
    public function testSimpleMultipleRootEntityQueryWithAliasedArticleEntity() : void
262
    {
263
        $rsm = new ResultSetMapping();
264
        $rsm->addEntityResult(CmsUser::class, 'u');
265
        $rsm->addEntityResult(CmsArticle::class, 'a', 'article');
266
        $rsm->addFieldResult('u', 'u__id', 'id');
267
        $rsm->addFieldResult('u', 'u__name', 'name');
268
        $rsm->addFieldResult('a', 'a__id', 'id');
269
        $rsm->addFieldResult('a', 'a__topic', 'topic');
270
271
        // Faked result set
272
        $resultSet = [
273
            [
274
                'u__id' => '1',
275
                'u__name' => 'romanb',
276
                'a__id' => '1',
277
                'a__topic' => 'Cool things.',
278
            ],
279
            [
280
                'u__id' => '2',
281
                'u__name' => 'jwage',
282
                'a__id' => '2',
283
                'a__topic' => 'Cool things II.',
284
            ],
285
        ];
286
287
        $stmt     = new HydratorMockStatement($resultSet);
288
        $hydrator = new ObjectHydrator($this->em);
289
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
290
291
        self::assertCount(4, $result);
292
293
        self::assertArrayHasKey(0, $result[0]);
294
        self::assertArrayNotHasKey('article', $result[0]);
295
        self::assertInstanceOf(CmsUser::class, $result[0][0]);
296
        self::assertEquals(1, $result[0][0]->id);
297
        self::assertEquals('romanb', $result[0][0]->name);
298
299
        self::assertArrayHasKey('article', $result[1]);
300
        self::assertArrayNotHasKey(0, $result[1]);
301
        self::assertInstanceOf(CmsArticle::class, $result[1]['article']);
302
        self::assertEquals(1, $result[1]['article']->id);
303
        self::assertEquals('Cool things.', $result[1]['article']->topic);
304
305
        self::assertArrayHasKey(0, $result[2]);
306
        self::assertArrayNotHasKey('article', $result[2]);
307
        self::assertInstanceOf(CmsUser::class, $result[2][0]);
308
        self::assertEquals(2, $result[2][0]->id);
309
        self::assertEquals('jwage', $result[2][0]->name);
310
311
        self::assertArrayHasKey('article', $result[3]);
312
        self::assertArrayNotHasKey(0, $result[3]);
313
        self::assertInstanceOf(CmsArticle::class, $result[3]['article']);
314
        self::assertEquals(2, $result[3]['article']->id);
315
        self::assertEquals('Cool things II.', $result[3]['article']->topic);
316
    }
317
318
    /**
319
     * SELECT PARTIAL u.{id, name} AS user, PARTIAL a.{id, topic} AS article
320
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u, Doctrine\Tests\Models\CMS\CmsArticle a
321
     */
322
    public function testSimpleMultipleRootEntityQueryWithAliasedEntities() : void
323
    {
324
        $rsm = new ResultSetMapping();
325
        $rsm->addEntityResult(CmsUser::class, 'u', 'user');
326
        $rsm->addEntityResult(CmsArticle::class, 'a', 'article');
327
        $rsm->addFieldResult('u', 'u__id', 'id');
328
        $rsm->addFieldResult('u', 'u__name', 'name');
329
        $rsm->addFieldResult('a', 'a__id', 'id');
330
        $rsm->addFieldResult('a', 'a__topic', 'topic');
331
332
        // Faked result set
333
        $resultSet = [
334
            [
335
                'u__id' => '1',
336
                'u__name' => 'romanb',
337
                'a__id' => '1',
338
                'a__topic' => 'Cool things.',
339
            ],
340
            [
341
                'u__id' => '2',
342
                'u__name' => 'jwage',
343
                'a__id' => '2',
344
                'a__topic' => 'Cool things II.',
345
            ],
346
        ];
347
348
        $stmt     = new HydratorMockStatement($resultSet);
349
        $hydrator = new ObjectHydrator($this->em);
350
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
351
352
        self::assertCount(4, $result);
353
354
        self::assertArrayHasKey('user', $result[0]);
355
        self::assertArrayNotHasKey('article', $result[0]);
356
        self::assertInstanceOf(CmsUser::class, $result[0]['user']);
357
        self::assertEquals(1, $result[0]['user']->id);
358
        self::assertEquals('romanb', $result[0]['user']->name);
359
360
        self::assertArrayHasKey('article', $result[1]);
361
        self::assertArrayNotHasKey('user', $result[1]);
362
        self::assertInstanceOf(CmsArticle::class, $result[1]['article']);
363
        self::assertEquals(1, $result[1]['article']->id);
364
        self::assertEquals('Cool things.', $result[1]['article']->topic);
365
366
        self::assertArrayHasKey('user', $result[2]);
367
        self::assertArrayNotHasKey('article', $result[2]);
368
        self::assertInstanceOf(CmsUser::class, $result[2]['user']);
369
        self::assertEquals(2, $result[2]['user']->id);
370
        self::assertEquals('jwage', $result[2]['user']->name);
371
372
        self::assertArrayHasKey('article', $result[3]);
373
        self::assertArrayNotHasKey('user', $result[3]);
374
        self::assertInstanceOf(CmsArticle::class, $result[3]['article']);
375
        self::assertEquals(2, $result[3]['article']->id);
376
        self::assertEquals('Cool things II.', $result[3]['article']->topic);
377
    }
378
379
    /**
380
     * SELECT PARTIAL u.{id, status}, COUNT(p.phonenumber) numPhones
381
     *   FROM User u
382
     *   JOIN u.phonenumbers p
383
     *  GROUP BY u.id
384
     *
385
     * @dataProvider provideDataForUserEntityResult
386
     */
387
    public function testMixedQueryNormalJoin($userEntityKey) : void
388
    {
389
        $rsm = new ResultSetMapping();
390
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
391
        $rsm->addFieldResult('u', 'u__id', 'id');
392
        $rsm->addFieldResult('u', 'u__status', 'status');
393
        $rsm->addScalarResult('sclr0', 'numPhones', Type::getType('integer'));
394
395
        // Faked result set
396
        $resultSet = [
397
            //row1
398
            [
399
                'u__id' => '1',
400
                'u__status' => 'developer',
401
                'sclr0' => '2',
402
            ],
403
            [
404
                'u__id' => '2',
405
                'u__status' => 'developer',
406
                'sclr0' => '1',
407
            ],
408
        ];
409
410
        $stmt     = new HydratorMockStatement($resultSet);
411
        $hydrator = new ObjectHydrator($this->em);
412
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
413
414
        self::assertCount(2, $result);
415
416
        self::assertInternalType('array', $result);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

416
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
417
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

417
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
418
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

418
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
419
420
        // first user => 2 phonenumbers
421
        self::assertEquals(2, $result[0]['numPhones']);
422
        self::assertInstanceOf(CmsUser::class, $result[0][$userEntityKey]);
423
424
        // second user => 1 phonenumber
425
        self::assertEquals(1, $result[1]['numPhones']);
426
        self::assertInstanceOf(CmsUser::class, $result[1][$userEntityKey]);
427
    }
428
429
    /**
430
     * SELECT PARTIAL u.{id, status}, PARTIAL p.{phonenumber}, UPPER(u.name) nameUpper
431
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
432
     *   JOIN u.phonenumbers p
433
     *
434
     * @dataProvider provideDataForUserEntityResult
435
     */
436
    public function testMixedQueryFetchJoin($userEntityKey) : void
437
    {
438
        $rsm = new ResultSetMapping();
439
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
440
        $rsm->addJoinedEntityResult(
441
            CmsPhonenumber::class,
442
            'p',
443
            'u',
444
            'phonenumbers'
445
        );
446
        $rsm->addFieldResult('u', 'u__id', 'id');
447
        $rsm->addFieldResult('u', 'u__status', 'status');
448
        $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
449
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
450
451
        // Faked result set
452
        $resultSet = [
453
            //row1
454
            [
455
                'u__id' => '1',
456
                'u__status' => 'developer',
457
                'p__phonenumber' => '42',
458
                'sclr0' => 'ROMANB',
459
            ],
460
            [
461
                'u__id' => '1',
462
                'u__status' => 'developer',
463
                'p__phonenumber' => '43',
464
                'sclr0' => 'ROMANB',
465
            ],
466
            [
467
                'u__id' => '2',
468
                'u__status' => 'developer',
469
                'p__phonenumber' => '91',
470
                'sclr0' => 'JWAGE',
471
            ],
472
        ];
473
474
        $stmt     = new HydratorMockStatement($resultSet);
475
        $hydrator = new ObjectHydrator($this->em);
476
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
477
478
        self::assertCount(2, $result);
479
480
        self::assertInternalType('array', $result);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

480
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
481
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

481
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
482
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

482
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
483
484
        self::assertInstanceOf(CmsUser::class, $result[0][$userEntityKey]);
485
        self::assertInstanceOf(PersistentCollection::class, $result[0][$userEntityKey]->phonenumbers);
486
        self::assertInstanceOf(CmsPhonenumber::class, $result[0][$userEntityKey]->phonenumbers[0]);
487
488
        self::assertInstanceOf(CmsUser::class, $result[1][$userEntityKey]);
489
        self::assertInstanceOf(PersistentCollection::class, $result[1][$userEntityKey]->phonenumbers);
490
        self::assertInstanceOf(CmsPhonenumber::class, $result[0][$userEntityKey]->phonenumbers[1]);
491
492
        // first user => 2 phonenumbers
493
        self::assertCount(2, $result[0][$userEntityKey]->phonenumbers);
494
        self::assertEquals('ROMANB', $result[0]['nameUpper']);
495
496
        // second user => 1 phonenumber
497
        self::assertCount(1, $result[1][$userEntityKey]->phonenumbers);
498
        self::assertEquals('JWAGE', $result[1]['nameUpper']);
499
500
        self::assertEquals(42, $result[0][$userEntityKey]->phonenumbers[0]->phonenumber);
501
        self::assertEquals(43, $result[0][$userEntityKey]->phonenumbers[1]->phonenumber);
502
        self::assertEquals(91, $result[1][$userEntityKey]->phonenumbers[0]->phonenumber);
503
    }
504
505
    /**
506
     * SELECT u, p, UPPER(u.name) nameUpper
507
     *   FROM User u
508
     *        INDEX BY u.id
509
     *   JOIN u.phonenumbers p
510
     *        INDEX BY p.phonenumber
511
     *
512
     * @dataProvider provideDataForUserEntityResult
513
     */
514
    public function testMixedQueryFetchJoinCustomIndex($userEntityKey) : void
515
    {
516
        $rsm = new ResultSetMapping();
517
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
518
        $rsm->addJoinedEntityResult(
519
            CmsPhonenumber::class,
520
            'p',
521
            'u',
522
            'phonenumbers'
523
        );
524
        $rsm->addFieldResult('u', 'u__id', 'id');
525
        $rsm->addFieldResult('u', 'u__status', 'status');
526
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
527
        $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
528
        $rsm->addIndexBy('u', 'id');
529
        $rsm->addIndexBy('p', 'phonenumber');
530
531
        // Faked result set
532
        $resultSet = [
533
            //row1
534
            [
535
                'u__id' => '1',
536
                'u__status' => 'developer',
537
                'sclr0' => 'ROMANB',
538
                'p__phonenumber' => '42',
539
            ],
540
            [
541
                'u__id' => '1',
542
                'u__status' => 'developer',
543
                'sclr0' => 'ROMANB',
544
                'p__phonenumber' => '43',
545
            ],
546
            [
547
                'u__id' => '2',
548
                'u__status' => 'developer',
549
                'sclr0' => 'JWAGE',
550
                'p__phonenumber' => '91',
551
            ],
552
        ];
553
554
        $stmt     = new HydratorMockStatement($resultSet);
555
        $hydrator = new ObjectHydrator($this->em);
556
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
557
558
        self::assertCount(2, $result);
559
560
        self::assertInternalType('array', $result);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

560
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
561
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

561
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
562
        self::assertInternalType('array', $result[2]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

562
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[2]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
563
564
        // test the scalar values
565
        self::assertEquals('ROMANB', $result[1]['nameUpper']);
566
        self::assertEquals('JWAGE', $result[2]['nameUpper']);
567
568
        self::assertInstanceOf(CmsUser::class, $result[1][$userEntityKey]);
569
        self::assertInstanceOf(CmsUser::class, $result[2][$userEntityKey]);
570
        self::assertInstanceOf(PersistentCollection::class, $result[1][$userEntityKey]->phonenumbers);
571
572
        // first user => 2 phonenumbers. notice the custom indexing by user id
573
        self::assertCount(2, $result[1][$userEntityKey]->phonenumbers);
574
575
        // second user => 1 phonenumber. notice the custom indexing by user id
576
        self::assertCount(1, $result[2][$userEntityKey]->phonenumbers);
577
578
        // test the custom indexing of the phonenumbers
579
        self::assertTrue(isset($result[1][$userEntityKey]->phonenumbers['42']));
580
        self::assertTrue(isset($result[1][$userEntityKey]->phonenumbers['43']));
581
        self::assertTrue(isset($result[2][$userEntityKey]->phonenumbers['91']));
582
    }
583
584
    /**
585
     * SELECT u, p, UPPER(u.name) nameUpper, a
586
     *   FROM User u
587
     *   JOIN u.phonenumbers p
588
     *   JOIN u.articles a
589
     *
590
     * @dataProvider provideDataForUserEntityResult
591
     */
592
    public function testMixedQueryMultipleFetchJoin($userEntityKey) : void
593
    {
594
        $rsm = new ResultSetMapping();
595
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
596
        $rsm->addJoinedEntityResult(
597
            CmsPhonenumber::class,
598
            'p',
599
            'u',
600
            'phonenumbers'
601
        );
602
        $rsm->addJoinedEntityResult(
603
            CmsArticle::class,
604
            'a',
605
            'u',
606
            'articles'
607
        );
608
        $rsm->addFieldResult('u', 'u__id', 'id');
609
        $rsm->addFieldResult('u', 'u__status', 'status');
610
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
611
        $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
612
        $rsm->addFieldResult('a', 'a__id', 'id');
613
        $rsm->addFieldResult('a', 'a__topic', 'topic');
614
615
        // Faked result set
616
        $resultSet = [
617
            //row1
618
            [
619
                'u__id' => '1',
620
                'u__status' => 'developer',
621
                'sclr0' => 'ROMANB',
622
                'p__phonenumber' => '42',
623
                'a__id' => '1',
624
                'a__topic' => 'Getting things done!',
625
            ],
626
            [
627
                'u__id' => '1',
628
                'u__status' => 'developer',
629
                'sclr0' => 'ROMANB',
630
                'p__phonenumber' => '43',
631
                'a__id' => '1',
632
                'a__topic' => 'Getting things done!',
633
            ],
634
            [
635
                'u__id' => '1',
636
                'u__status' => 'developer',
637
                'sclr0' => 'ROMANB',
638
                'p__phonenumber' => '42',
639
                'a__id' => '2',
640
                'a__topic' => 'ZendCon',
641
            ],
642
            [
643
                'u__id' => '1',
644
                'u__status' => 'developer',
645
                'sclr0' => 'ROMANB',
646
                'p__phonenumber' => '43',
647
                'a__id' => '2',
648
                'a__topic' => 'ZendCon',
649
            ],
650
            [
651
                'u__id' => '2',
652
                'u__status' => 'developer',
653
                'sclr0' => 'JWAGE',
654
                'p__phonenumber' => '91',
655
                'a__id' => '3',
656
                'a__topic' => 'LINQ',
657
            ],
658
            [
659
                'u__id' => '2',
660
                'u__status' => 'developer',
661
                'sclr0' => 'JWAGE',
662
                'p__phonenumber' => '91',
663
                'a__id' => '4',
664
                'a__topic' => 'PHP7',
665
            ],
666
        ];
667
668
        $stmt     = new HydratorMockStatement($resultSet);
669
        $hydrator = new ObjectHydrator($this->em);
670
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
671
672
        self::assertCount(2, $result);
673
674
        self::assertInternalType('array', $result);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

674
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
675
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

675
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
676
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

676
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
677
678
        self::assertInstanceOf(CmsUser::class, $result[0][$userEntityKey]);
679
        self::assertInstanceOf(PersistentCollection::class, $result[0][$userEntityKey]->phonenumbers);
680
        self::assertInstanceOf(CmsPhonenumber::class, $result[0][$userEntityKey]->phonenumbers[0]);
681
        self::assertInstanceOf(CmsPhonenumber::class, $result[0][$userEntityKey]->phonenumbers[1]);
682
        self::assertInstanceOf(PersistentCollection::class, $result[0][$userEntityKey]->articles);
683
        self::assertInstanceOf(CmsArticle::class, $result[0][$userEntityKey]->articles[0]);
684
        self::assertInstanceOf(CmsArticle::class, $result[0][$userEntityKey]->articles[1]);
685
686
        self::assertInstanceOf(CmsUser::class, $result[1][$userEntityKey]);
687
        self::assertInstanceOf(PersistentCollection::class, $result[1][$userEntityKey]->phonenumbers);
688
        self::assertInstanceOf(CmsPhonenumber::class, $result[1][$userEntityKey]->phonenumbers[0]);
689
        self::assertInstanceOf(CmsArticle::class, $result[1][$userEntityKey]->articles[0]);
690
        self::assertInstanceOf(CmsArticle::class, $result[1][$userEntityKey]->articles[1]);
691
    }
692
693
    /**
694
     * SELECT u, p, UPPER(u.name) nameUpper, a, c
695
     *   FROM User u
696
     *   JOIN u.phonenumbers p
697
     *   JOIN u.articles a
698
     *   LEFT JOIN a.comments c
699
     *
700
     * @dataProvider provideDataForUserEntityResult
701
     */
702
    public function testMixedQueryMultipleDeepMixedFetchJoin($userEntityKey) : void
703
    {
704
        $rsm = new ResultSetMapping();
705
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
706
        $rsm->addJoinedEntityResult(
707
            CmsPhonenumber::class,
708
            'p',
709
            'u',
710
            'phonenumbers'
711
        );
712
        $rsm->addJoinedEntityResult(
713
            CmsArticle::class,
714
            'a',
715
            'u',
716
            'articles'
717
        );
718
        $rsm->addJoinedEntityResult(
719
            CmsComment::class,
720
            'c',
721
            'a',
722
            'comments'
723
        );
724
        $rsm->addFieldResult('u', 'u__id', 'id');
725
        $rsm->addFieldResult('u', 'u__status', 'status');
726
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
727
        $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
728
        $rsm->addFieldResult('a', 'a__id', 'id');
729
        $rsm->addFieldResult('a', 'a__topic', 'topic');
730
        $rsm->addFieldResult('c', 'c__id', 'id');
731
        $rsm->addFieldResult('c', 'c__topic', 'topic');
732
733
        // Faked result set
734
        $resultSet = [
735
            //row1
736
            [
737
                'u__id' => '1',
738
                'u__status' => 'developer',
739
                'sclr0' => 'ROMANB',
740
                'p__phonenumber' => '42',
741
                'a__id' => '1',
742
                'a__topic' => 'Getting things done!',
743
                'c__id' => '1',
744
                'c__topic' => 'First!',
745
            ],
746
            [
747
                'u__id' => '1',
748
                'u__status' => 'developer',
749
                'sclr0' => 'ROMANB',
750
                'p__phonenumber' => '43',
751
                'a__id' => '1',
752
                'a__topic' => 'Getting things done!',
753
                'c__id' => '1',
754
                'c__topic' => 'First!',
755
            ],
756
            [
757
                'u__id' => '1',
758
                'u__status' => 'developer',
759
                'sclr0' => 'ROMANB',
760
                'p__phonenumber' => '42',
761
                'a__id' => '2',
762
                'a__topic' => 'ZendCon',
763
                'c__id' => null,
764
                'c__topic' => null,
765
            ],
766
            [
767
                'u__id' => '1',
768
                'u__status' => 'developer',
769
                'sclr0' => 'ROMANB',
770
                'p__phonenumber' => '43',
771
                'a__id' => '2',
772
                'a__topic' => 'ZendCon',
773
                'c__id' => null,
774
                'c__topic' => null,
775
            ],
776
            [
777
                'u__id' => '2',
778
                'u__status' => 'developer',
779
                'sclr0' => 'JWAGE',
780
                'p__phonenumber' => '91',
781
                'a__id' => '3',
782
                'a__topic' => 'LINQ',
783
                'c__id' => null,
784
                'c__topic' => null,
785
            ],
786
            [
787
                'u__id' => '2',
788
                'u__status' => 'developer',
789
                'sclr0' => 'JWAGE',
790
                'p__phonenumber' => '91',
791
                'a__id' => '4',
792
                'a__topic' => 'PHP7',
793
                'c__id' => null,
794
                'c__topic' => null,
795
            ],
796
        ];
797
798
        $stmt     = new HydratorMockStatement($resultSet);
799
        $hydrator = new ObjectHydrator($this->em);
800
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
801
802
        self::assertCount(2, $result);
803
804
        self::assertInternalType('array', $result);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

804
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
805
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

805
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
806
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

806
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
807
808
        self::assertInstanceOf(CmsUser::class, $result[0][$userEntityKey]);
809
        self::assertInstanceOf(CmsUser::class, $result[1][$userEntityKey]);
810
811
        // phonenumbers
812
        self::assertInstanceOf(PersistentCollection::class, $result[0][$userEntityKey]->phonenumbers);
813
        self::assertInstanceOf(CmsPhonenumber::class, $result[0][$userEntityKey]->phonenumbers[0]);
814
        self::assertInstanceOf(CmsPhonenumber::class, $result[0][$userEntityKey]->phonenumbers[1]);
815
816
        self::assertInstanceOf(PersistentCollection::class, $result[1][$userEntityKey]->phonenumbers);
817
        self::assertInstanceOf(CmsPhonenumber::class, $result[1][$userEntityKey]->phonenumbers[0]);
818
819
        // articles
820
        self::assertInstanceOf(PersistentCollection::class, $result[0][$userEntityKey]->articles);
821
        self::assertInstanceOf(CmsArticle::class, $result[0][$userEntityKey]->articles[0]);
822
        self::assertInstanceOf(CmsArticle::class, $result[0][$userEntityKey]->articles[1]);
823
824
        self::assertInstanceOf(CmsArticle::class, $result[1][$userEntityKey]->articles[0]);
825
        self::assertInstanceOf(CmsArticle::class, $result[1][$userEntityKey]->articles[1]);
826
827
        // article comments
828
        self::assertInstanceOf(PersistentCollection::class, $result[0][$userEntityKey]->articles[0]->comments);
829
        self::assertInstanceOf(CmsComment::class, $result[0][$userEntityKey]->articles[0]->comments[0]);
830
831
        // empty comment collections
832
        self::assertInstanceOf(PersistentCollection::class, $result[0][$userEntityKey]->articles[1]->comments);
833
        self::assertCount(0, $result[0][$userEntityKey]->articles[1]->comments);
834
835
        self::assertInstanceOf(PersistentCollection::class, $result[1][$userEntityKey]->articles[0]->comments);
836
        self::assertCount(0, $result[1][$userEntityKey]->articles[0]->comments);
837
        self::assertInstanceOf(PersistentCollection::class, $result[1][$userEntityKey]->articles[1]->comments);
838
        self::assertCount(0, $result[1][$userEntityKey]->articles[1]->comments);
839
    }
840
841
    /**
842
     * Tests that the hydrator does not rely on a particular order of the rows
843
     * in the result set.
844
     *
845
     * DQL:
846
     * select c, b from Doctrine\Tests\Models\Forum\ForumCategory c inner join c.boards b
847
     * order by c.position asc, b.position asc
848
     *
849
     * Checks whether the boards are correctly assigned to the categories.
850
     *
851
     * The 'evil' result set that confuses the object population is displayed below.
852
     *
853
     * c.id  | c.position | c.name   | boardPos | b.id | b.category_id (just for clarity)
854
     *  1    | 0          | First    | 0        |   1  | 1
855
     *  2    | 0          | Second   | 0        |   2  | 2   <--
856
     *  1    | 0          | First    | 1        |   3  | 1
857
     *  1    | 0          | First    | 2        |   4  | 1
858
     */
859
    public function testEntityQueryCustomResultSetOrder() : void
860
    {
861
        $rsm = new ResultSetMapping();
862
        $rsm->addEntityResult(ForumCategory::class, 'c');
863
        $rsm->addJoinedEntityResult(
864
            ForumBoard::class,
865
            'b',
866
            'c',
867
            'boards'
868
        );
869
        $rsm->addFieldResult('c', 'c__id', 'id');
870
        $rsm->addFieldResult('c', 'c__position', 'position');
871
        $rsm->addFieldResult('c', 'c__name', 'name');
872
        $rsm->addFieldResult('b', 'b__id', 'id');
873
        $rsm->addFieldResult('b', 'b__position', 'position');
874
875
        // Faked result set
876
        $resultSet = [
877
            [
878
                'c__id' => '1',
879
                'c__position' => '0',
880
                'c__name' => 'First',
881
                'b__id' => '1',
882
                'b__position' => '0',
883
                //'b__category_id' => '1'
884
            ],
885
            [
886
                'c__id' => '2',
887
                'c__position' => '0',
888
                'c__name' => 'Second',
889
                'b__id' => '2',
890
                'b__position' => '0',
891
                //'b__category_id' => '2'
892
            ],
893
            [
894
                'c__id' => '1',
895
                'c__position' => '0',
896
                'c__name' => 'First',
897
                'b__id' => '3',
898
                'b__position' => '1',
899
                //'b__category_id' => '1'
900
            ],
901
            [
902
                'c__id' => '1',
903
                'c__position' => '0',
904
                'c__name' => 'First',
905
                'b__id' => '4',
906
                'b__position' => '2',
907
                //'b__category_id' => '1'
908
            ],
909
        ];
910
911
        $stmt     = new HydratorMockStatement($resultSet);
912
        $hydrator = new ObjectHydrator($this->em);
913
        /** @var ForumCategory[] $result */
914
        $result = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
915
916
        self::assertCount(2, $result);
917
918
        self::assertInstanceOf(ForumCategory::class, $result[0]);
919
        self::assertInstanceOf(ForumCategory::class, $result[1]);
920
921
        self::assertNotSame($result[0], $result[1]);
922
923
        self::assertEquals(1, $result[0]->getId());
924
        self::assertEquals(2, $result[1]->getId());
925
926
        self::assertObjectHasAttribute('boards', $result[0]);
927
        self::assertCount(3, $result[0]->boards);
928
929
        self::assertObjectHasAttribute('boards', $result[1]);
930
        self::assertCount(1, $result[1]->boards);
931
    }
932
933
    /**
934
     * SELECT PARTIAL u.{id,name}
935
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
936
     *
937
     * @group DDC-644
938
     */
939
    public function testSkipUnknownColumns() : void
940
    {
941
        $rsm = new ResultSetMapping();
942
        $rsm->addEntityResult(CmsUser::class, 'u');
943
        $rsm->addFieldResult('u', 'u__id', 'id');
944
        $rsm->addFieldResult('u', 'u__name', 'name');
945
946
        // Faked result set
947
        $resultSet = [
948
            [
949
                'u__id' => '1',
950
                'u__name' => 'romanb',
951
                'foo' => 'bar', // unknown!
952
            ],
953
        ];
954
955
        $stmt     = new HydratorMockStatement($resultSet);
956
        $hydrator = new ObjectHydrator($this->em);
957
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
958
959
        self::assertCount(1, $result);
960
        self::assertInstanceOf(CmsUser::class, $result[0]);
961
    }
962
963
    /**
964
     * SELECT u.id, u.name
965
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
966
     *
967
     * @dataProvider provideDataForUserEntityResult
968
     */
969
    public function testScalarQueryWithoutResultVariables($userEntityKey) : void
970
    {
971
        $rsm = new ResultSetMapping();
972
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
973
        $rsm->addScalarResult('sclr0', 'id', Type::getType('integer'));
974
        $rsm->addScalarResult('sclr1', 'name', Type::getType('string'));
975
976
        // Faked result set
977
        $resultSet = [
978
            [
979
                'sclr0' => '1',
980
                'sclr1' => 'romanb',
981
            ],
982
            [
983
                'sclr0' => '2',
984
                'sclr1' => 'jwage',
985
            ],
986
        ];
987
988
        $stmt     = new HydratorMockStatement($resultSet);
989
        $hydrator = new ObjectHydrator($this->em);
990
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
991
992
        self::assertCount(2, $result);
993
994
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

994
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
995
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

995
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
996
997
        self::assertEquals(1, $result[0]['id']);
998
        self::assertEquals('romanb', $result[0]['name']);
999
1000
        self::assertEquals(2, $result[1]['id']);
1001
        self::assertEquals('jwage', $result[1]['name']);
1002
    }
1003
1004
    /**
1005
     * SELECT p
1006
     *   FROM Doctrine\Tests\Models\ECommerce\ECommerceProduct p
1007
     */
1008
    public function testCreatesProxyForLazyLoadingWithForeignKeys() : void
1009
    {
1010
        $rsm = new ResultSetMapping();
1011
        $rsm->addEntityResult(ECommerceProduct::class, 'p');
1012
        $rsm->addFieldResult('p', 'p__id', 'id');
1013
        $rsm->addFieldResult('p', 'p__name', 'name');
1014
        $rsm->addMetaResult('p', 'p__shipping_id', 'shipping_id', false, Type::getType('integer'));
1015
1016
        // Faked result set
1017
        $resultSet = [
1018
            [
1019
                'p__id' => '1',
1020
                'p__name' => 'Doctrine Book',
1021
                'p__shipping_id' => 42,
1022
            ],
1023
        ];
1024
1025
        $proxyInstance = (new LazyLoadingGhostFactory(new Configuration()))
1026
            ->createProxy(ECommerceShipping::class, static function () {
1027
                self::fail('Proxy is not supposed to be lazy-loaded');
1028
            });
1029
1030
        // mocking the proxy factory
1031
        $proxyFactory = $this->createMock(ProxyFactory::class);
1032
1033
        $proxyFactory
1034
            ->expects(self::once())
1035
            ->method('getProxy')
1036
            ->with($this->em->getClassMetadata(ECommerceShipping::class), ['id' => 42])
1037
            ->willReturn($proxyInstance);
1038
1039
        $this->em->setProxyFactory($proxyFactory);
1040
1041
        // configuring lazy loading
1042
        $metadata = $this->em->getClassMetadata(ECommerceProduct::class);
1043
        $metadata->getProperty('shipping')->setFetchMode(FetchMode::LAZY);
0 ignored issues
show
Bug introduced by
The method getProperty() does not exist on Doctrine\Common\Persistence\Mapping\ClassMetadata. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

1043
        $metadata->/** @scrutinizer ignore-call */ 
1044
                   getProperty('shipping')->setFetchMode(FetchMode::LAZY);

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
1044
1045
        $stmt     = new HydratorMockStatement($resultSet);
1046
        $hydrator = new ObjectHydrator($this->em);
1047
        $result   = $hydrator->hydrateAll($stmt, $rsm);
1048
1049
        self::assertCount(1, $result);
1050
1051
        self::assertInstanceOf(ECommerceProduct::class, $result[0]);
1052
    }
1053
1054
    /**
1055
     * SELECT p AS product
1056
     *   FROM Doctrine\Tests\Models\ECommerce\ECommerceProduct p
1057
     */
1058
    public function testCreatesProxyForLazyLoadingWithForeignKeysWithAliasedProductEntity() : void
1059
    {
1060
        $rsm = new ResultSetMapping();
1061
        $rsm->addEntityResult(ECommerceProduct::class, 'p', 'product');
1062
        $rsm->addFieldResult('p', 'p__id', 'id');
1063
        $rsm->addFieldResult('p', 'p__name', 'name');
1064
        $rsm->addMetaResult('p', 'p__shipping_id', 'shipping_id', false, Type::getType('integer'));
1065
1066
        // Faked result set
1067
        $resultSet = [
1068
            [
1069
                'p__id' => '1',
1070
                'p__name' => 'Doctrine Book',
1071
                'p__shipping_id' => 42,
1072
            ],
1073
        ];
1074
1075
        $proxyInstance = (new LazyLoadingGhostFactory(new Configuration()))
1076
            ->createProxy(ECommerceShipping::class, static function () {
1077
                self::fail('Proxy is not supposed to be lazy-loaded');
1078
            });
1079
1080
        // mocking the proxy factory
1081
        $proxyFactory = $this
1082
            ->getMockBuilder(ProxyFactory::class)
1083
            ->disableOriginalConstructor()
1084
            ->getMock();
1085
1086
        $proxyFactory
1087
            ->expects(self::once())
1088
            ->method('getProxy')
1089
            ->with($this->em->getClassMetadata(ECommerceShipping::class), ['id' => 42])
1090
            ->willReturn($proxyInstance);
1091
1092
        $this->em->setProxyFactory($proxyFactory);
1093
1094
        // configuring lazy loading
1095
        $metadata = $this->em->getClassMetadata(ECommerceProduct::class);
1096
        $metadata->getProperty('shipping')->setFetchMode(FetchMode::LAZY);
1097
1098
        $stmt     = new HydratorMockStatement($resultSet);
1099
        $hydrator = new ObjectHydrator($this->em);
1100
        $result   = $hydrator->hydrateAll($stmt, $rsm);
1101
1102
        self::assertCount(1, $result);
1103
1104
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1104
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
1105
        self::assertInstanceOf(ECommerceProduct::class, $result[0]['product']);
1106
    }
1107
1108
    /**
1109
     * SELECT PARTIAL u.{id, status}, PARTIAL a.{id, topic}, PARTIAL c.{id, topic}
1110
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1111
     *   LEFT JOIN u.articles a
1112
     *   LEFT JOIN a.comments c
1113
     */
1114
    public function testChainedJoinWithEmptyCollections() : void
1115
    {
1116
        $rsm = new ResultSetMapping();
1117
        $rsm->addEntityResult(CmsUser::class, 'u');
1118
        $rsm->addJoinedEntityResult(
1119
            CmsArticle::class,
1120
            'a',
1121
            'u',
1122
            'articles'
1123
        );
1124
        $rsm->addJoinedEntityResult(
1125
            CmsComment::class,
1126
            'c',
1127
            'a',
1128
            'comments'
1129
        );
1130
        $rsm->addFieldResult('u', 'u__id', 'id');
1131
        $rsm->addFieldResult('u', 'u__status', 'status');
1132
        $rsm->addFieldResult('a', 'a__id', 'id');
1133
        $rsm->addFieldResult('a', 'a__topic', 'topic');
1134
        $rsm->addFieldResult('c', 'c__id', 'id');
1135
        $rsm->addFieldResult('c', 'c__topic', 'topic');
1136
1137
        // Faked result set
1138
        $resultSet = [
1139
            //row1
1140
            [
1141
                'u__id' => '1',
1142
                'u__status' => 'developer',
1143
                'a__id' => null,
1144
                'a__topic' => null,
1145
                'c__id' => null,
1146
                'c__topic' => null,
1147
            ],
1148
            [
1149
                'u__id' => '2',
1150
                'u__status' => 'developer',
1151
                'a__id' => null,
1152
                'a__topic' => null,
1153
                'c__id' => null,
1154
                'c__topic' => null,
1155
            ],
1156
        ];
1157
1158
        $stmt     = new HydratorMockStatement($resultSet);
1159
        $hydrator = new ObjectHydrator($this->em);
1160
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1161
1162
        self::assertCount(2, $result);
1163
1164
        self::assertInstanceOf(CmsUser::class, $result[0]);
1165
        self::assertInstanceOf(CmsUser::class, $result[1]);
1166
1167
        self::assertEquals(0, $result[0]->articles->count());
1168
        self::assertEquals(0, $result[1]->articles->count());
1169
    }
1170
1171
    /**
1172
     * SELECT PARTIAL u.{id, status} AS user, PARTIAL a.{id, topic}, PARTIAL c.{id, topic}
1173
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1174
     *   LEFT JOIN u.articles a
1175
     *   LEFT JOIN a.comments c
1176
     */
1177
    public function testChainedJoinWithEmptyCollectionsWithAliasedUserEntity() : void
1178
    {
1179
        $rsm = new ResultSetMapping();
1180
        $rsm->addEntityResult(CmsUser::class, 'u', 'user');
1181
        $rsm->addJoinedEntityResult(
1182
            CmsArticle::class,
1183
            'a',
1184
            'u',
1185
            'articles'
1186
        );
1187
        $rsm->addJoinedEntityResult(
1188
            CmsComment::class,
1189
            'c',
1190
            'a',
1191
            'comments'
1192
        );
1193
        $rsm->addFieldResult('u', 'u__id', 'id');
1194
        $rsm->addFieldResult('u', 'u__status', 'status');
1195
        $rsm->addFieldResult('a', 'a__id', 'id');
1196
        $rsm->addFieldResult('a', 'a__topic', 'topic');
1197
        $rsm->addFieldResult('c', 'c__id', 'id');
1198
        $rsm->addFieldResult('c', 'c__topic', 'topic');
1199
1200
        // Faked result set
1201
        $resultSet = [
1202
            //row1
1203
            [
1204
                'u__id' => '1',
1205
                'u__status' => 'developer',
1206
                'a__id' => null,
1207
                'a__topic' => null,
1208
                'c__id' => null,
1209
                'c__topic' => null,
1210
            ],
1211
            [
1212
                'u__id' => '2',
1213
                'u__status' => 'developer',
1214
                'a__id' => null,
1215
                'a__topic' => null,
1216
                'c__id' => null,
1217
                'c__topic' => null,
1218
            ],
1219
        ];
1220
1221
        $stmt     = new HydratorMockStatement($resultSet);
1222
        $hydrator = new ObjectHydrator($this->em);
1223
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1224
1225
        self::assertCount(2, $result);
1226
1227
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1227
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
1228
        self::assertInstanceOf(CmsUser::class, $result[0]['user']);
1229
1230
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1230
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
1231
        self::assertInstanceOf(CmsUser::class, $result[1]['user']);
1232
1233
        self::assertEquals(0, $result[0]['user']->articles->count());
1234
        self::assertEquals(0, $result[1]['user']->articles->count());
1235
    }
1236
1237
    /**
1238
     * SELECT PARTIAL u.{id,status}, a.id, a.topic, c.id as cid, c.topic as ctopic
1239
     *   FROM CmsUser u
1240
     *   LEFT JOIN u.articles a
1241
     *   LEFT JOIN a.comments c
1242
     *
1243
     * @todo Figure it out why this test is commented out and provide a better description in docblock
1244
     * @group bubu
1245
     * @dataProvider provideDataForUserEntityResult
1246
     */
1247
    /*public function testChainedJoinWithScalars($userEntityKey) : void
1248
    {
1249
        $rsm = new ResultSetMapping;
1250
        $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsUser', 'u', $userEntityKey ?: null);
1251
        $rsm->addFieldResult('u', 'u__id', 'id');
1252
        $rsm->addFieldResult('u', 'u__status', 'status');
1253
        $rsm->addScalarResult('a__id', 'id', Type::getType('integer'));
1254
        $rsm->addScalarResult('a__topic', 'topic', Type::getType('string'));
1255
        $rsm->addScalarResult('c__id', 'cid', Type::getType('integer'));
1256
        $rsm->addScalarResult('c__topic', 'ctopic', Type::getType('string'));
1257
1258
        // Faked result set
1259
        $resultSet = array(
1260
            //row1
1261
            array(
1262
                'u__id' => '1',
1263
                'u__status' => 'developer',
1264
                'a__id' => '1',
1265
                'a__topic' => 'The First',
1266
                'c__id' => '1',
1267
                'c__topic' => 'First Comment'
1268
            ),
1269
            array(
1270
                'u__id' => '1',
1271
                'u__status' => 'developer',
1272
                'a__id' => '1',
1273
                'a__topic' => 'The First',
1274
                'c__id' => '2',
1275
                'c__topic' => 'Second Comment'
1276
            ),
1277
            array(
1278
                'u__id' => '1',
1279
                'u__status' => 'developer',
1280
                'a__id' => '42',
1281
                'a__topic' => 'The Answer',
1282
                'c__id' => null,
1283
                'c__topic' => null
1284
            ),
1285
        );
1286
1287
        $stmt     = new HydratorMockStatement($resultSet);
1288
        $hydrator = new \Doctrine\ORM\Internal\Hydration\ObjectHydrator($this->em);
1289
        $result   = $hydrator->hydrateAll($stmt, $rsm, array(Query::HINT_FORCE_PARTIAL_LOAD => true));
1290
1291
        \Doctrine\Common\Util\Debug::dump($result, 3);
1292
1293
        self::assertCount(1, $result);
1294
1295
        self::assertInstanceOf('Doctrine\Tests\Models\CMS\CmsUser', $result[0][$userEntityKey]); // User object
1296
        self::assertEquals(42, $result[0]['id']);
1297
        self::assertEquals('The First', $result[0]['topic']);
1298
        self::assertEquals(1, $result[0]['cid']);
1299
        self::assertEquals('First Comment', $result[0]['ctopic']);
1300
    }*/
1301
1302
    /**
1303
     * SELECT PARTIAL u.{id, name}
1304
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1305
     */
1306
    public function testResultIteration() : void
1307
    {
1308
        $rsm = new ResultSetMapping();
1309
        $rsm->addEntityResult(CmsUser::class, 'u');
1310
        $rsm->addFieldResult('u', 'u__id', 'id');
1311
        $rsm->addFieldResult('u', 'u__name', 'name');
1312
1313
        // Faked result set
1314
        $resultSet = [
1315
            [
1316
                'u__id' => '1',
1317
                'u__name' => 'romanb',
1318
            ],
1319
            [
1320
                'u__id' => '2',
1321
                'u__name' => 'jwage',
1322
            ],
1323
        ];
1324
1325
        $hydrator = new ObjectHydrator($this->em);
1326
1327
        $iterableResult = $hydrator->iterate(
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\ORM\Internal\Hy...ractHydrator::iterate() has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1327
        $iterableResult = /** @scrutinizer ignore-deprecated */ $hydrator->iterate(
Loading history...
1328
            new HydratorMockStatement($resultSet),
1329
            $rsm,
1330
            [Query::HINT_FORCE_PARTIAL_LOAD => true]
1331
        );
1332
        $rowNum         = 0;
1333
1334
        while (($row = $iterableResult->next()) !== false) {
1335
            self::assertCount(1, $row);
1336
            self::assertInstanceOf(CmsUser::class, $row[0]);
1337
1338
            if ($rowNum === 0) {
1339
                self::assertEquals(1, $row[0]->id);
1340
                self::assertEquals('romanb', $row[0]->name);
1341
            }
1342
1343
            if ($rowNum === 1) {
1344
                self::assertEquals(2, $row[0]->id);
1345
                self::assertEquals('jwage', $row[0]->name);
1346
            }
1347
1348
            ++$rowNum;
1349
        }
1350
1351
        self::assertSame(2, $rowNum);
1352
1353
        $iterableResult = $hydrator->getIterable(
1354
            new HydratorMockStatement($resultSet),
1355
            $rsm,
1356
            [Query::HINT_FORCE_PARTIAL_LOAD => true]
1357
        );
1358
        $rowNum         = 0;
1359
1360
        foreach ($iterableResult as $user) {
1361
            self::assertInstanceOf(CmsUser::class, $user);
1362
1363
            if ($rowNum === 0) {
1364
                self::assertEquals(1, $user->id);
1365
                self::assertEquals('romanb', $user->name);
1366
            }
1367
1368
            if ($rowNum === 1) {
1369
                self::assertEquals(2, $user->id);
1370
                self::assertEquals('jwage', $user->name);
1371
            }
1372
1373
            ++$rowNum;
1374
        }
1375
1376
        self::assertSame(2, $rowNum);
1377
    }
1378
1379
    /**
1380
     * SELECT PARTIAL u.{id, name}
1381
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1382
     */
1383
    public function testResultIterationWithAliasedUserEntity() : void
1384
    {
1385
        $rsm = new ResultSetMapping();
1386
        $rsm->addEntityResult(CmsUser::class, 'u', 'user');
1387
        $rsm->addFieldResult('u', 'u__id', 'id');
1388
        $rsm->addFieldResult('u', 'u__name', 'name');
1389
1390
        // Faked result set
1391
        $resultSet = [
1392
            [
1393
                'u__id' => '1',
1394
                'u__name' => 'romanb',
1395
            ],
1396
            [
1397
                'u__id' => '2',
1398
                'u__name' => 'jwage',
1399
            ],
1400
        ];
1401
1402
        $hydrator = new ObjectHydrator($this->em);
1403
1404
        $rowNum         = 0;
1405
        $iterableResult = $hydrator->iterate(
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\ORM\Internal\Hy...ractHydrator::iterate() has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1405
        $iterableResult = /** @scrutinizer ignore-deprecated */ $hydrator->iterate(
Loading history...
1406
            new HydratorMockStatement($resultSet),
1407
            $rsm,
1408
            [Query::HINT_FORCE_PARTIAL_LOAD => true]
1409
        );
1410
1411
        while (($row = $iterableResult->next()) !== false) {
1412
            self::assertCount(1, $row);
1413
            self::assertArrayHasKey(0, $row);
1414
            self::assertArrayHasKey('user', $row[0]);
1415
            self::assertInstanceOf(CmsUser::class, $row[0]['user']);
1416
1417
            if ($rowNum === 0) {
1418
                self::assertEquals(1, $row[0]['user']->id);
1419
                self::assertEquals('romanb', $row[0]['user']->name);
1420
            }
1421
1422
            if ($rowNum === 1) {
1423
                self::assertEquals(2, $row[0]['user']->id);
1424
                self::assertEquals('jwage', $row[0]['user']->name);
1425
            }
1426
1427
            ++$rowNum;
1428
        }
1429
1430
        self::assertSame(2, $rowNum);
1431
1432
        $rowNum         = 0;
1433
        $iterableResult = $hydrator->getIterable(
1434
            new HydratorMockStatement($resultSet),
1435
            $rsm,
1436
            [Query::HINT_FORCE_PARTIAL_LOAD => true]
1437
        );
1438
1439
        foreach ($iterableResult as $row) {
1440
            self::assertCount(1, $row);
1441
            self::assertArrayHasKey('user', $row);
1442
            self::assertInstanceOf(CmsUser::class, $row['user']);
1443
1444
            if ($rowNum === 0) {
1445
                self::assertEquals(1, $row['user']->id);
1446
                self::assertEquals('romanb', $row['user']->name);
1447
            }
1448
1449
            if ($rowNum === 1) {
1450
                self::assertEquals(2, $row['user']->id);
1451
                self::assertEquals('jwage', $row['user']->name);
1452
            }
1453
1454
            ++$rowNum;
1455
        }
1456
1457
        self::assertSame(2, $rowNum);
1458
    }
1459
1460
    /**
1461
     * Checks if multiple joined multiple-valued collections is hydrated correctly.
1462
     *
1463
     * SELECT PARTIAL u.{id, status}, PARTIAL g.{id, name}, PARTIAL p.{phonenumber}
1464
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1465
     *
1466
     * @group DDC-809
1467
     */
1468
    public function testManyToManyHydration() : void
1469
    {
1470
        $rsm = new ResultSetMapping();
1471
        $rsm->addEntityResult(CmsUser::class, 'u');
1472
        $rsm->addFieldResult('u', 'u__id', 'id');
1473
        $rsm->addFieldResult('u', 'u__name', 'name');
1474
        $rsm->addJoinedEntityResult(CmsGroup::class, 'g', 'u', 'groups');
1475
        $rsm->addFieldResult('g', 'g__id', 'id');
1476
        $rsm->addFieldResult('g', 'g__name', 'name');
1477
        $rsm->addJoinedEntityResult(CmsPhonenumber::class, 'p', 'u', 'phonenumbers');
1478
        $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
1479
1480
        // Faked result set
1481
        $resultSet = [
1482
            [
1483
                'u__id' => '1',
1484
                'u__name' => 'romanb',
1485
                'g__id' => '3',
1486
                'g__name' => 'TestGroupB',
1487
                'p__phonenumber' => 1111,
1488
            ],
1489
            [
1490
                'u__id' => '1',
1491
                'u__name' => 'romanb',
1492
                'g__id' => '5',
1493
                'g__name' => 'TestGroupD',
1494
                'p__phonenumber' => 1111,
1495
            ],
1496
            [
1497
                'u__id' => '1',
1498
                'u__name' => 'romanb',
1499
                'g__id' => '3',
1500
                'g__name' => 'TestGroupB',
1501
                'p__phonenumber' => 2222,
1502
            ],
1503
            [
1504
                'u__id' => '1',
1505
                'u__name' => 'romanb',
1506
                'g__id' => '5',
1507
                'g__name' => 'TestGroupD',
1508
                'p__phonenumber' => 2222,
1509
            ],
1510
            [
1511
                'u__id' => '2',
1512
                'u__name' => 'jwage',
1513
                'g__id' => '2',
1514
                'g__name' => 'TestGroupA',
1515
                'p__phonenumber' => 3333,
1516
            ],
1517
            [
1518
                'u__id' => '2',
1519
                'u__name' => 'jwage',
1520
                'g__id' => '3',
1521
                'g__name' => 'TestGroupB',
1522
                'p__phonenumber' => 3333,
1523
            ],
1524
            [
1525
                'u__id' => '2',
1526
                'u__name' => 'jwage',
1527
                'g__id' => '4',
1528
                'g__name' => 'TestGroupC',
1529
                'p__phonenumber' => 3333,
1530
            ],
1531
            [
1532
                'u__id' => '2',
1533
                'u__name' => 'jwage',
1534
                'g__id' => '5',
1535
                'g__name' => 'TestGroupD',
1536
                'p__phonenumber' => 3333,
1537
            ],
1538
            [
1539
                'u__id' => '2',
1540
                'u__name' => 'jwage',
1541
                'g__id' => '2',
1542
                'g__name' => 'TestGroupA',
1543
                'p__phonenumber' => 4444,
1544
            ],
1545
            [
1546
                'u__id' => '2',
1547
                'u__name' => 'jwage',
1548
                'g__id' => '3',
1549
                'g__name' => 'TestGroupB',
1550
                'p__phonenumber' => 4444,
1551
            ],
1552
            [
1553
                'u__id' => '2',
1554
                'u__name' => 'jwage',
1555
                'g__id' => '4',
1556
                'g__name' => 'TestGroupC',
1557
                'p__phonenumber' => 4444,
1558
            ],
1559
            [
1560
                'u__id' => '2',
1561
                'u__name' => 'jwage',
1562
                'g__id' => '5',
1563
                'g__name' => 'TestGroupD',
1564
                'p__phonenumber' => 4444,
1565
            ],
1566
        ];
1567
1568
        $stmt     = new HydratorMockStatement($resultSet);
1569
        $hydrator = new ObjectHydrator($this->em);
1570
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1571
1572
        self::assertCount(2, $result);
1573
1574
        self::assertContainsOnly(CmsUser::class, $result);
1575
1576
        self::assertCount(2, $result[0]->groups);
1577
        self::assertCount(2, $result[0]->phonenumbers);
1578
1579
        self::assertCount(4, $result[1]->groups);
1580
        self::assertCount(2, $result[1]->phonenumbers);
1581
    }
1582
1583
    /**
1584
     * Checks if multiple joined multiple-valued collections is hydrated correctly.
1585
     *
1586
     * SELECT PARTIAL u.{id, status} As user, PARTIAL g.{id, name}, PARTIAL p.{phonenumber}
1587
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1588
     *
1589
     * @group DDC-809
1590
     */
1591
    public function testManyToManyHydrationWithAliasedUserEntity() : void
1592
    {
1593
        $rsm = new ResultSetMapping();
1594
        $rsm->addEntityResult(CmsUser::class, 'u', 'user');
1595
        $rsm->addFieldResult('u', 'u__id', 'id');
1596
        $rsm->addFieldResult('u', 'u__name', 'name');
1597
        $rsm->addJoinedEntityResult(CmsGroup::class, 'g', 'u', 'groups');
1598
        $rsm->addFieldResult('g', 'g__id', 'id');
1599
        $rsm->addFieldResult('g', 'g__name', 'name');
1600
        $rsm->addJoinedEntityResult(CmsPhonenumber::class, 'p', 'u', 'phonenumbers');
1601
        $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
1602
1603
        // Faked result set
1604
        $resultSet = [
1605
            [
1606
                'u__id' => '1',
1607
                'u__name' => 'romanb',
1608
                'g__id' => '3',
1609
                'g__name' => 'TestGroupB',
1610
                'p__phonenumber' => 1111,
1611
            ],
1612
            [
1613
                'u__id' => '1',
1614
                'u__name' => 'romanb',
1615
                'g__id' => '5',
1616
                'g__name' => 'TestGroupD',
1617
                'p__phonenumber' => 1111,
1618
            ],
1619
            [
1620
                'u__id' => '1',
1621
                'u__name' => 'romanb',
1622
                'g__id' => '3',
1623
                'g__name' => 'TestGroupB',
1624
                'p__phonenumber' => 2222,
1625
            ],
1626
            [
1627
                'u__id' => '1',
1628
                'u__name' => 'romanb',
1629
                'g__id' => '5',
1630
                'g__name' => 'TestGroupD',
1631
                'p__phonenumber' => 2222,
1632
            ],
1633
            [
1634
                'u__id' => '2',
1635
                'u__name' => 'jwage',
1636
                'g__id' => '2',
1637
                'g__name' => 'TestGroupA',
1638
                'p__phonenumber' => 3333,
1639
            ],
1640
            [
1641
                'u__id' => '2',
1642
                'u__name' => 'jwage',
1643
                'g__id' => '3',
1644
                'g__name' => 'TestGroupB',
1645
                'p__phonenumber' => 3333,
1646
            ],
1647
            [
1648
                'u__id' => '2',
1649
                'u__name' => 'jwage',
1650
                'g__id' => '4',
1651
                'g__name' => 'TestGroupC',
1652
                'p__phonenumber' => 3333,
1653
            ],
1654
            [
1655
                'u__id' => '2',
1656
                'u__name' => 'jwage',
1657
                'g__id' => '5',
1658
                'g__name' => 'TestGroupD',
1659
                'p__phonenumber' => 3333,
1660
            ],
1661
            [
1662
                'u__id' => '2',
1663
                'u__name' => 'jwage',
1664
                'g__id' => '2',
1665
                'g__name' => 'TestGroupA',
1666
                'p__phonenumber' => 4444,
1667
            ],
1668
            [
1669
                'u__id' => '2',
1670
                'u__name' => 'jwage',
1671
                'g__id' => '3',
1672
                'g__name' => 'TestGroupB',
1673
                'p__phonenumber' => 4444,
1674
            ],
1675
            [
1676
                'u__id' => '2',
1677
                'u__name' => 'jwage',
1678
                'g__id' => '4',
1679
                'g__name' => 'TestGroupC',
1680
                'p__phonenumber' => 4444,
1681
            ],
1682
            [
1683
                'u__id' => '2',
1684
                'u__name' => 'jwage',
1685
                'g__id' => '5',
1686
                'g__name' => 'TestGroupD',
1687
                'p__phonenumber' => 4444,
1688
            ],
1689
        ];
1690
1691
        $stmt     = new HydratorMockStatement($resultSet);
1692
        $hydrator = new ObjectHydrator($this->em);
1693
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1694
1695
        self::assertCount(2, $result);
1696
1697
        self::assertInternalType('array', $result[0]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1697
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[0]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
1698
        self::assertInstanceOf(CmsUser::class, $result[0]['user']);
1699
        self::assertInternalType('array', $result[1]);
0 ignored issues
show
Deprecated Code introduced by
The function PHPUnit\Framework\Assert::assertInternalType() has been deprecated: https://github.com/sebastianbergmann/phpunit/issues/3369 ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

1699
        /** @scrutinizer ignore-deprecated */ self::assertInternalType('array', $result[1]);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
1700
        self::assertInstanceOf(CmsUser::class, $result[1]['user']);
1701
1702
        self::assertCount(2, $result[0]['user']->groups);
1703
        self::assertCount(2, $result[0]['user']->phonenumbers);
1704
1705
        self::assertCount(4, $result[1]['user']->groups);
1706
        self::assertCount(2, $result[1]['user']->phonenumbers);
1707
    }
1708
1709
    /**
1710
     * SELECT PARTIAL u.{id, status}, UPPER(u.name) as nameUpper
1711
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1712
     *
1713
     * @group DDC-1358
1714
     * @dataProvider provideDataForUserEntityResult
1715
     */
1716
    public function testMissingIdForRootEntity($userEntityKey) : void
1717
    {
1718
        $rsm = new ResultSetMapping();
1719
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
1720
        $rsm->addFieldResult('u', 'u__id', 'id');
1721
        $rsm->addFieldResult('u', 'u__status', 'status');
1722
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
1723
1724
        // Faked result set
1725
        $resultSet = [
1726
            //row1
1727
            [
1728
                'u__id' => '1',
1729
                'u__status' => 'developer',
1730
                'sclr0' => 'ROMANB',
1731
            ],
1732
            [
1733
                'u__id' => null,
1734
                'u__status' => null,
1735
                'sclr0' => 'ROMANB',
1736
            ],
1737
            [
1738
                'u__id' => '2',
1739
                'u__status' => 'developer',
1740
                'sclr0' => 'JWAGE',
1741
            ],
1742
            [
1743
                'u__id' => null,
1744
                'u__status' => null,
1745
                'sclr0' => 'JWAGE',
1746
            ],
1747
        ];
1748
1749
        $stmt     = new HydratorMockStatement($resultSet);
1750
        $hydrator = new ObjectHydrator($this->em);
1751
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1752
1753
        self::assertCount(4, $result, 'Should hydrate four results.');
1754
1755
        self::assertEquals('ROMANB', $result[0]['nameUpper']);
1756
        self::assertEquals('ROMANB', $result[1]['nameUpper']);
1757
        self::assertEquals('JWAGE', $result[2]['nameUpper']);
1758
        self::assertEquals('JWAGE', $result[3]['nameUpper']);
1759
1760
        self::assertInstanceOf(CmsUser::class, $result[0][$userEntityKey]);
1761
        self::assertNull($result[1][$userEntityKey]);
1762
1763
        self::assertInstanceOf(CmsUser::class, $result[2][$userEntityKey]);
1764
        self::assertNull($result[3][$userEntityKey]);
1765
    }
1766
1767
    /**
1768
     * SELECT PARTIAL u.{id, status}, PARTIAL p.{phonenumber}, UPPER(u.name) AS nameUpper
1769
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1770
     *   LEFT JOIN u.phonenumbers u
1771
     *
1772
     * @group DDC-1358
1773
     * @dataProvider provideDataForUserEntityResult
1774
     */
1775
    public function testMissingIdForCollectionValuedChildEntity($userEntityKey) : void
1776
    {
1777
        $rsm = new ResultSetMapping();
1778
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
1779
        $rsm->addJoinedEntityResult(
1780
            CmsPhonenumber::class,
1781
            'p',
1782
            'u',
1783
            'phonenumbers'
1784
        );
1785
        $rsm->addFieldResult('u', 'u__id', 'id');
1786
        $rsm->addFieldResult('u', 'u__status', 'status');
1787
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
1788
        $rsm->addFieldResult('p', 'p__phonenumber', 'phonenumber');
1789
1790
        // Faked result set
1791
        $resultSet = [
1792
            //row1
1793
            [
1794
                'u__id' => '1',
1795
                'u__status' => 'developer',
1796
                'sclr0' => 'ROMANB',
1797
                'p__phonenumber' => '42',
1798
            ],
1799
            [
1800
                'u__id' => '1',
1801
                'u__status' => 'developer',
1802
                'sclr0' => 'ROMANB',
1803
                'p__phonenumber' => null,
1804
            ],
1805
            [
1806
                'u__id' => '2',
1807
                'u__status' => 'developer',
1808
                'sclr0' => 'JWAGE',
1809
                'p__phonenumber' => '91',
1810
            ],
1811
            [
1812
                'u__id' => '2',
1813
                'u__status' => 'developer',
1814
                'sclr0' => 'JWAGE',
1815
                'p__phonenumber' => null,
1816
            ],
1817
        ];
1818
1819
        $stmt     = new HydratorMockStatement($resultSet);
1820
        $hydrator = new ObjectHydrator($this->em);
1821
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1822
1823
        self::assertCount(2, $result);
1824
1825
        self::assertEquals(1, $result[0][$userEntityKey]->phonenumbers->count());
1826
        self::assertEquals(1, $result[1][$userEntityKey]->phonenumbers->count());
1827
    }
1828
1829
    /**
1830
     * SELECT PARTIAL u.{id, status}, PARTIAL a.{id, city}, UPPER(u.name) AS nameUpper
1831
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1832
     *   JOIN u.address a
1833
     *
1834
     * @group DDC-1358
1835
     * @dataProvider provideDataForUserEntityResult
1836
     */
1837
    public function testMissingIdForSingleValuedChildEntity($userEntityKey) : void
1838
    {
1839
        $rsm = new ResultSetMapping();
1840
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
1841
        $rsm->addJoinedEntityResult(
1842
            CmsAddress::class,
1843
            'a',
1844
            'u',
1845
            'address'
1846
        );
1847
        $rsm->addFieldResult('u', 'u__id', 'id');
1848
        $rsm->addFieldResult('u', 'u__status', 'status');
1849
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
1850
        $rsm->addFieldResult('a', 'a__id', 'id');
1851
        $rsm->addFieldResult('a', 'a__city', 'city');
1852
        $rsm->addMetaResult('a', 'user_id', 'user_id', false, Type::getType('string'));
1853
1854
        // Faked result set
1855
        $resultSet = [
1856
            //row1
1857
            [
1858
                'u__id' => '1',
1859
                'u__status' => 'developer',
1860
                'sclr0' => 'ROMANB',
1861
                'a__id' => 1,
1862
                'a__city' => 'Berlin',
1863
            ],
1864
            [
1865
                'u__id' => '2',
1866
                'u__status' => 'developer',
1867
                'sclr0' => 'BENJAMIN',
1868
                'a__id' => null,
1869
                'a__city' => null,
1870
            ],
1871
        ];
1872
1873
        $stmt     = new HydratorMockStatement($resultSet);
1874
        $hydrator = new ObjectHydrator($this->em);
1875
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1876
1877
        self::assertCount(2, $result);
1878
1879
        self::assertInstanceOf(CmsAddress::class, $result[0][$userEntityKey]->address);
1880
        self::assertNull($result[1][$userEntityKey]->address);
1881
    }
1882
1883
    /**
1884
     * SELECT PARTIAL u.{id, status}, UPPER(u.name) AS nameUpper
1885
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1886
     *        INDEX BY u.id
1887
     *
1888
     * @group DDC-1385
1889
     * @dataProvider provideDataForUserEntityResult
1890
     */
1891
    public function testIndexByAndMixedResult($userEntityKey) : void
1892
    {
1893
        $rsm = new ResultSetMapping();
1894
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
1895
        $rsm->addFieldResult('u', 'u__id', 'id');
1896
        $rsm->addFieldResult('u', 'u__status', 'status');
1897
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
1898
        $rsm->addIndexBy('u', 'id');
1899
1900
        // Faked result set
1901
        $resultSet = [
1902
            //row1
1903
            [
1904
                'u__id' => '1',
1905
                'u__status' => 'developer',
1906
                'sclr0' => 'ROMANB',
1907
            ],
1908
            [
1909
                'u__id' => '2',
1910
                'u__status' => 'developer',
1911
                'sclr0' => 'JWAGE',
1912
            ],
1913
        ];
1914
1915
        $stmt     = new HydratorMockStatement($resultSet);
1916
        $hydrator = new ObjectHydrator($this->em);
1917
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1918
1919
        self::assertCount(2, $result);
1920
1921
        self::assertArrayHasKey(1, $result);
1922
        self::assertEquals(1, $result[1][$userEntityKey]->id);
1923
1924
        self::assertArrayHasKey(2, $result);
1925
        self::assertEquals(2, $result[2][$userEntityKey]->id);
1926
    }
1927
1928
    /**
1929
     * SELECT UPPER(u.name) AS nameUpper
1930
     *   FROM Doctrine\Tests\Models\CMS\CmsUser u
1931
     *
1932
     * @group DDC-1385
1933
     * @dataProvider provideDataForUserEntityResult
1934
     */
1935
    public function testIndexByScalarsOnly($userEntityKey) : void
1936
    {
1937
        $rsm = new ResultSetMapping();
1938
        $rsm->addEntityResult(CmsUser::class, 'u', $userEntityKey ?: null);
1939
        $rsm->addScalarResult('sclr0', 'nameUpper', Type::getType('string'));
1940
        $rsm->addIndexByScalar('sclr0');
1941
1942
        // Faked result set
1943
        $resultSet = [
1944
            //row1
1945
            ['sclr0' => 'ROMANB'],
1946
            ['sclr0' => 'JWAGE'],
1947
        ];
1948
1949
        $stmt     = new HydratorMockStatement($resultSet);
1950
        $hydrator = new ObjectHydrator($this->em);
1951
        $result   = $hydrator->hydrateAll($stmt, $rsm, [Query::HINT_FORCE_PARTIAL_LOAD => true]);
1952
1953
        self::assertEquals(
1954
            [
1955
                'ROMANB' => ['nameUpper' => 'ROMANB'],
1956
                'JWAGE'  => ['nameUpper' => 'JWAGE'],
1957
            ],
1958
            $result
1959
        );
1960
    }
1961
1962
    /**
1963
     * @group DDC-1470
1964
     * @expectedException \Doctrine\ORM\Internal\Hydration\HydrationException
1965
     * @expectedExceptionMessage The meta mapping for the discriminator column "c_discr" is missing for "Doctrine\Tests\Models\Company\CompanyFixContract" using the DQL alias "c".
1966
     */
1967
    public function testMissingMetaMappingException() : void
1968
    {
1969
        $rsm = new ResultSetMapping();
1970
1971
        $rsm->addEntityResult(CompanyFixContract::class, 'c');
1972
        $rsm->addJoinedEntityResult(CompanyEmployee::class, 'e', 'c', 'salesPerson');
1973
        $rsm->addFieldResult('c', 'c__id', 'id');
1974
        $rsm->setDiscriminatorColumn('c', 'c_discr');
1975
1976
        $resultSet = [
1977
            [
1978
                'c__id'   => '1',
1979
                'c_discr' => 'fix',
1980
            ],
1981
        ];
1982
1983
        $stmt     = new HydratorMockStatement($resultSet);
1984
        $hydrator = new ObjectHydrator($this->em);
1985
        $hydrator->hydrateAll($stmt, $rsm);
1986
    }
1987
1988
    /**
1989
     * @group DDC-1470
1990
     * @expectedException \Doctrine\ORM\Internal\Hydration\HydrationException
1991
     * @expectedExceptionMessage The discriminator column "discr" is missing for "Doctrine\Tests\Models\Company\CompanyEmployee" using the DQL alias "e".
1992
     */
1993
    public function testMissingDiscriminatorColumnException() : void
1994
    {
1995
        $rsm = new ResultSetMapping();
1996
1997
        $rsm->addEntityResult(CompanyFixContract::class, 'c');
1998
        $rsm->addJoinedEntityResult(CompanyEmployee::class, 'e', 'c', 'salesPerson');
1999
        $rsm->addFieldResult('c', 'c__id', 'id');
2000
        $rsm->addMetaResult('c', 'c_discr', 'discr', false, Type::getType('string'));
2001
        $rsm->setDiscriminatorColumn('c', 'c_discr');
2002
        $rsm->addFieldResult('e', 'e__id', 'id');
2003
        $rsm->addFieldResult('e', 'e__name', 'name');
2004
        $rsm->addMetaResult('e ', 'e_discr', 'discr', false, Type::getType('string'));
2005
        $rsm->setDiscriminatorColumn('e', 'e_discr');
2006
2007
        $resultSet = [
2008
            [
2009
                'c__id'   => '1',
2010
                'c_discr' => 'fix',
2011
                'e__id'   => '1',
2012
                'e__name' => 'Fabio B. Silva',
2013
            ],
2014
        ];
2015
2016
        $stmt     = new HydratorMockStatement($resultSet);
2017
        $hydrator = new ObjectHydrator($this->em);
2018
        $hydrator->hydrateAll($stmt, $rsm);
2019
    }
2020
2021
    /**
2022
     * @group DDC-3076
2023
     * @expectedException \Doctrine\ORM\Internal\Hydration\HydrationException
2024
     * @expectedExceptionMessage The discriminator value "subworker" is invalid. It must be one of "person", "manager", "employee".
2025
     */
2026
    public function testInvalidDiscriminatorValueException() : void
2027
    {
2028
        $rsm = new ResultSetMapping();
2029
2030
        $rsm->addEntityResult(CompanyPerson::class, 'p');
2031
        $rsm->addFieldResult('p', 'p__id', 'id');
2032
        $rsm->addFieldResult('p', 'p__name', 'name');
2033
        $rsm->addMetaResult('p', 'discr', 'discr', false, Type::getType('string'));
2034
        $rsm->setDiscriminatorColumn('p', 'discr');
2035
2036
        $resultSet = [
2037
            [
2038
                'p__id'   => '1',
2039
                'p__name' => 'Fabio B. Silva',
2040
                'discr'   => 'subworker',
2041
            ],
2042
        ];
2043
2044
        $stmt     = new HydratorMockStatement($resultSet);
2045
        $hydrator = new ObjectHydrator($this->em);
2046
        $hydrator->hydrateAll($stmt, $rsm);
2047
    }
2048
2049
    public function testFetchJoinCollectionValuedAssociationWithDefaultArrayValue() : void
2050
    {
2051
        $rsm = new ResultSetMapping();
2052
2053
        $rsm->addEntityResult(EntityWithArrayDefaultArrayValueM2M::class, 'e1');
2054
        $rsm->addJoinedEntityResult(SimpleEntity::class, 'e2', 'e1', 'collection');
2055
        $rsm->addFieldResult('e1', 'a1__id', 'id');
2056
        $rsm->addFieldResult('e2', 'e2__id', 'id');
2057
2058
        $resultSet = [
2059
            [
2060
                'a1__id' => '1',
2061
                'e2__id' => '1',
2062
            ],
2063
        ];
2064
2065
        $stmt     = new HydratorMockStatement($resultSet);
2066
        $hydrator = new ObjectHydrator($this->em);
2067
        $result   = $hydrator->hydrateAll($stmt, $rsm);
2068
2069
        self::assertCount(1, $result);
2070
        self::assertInstanceOf(EntityWithArrayDefaultArrayValueM2M::class, $result[0]);
2071
        self::assertInstanceOf(PersistentCollection::class, $result[0]->collection);
2072
        self::assertCount(1, $result[0]->collection);
2073
        self::assertInstanceOf(SimpleEntity::class, $result[0]->collection[0]);
2074
    }
2075
}
2076