Completed
Pull Request — master (#1610)
by Maciej
09:22
created

Cursor::info()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
dl 0
loc 4
ccs 0
cts 2
cp 0
rs 10
c 0
b 0
f 0
cc 1
eloc 2
nc 1
nop 0
crap 2
1
<?php
2
/*
3
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
4
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
5
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
6
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
7
 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
8
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
9
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
10
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
11
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
12
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
13
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
14
 *
15
 * This software consists of voluntary contributions made by many individuals
16
 * and is licensed under the MIT license. For more information, see
17
 * <http://www.doctrine-project.org>.
18
 */
19
20
namespace Doctrine\ODM\MongoDB;
21
22
use Doctrine\MongoDB\Collection;
23
use Doctrine\MongoDB\Connection;
24
use Doctrine\MongoDB\CursorInterface;
25
use Doctrine\MongoDB\EagerCursor as BaseEagerCursor;
26
use Doctrine\ODM\MongoDB\Mapping\ClassMetadata;
27
use Doctrine\ODM\MongoDB\Query\Query;
28
use Doctrine\ODM\MongoDB\Query\ReferencePrimer;
29
30
/**
31
 * Wrapper for the Doctrine\MongoDB\Cursor class.
32
 *
33
 * This class composes a Doctrine\MongoDB\Cursor instance and wraps its methods
34
 * in order to return results as hydrated document class instances. Hydration
35
 * behavior may be controlled with the {@link Cursor::hydrate()} method.
36
 *
37
 * For compatibility, this class also extends Doctrine\MongoDB\Cursor.
38
 *
39
 * @since  1.0
40
 */
41
class Cursor implements CursorInterface
42
{
43
    /**
44
     * The Doctrine\MongoDB\Cursor instance being wrapped.
45
     *
46
     * @var CursorInterface
47
     */
48
    private $baseCursor;
49
50
    /**
51
     * The ClassMetadata instance for the document class being queried.
52
     *
53
     * @var ClassMetadata
54
     */
55
    private $class;
56
57
    /**
58
     * Whether or not to hydrate results as document class instances.
59
     *
60
     * @var boolean
61
     */
62
    private $hydrate = true;
63
64
    /**
65
     * The UnitOfWork instance used for result hydration and preparing arguments
66
     * for {@link Cursor::sort()}.
67
     *
68
     * @var UnitOfWork
69
     */
70
    private $unitOfWork;
71
72
    /**
73
     * Hints for UnitOfWork behavior.
74
     *
75
     * @var array
76
     */
77
    private $unitOfWorkHints = array();
78
79
    /**
80
     * ReferencePrimer object for priming references
81
     *
82
     * @var ReferencePrimer
83
     */
84
    private $referencePrimer;
85
86
    /**
87
     * Primers
88
     *
89
     * @var array
90
     */
91
    private $primers = array();
92
93
    /**
94
     * Whether references have been primed
95
     *
96
     * @var bool
97
     */
98
    private $referencesPrimed = false;
99
100
    /**
101
     * Constructor.
102
     *
103
     * @param CursorInterface $baseCursor  Cursor instance being wrapped
104
     * @param UnitOfWork      $unitOfWork  UnitOfWork for result hydration and query preparation
105
     * @param ClassMetadata   $class       ClassMetadata for the document class being queried
106
     */
107 149
    public function __construct(CursorInterface $baseCursor, UnitOfWork $unitOfWork, ClassMetadata $class)
108
    {
109 149
        $this->baseCursor = $baseCursor;
110 149
        $this->unitOfWork = $unitOfWork;
111 149
        $this->class = $class;
112 149
    }
113
114
    /**
115
     * Return the wrapped Doctrine\MongoDB\Cursor instance.
116
     *
117
     * @return CursorInterface
118
     */
119
    public function getBaseCursor()
120
    {
121
        return $this->baseCursor;
122
    }
123
124
    /**
125
     * Return the database connection for this cursor.
126
     *
127
     * @see \Doctrine\MongoDB\Cursor::getConnection()
128
     * @return Connection
129
     */
130
    public function getConnection()
131
    {
132
        return $this->baseCursor->getCollection()->getDatabase()->getConnection();
133
    }
134
135
    /**
136
     * Return the collection for this cursor.
137
     *
138
     * @see CursorInterface::getCollection()
139
     * @return Collection
140
     */
141
    public function getCollection()
142
    {
143
        return $this->baseCursor->getCollection();
144
    }
145
146
    /**
147
     * Return the selected fields (projection).
148
     *
149
     * @see CursorInterface::getFields()
150
     * @return array
151
     */
152
    public function getFields()
153
    {
154
        return $this->baseCursor->getFields();
155
    }
156
157
    /**
158
     * Get hints for UnitOfWork behavior.
159
     *
160
     * @return array
161
     */
162 18
    public function getHints()
163
    {
164 18
        return $this->unitOfWorkHints;
165
    }
166
167
    /**
168
     * Set hints for UnitOfWork behavior.
169
     *
170
     * @param array $hints
171
     */
172 133
    public function setHints(array $hints)
173
    {
174 133
        $this->unitOfWorkHints = $hints;
175 133
    }
176
177
    /**
178
     * Return the query criteria.
179
     *
180
     * @see CursorInterface::getQuery()
181
     * @return array
182
     */
183
    public function getQuery()
184
    {
185
        return $this->baseCursor->getQuery();
186
    }
187
188
    /**
189
     * Wrapper method for MongoCursor::addOption().
190
     *
191
     * @see CursorInterface::addOption()
192
     * @see http://php.net/manual/en/mongocursor.addoption.php
193
     * @param string $key
194
     * @param mixed $value
195
     * @return $this
196
     */
197
    public function addOption($key, $value)
198
    {
199
        $this->baseCursor->addOption($key, $value);
200
        return $this;
201
    }
202
203
    /**
204
     * Wrapper method for MongoCursor::batchSize().
205
     *
206
     * @see CursorInterface::batchSize()
207
     * @see http://php.net/manual/en/mongocursor.batchsize.php
208
     * @param integer $num
209
     * @return $this
210
     */
211
    public function batchSize($num)
212
    {
213
        $this->baseCursor->batchSize($num);
214
        return $this;
215
    }
216
217
    /**
218
     * Wrapper method for MongoCursor::count().
219
     *
220
     * @see CursorInterface::count()
221
     * @see http://php.net/manual/en/countable.count.php
222
     * @see http://php.net/manual/en/mongocursor.count.php
223
     * @param boolean $foundOnly
224
     * @return integer
225
     */
226 25
    public function count($foundOnly = false)
227
    {
228 25
        return $this->baseCursor->count($foundOnly);
229
    }
230
231
    /**
232
     * Wrapper method for MongoCursor::current().
233
     *
234
     * If configured, the result may be a hydrated document class instance.
235
     *
236
     * @see CursorInterface::current()
237
     * @see http://php.net/manual/en/iterator.current.php
238
     * @see http://php.net/manual/en/mongocursor.current.php
239
     * @return array|object|null
240
     */
241 60
    public function current()
242
    {
243 60
        $this->primeReferences();
244
245 58
        return $this->hydrateDocument($this->baseCursor->current());
246
    }
247
248
    /**
249
     * Wrapper method for MongoCursor::dead().
250
     *
251
     * @see CursorInterface::dead()
252
     * @see http://php.net/manual/en/mongocursor.dead.php
253
     * @return boolean
254
     */
255
    public function dead()
256
    {
257
        return $this->baseCursor->dead();
258
    }
259
260
    /**
261
     * Wrapper method for MongoCursor::explain().
262
     *
263
     * @see CursorInterface::explain()
264
     * @see http://php.net/manual/en/mongocursor.explain.php
265
     * @return array
266
     */
267
    public function explain()
268
    {
269
        return $this->baseCursor->explain();
270
    }
271
272
    /**
273
     * Wrapper method for MongoCursor::fields().
274
     *
275
     * @param array $f Fields to return (or not return).
276
     *
277
     * @see CursorInterface::fields()
278
     * @see http://php.net/manual/en/mongocursor.fields.php
279
     * @return $this
280
     */
281
    public function fields(array $f)
282
    {
283
        $this->baseCursor->fields($f);
284
        return $this;
285
    }
286
287
    /**
288
     * Wrapper method for MongoCursor::getNext().
289
     *
290
     * If configured, the result may be a hydrated document class instance.
291
     *
292
     * @see CursorInterface::getNext()
293
     * @see http://php.net/manual/en/mongocursor.getnext.php
294
     * @return array|object|null
295
     */
296 3
    public function getNext()
297
    {
298 3
        $this->primeReferences();
299
300 3
        return $this->hydrateDocument($this->baseCursor->getNext());
0 ignored issues
show
Bug introduced by
It seems like $this->baseCursor->getNext() targeting Doctrine\MongoDB\CursorInterface::getNext() can also be of type null; however, Doctrine\ODM\MongoDB\Cursor::hydrateDocument() does only seem to accept array, maybe add an additional type check?

This check looks at variables that are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
Bug Compatibility introduced by
The expression $this->hydrateDocument($...baseCursor->getNext()); of type object|array adds the type object to the return on line 300 which is incompatible with the return type declared by the interface Doctrine\MongoDB\CursorInterface::getNext of type array|null.
Loading history...
301
    }
302
303
    /**
304
     * Wrapper method for MongoCursor::getReadPreference().
305
     *
306
     * @see CursorInterface::getReadPreference()
307
     * @see http://php.net/manual/en/mongocursor.getreadpreference.php
308
     * @return array
309
     */
310
    public function getReadPreference()
311
    {
312
        return $this->baseCursor->getReadPreference();
313
    }
314
315
    /**
316
     * Wrapper method for MongoCursor::setReadPreference().
317
     *
318
     * @see CursorInterface::setReadPreference()
319
     * @see http://php.net/manual/en/mongocursor.setreadpreference.php
320
     * @param string $readPreference
321
     * @param array  $tags
322
     * @return $this
323
     */
324
    public function setReadPreference($readPreference, array $tags = null)
325
    {
326
        $this->baseCursor->setReadPreference($readPreference, $tags);
327
        $this->unitOfWorkHints[Query::HINT_READ_PREFERENCE] = $readPreference;
328
        $this->unitOfWorkHints[Query::HINT_READ_PREFERENCE_TAGS] = $tags;
329
        return $this;
330
    }
331
332
    /**
333
     * Reset the cursor and return its first result.
334
     *
335
     * The cursor will be reset both before and after the single result is
336
     * fetched. The original cursor limit (if any) will remain in place.
337
     *
338
     * @see Iterator::getSingleResult()
339
     * @return array|object|null
340
     */
341 89
    public function getSingleResult()
342
    {
343 89
        $document = $this->hydrateDocument($this->baseCursor->getSingleResult());
0 ignored issues
show
Bug introduced by
It seems like $this->baseCursor->getSingleResult() targeting Doctrine\MongoDB\Iterator::getSingleResult() can also be of type null or object; however, Doctrine\ODM\MongoDB\Cursor::hydrateDocument() does only seem to accept array, maybe add an additional type check?

This check looks at variables that are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
344 89
        $this->primeReferencesForSingleResult($document);
0 ignored issues
show
Bug introduced by
It seems like $document defined by $this->hydrateDocument($...sor->getSingleResult()) on line 343 can also be of type array; however, Doctrine\ODM\MongoDB\Cur...rencesForSingleResult() does only seem to accept object, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
345
346 89
        return $document;
347
    }
348
349
    /**
350
     * {@inheritDoc}
351
     */
352 54
    public function getUseIdentifierKeys()
353
    {
354 54
        return $this->baseCursor->getUseIdentifierKeys();
355
    }
356
357
    /**
358
     * {@inheritDoc}
359
     */
360 54
    public function setUseIdentifierKeys($useIdentifierKeys)
361
    {
362 54
        $this->baseCursor->setUseIdentifierKeys($useIdentifierKeys);
363
364 54
        return $this;
365
    }
366
367
    /**
368
     * {@inheritDoc}
369
     */
370
    public function hasNext()
371
    {
372
        return $this->baseCursor->hasNext();
373
    }
374
375
    /**
376
     * Wrapper method for MongoCursor::hint().
377
     *
378
     * This method is intended for setting MongoDB query hints, which are
379
     * unrelated to UnitOfWork hints.
380
     *
381
     * @see CursorInterface::hint()
382
     * @see http://php.net/manual/en/mongocursor.hint.php
383
     * @param array|string $keyPattern
384
     * @return $this
385
     */
386
    public function hint($keyPattern)
387
    {
388
        $this->baseCursor->hint($keyPattern);
389
        return $this;
390
    }
391
392
    /**
393
     * Set whether to hydrate results as document class instances.
394
     *
395
     * @param boolean $hydrate
396
     * @return $this
397
     */
398 133
    public function hydrate($hydrate = true)
399
    {
400 133
        $this->hydrate = (boolean) $hydrate;
401 133
        return $this;
402
    }
403
404
    /**
405
     * @param array $document
406
     * @return array|object|null
407
     */
408 133
    private function hydrateDocument($document)
409
    {
410 133
        if ($document !== null && $this->hydrate) {
411 125
            return $this->unitOfWork->getOrCreateDocument($this->class->name, $document, $this->unitOfWorkHints);
412
        }
413
414 12
        return $document;
415
    }
416
417
    /**
418
     * Wrapper method for MongoCursor::immortal().
419
     *
420
     * @see CursorInterface::immortal()
421
     * @see http://php.net/manual/en/mongocursor.immortal.php
422
     * @param boolean $liveForever
423
     * @return $this
424
     */
425
    public function immortal($liveForever = true)
426
    {
427
        $this->baseCursor->immortal($liveForever);
428
        return $this;
429
    }
430
431
    /**
432
     * Wrapper method for MongoCursor::info().
433
     *
434
     * @see CursorInterface::info()
435
     * @see http://php.net/manual/en/mongocursor.info.php
436
     * @return array
437
     */
438
    public function info()
439
    {
440
        return $this->baseCursor->info();
441
    }
442
443
    /**
444
     * Wrapper method for MongoCursor::key().
445
     *
446
     * @see CursorInterface::key()
447
     * @see http://php.net/manual/en/iterator.key.php
448
     * @see http://php.net/manual/en/mongocursor.key.php
449
     * @return string
450
     */
451 5
    public function key()
452
    {
453 5
        return $this->baseCursor->key();
454
    }
455
456
    /**
457
     * Wrapper method for MongoCursor::limit().
458
     *
459
     * @see CursorInterface::limit()
460
     * @see http://php.net/manual/en/mongocursor.limit.php
461
     * @param integer $num
462
     * @return $this
463
     */
464 13
    public function limit($num)
465
    {
466 13
        $this->baseCursor->limit($num);
467 13
        return $this;
468
    }
469
470
    /**
471
     * Wrapper method for MongoCursor::next().
472
     *
473
     * @see CursorInterface::next()
474
     * @see http://php.net/manual/en/iterator.next.php
475
     * @see http://php.net/manual/en/mongocursor.next.php
476
     */
477 58
    public function next()
478
    {
479 58
        $this->baseCursor->next();
480 58
    }
481
482
    /**
483
     * Recreates the internal MongoCursor.
484
     *
485
     * @see CursorInterface::recreate()
486
     */
487 2
    public function recreate()
488
    {
489 2
        $this->baseCursor->recreate();
490 2
    }
491
492
    /**
493
     * Set whether to refresh hydrated documents that are already in the
494
     * identity map.
495
     *
496
     * This option has no effect if hydration is disabled.
497
     *
498
     * @param boolean $refresh
499
     * @return $this
500
     */
501
    public function refresh($refresh = true)
502
    {
503
        $this->unitOfWorkHints[Query::HINT_REFRESH] = (boolean) $refresh;
504
        return $this;
505
    }
506
507
    /**
508
     * Wrapper method for MongoCursor::reset().
509
     *
510
     * @see CursorInterface::reset()
511
     * @see http://php.net/manual/en/iterator.reset.php
512
     * @see http://php.net/manual/en/mongocursor.reset.php
513
     */
514 1
    public function reset()
515
    {
516 1
        $this->baseCursor->reset();
517 1
    }
518
519
    /**
520
     * Wrapper method for MongoCursor::rewind().
521
     *
522
     * @see CursorInterface::rewind()
523
     * @see http://php.net/manual/en/iterator.rewind.php
524
     * @see http://php.net/manual/en/mongocursor.rewind.php
525
     */
526 61
    public function rewind()
527
    {
528 61
        $this->baseCursor->rewind();
529 61
    }
530
531
    /**
532
     * Wrapper method for MongoCursor::skip().
533
     *
534
     * @see CursorInterface::skip()
535
     * @see http://php.net/manual/en/mongocursor.skip.php
536
     * @param integer $num
537
     * @return $this
538
     */
539 2
    public function skip($num)
540
    {
541 2
        $this->baseCursor->skip($num);
542 2
        return $this;
543
    }
544
545
    /**
546
     * Wrapper method for MongoCursor::slaveOkay().
547
     *
548
     * @see CursorInterface::slaveOkay()
549
     * @see http://php.net/manual/en/mongocursor.slaveokay.php
550
     * @param boolean $ok
551
     * @return $this
552
     *
553
     * @deprecated in version 1.2 - use setReadPreference instead.
554
     */
555
    public function slaveOkay($ok = true)
556
    {
557
        @trigger_error(
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
558
            sprintf('%s was deprecated in version 1.2 - use setReadPreference instead.'),
559
            E_USER_DEPRECATED
560
        );
561
        $ok = (boolean) $ok;
562
        $this->baseCursor->slaveOkay($ok);
563
        $this->unitOfWorkHints[Query::HINT_SLAVE_OKAY] = $ok;
0 ignored issues
show
Deprecated Code introduced by
The constant Doctrine\ODM\MongoDB\Query\Query::HINT_SLAVE_OKAY has been deprecated.

This class constant has been deprecated.

Loading history...
564
        return $this;
565
    }
566
567
    /**
568
     * Wrapper method for MongoCursor::snapshot().
569
     *
570
     * @see CursorInterface::snapshot()
571
     * @see http://php.net/manual/en/mongocursor.snapshot.php
572
     * @return $this
573
     */
574
    public function snapshot()
575
    {
576
        $this->baseCursor->snapshot();
577
        return $this;
578
    }
579
580
    /**
581
     * Wrapper method for MongoCursor::sort().
582
     *
583
     * Field names will be prepared according to the document mapping.
584
     *
585
     * @see CursorInterface::sort()
586
     * @see http://php.net/manual/en/mongocursor.sort.php
587
     * @param array $fields
588
     * @return $this
589
     */
590 14
    public function sort($fields)
591
    {
592 14
        $fields = $this->unitOfWork
593 14
            ->getDocumentPersister($this->class->name)
594 14
            ->prepareSortOrProjection($fields);
595
596 14
        $this->baseCursor->sort($fields);
597 14
        return $this;
598
    }
599
600
    /**
601
     * Wrapper method for MongoCursor::tailable().
602
     *
603
     * @see CursorInterface::tailable()
604
     * @see http://php.net/manual/en/mongocursor.tailable.php
605
     * @param boolean $tail
606
     * @return $this
607
     */
608
    public function tailable($tail = true)
609
    {
610
        $this->baseCursor->tailable($tail);
611
        return $this;
612
    }
613
614
    /**
615
     * Wrapper method for MongoCursor::timeout().
616
     *
617
     * @see CursorInterface::timeout()
618
     * @see http://php.net/manual/en/mongocursor.timeout.php
619
     * @param integer $ms
620
     * @return $this
621
     */
622
    public function timeout($ms)
623
    {
624
        $this->baseCursor->timeout($ms);
625
        return $this;
626
    }
627
628
    /**
629
     * Return the cursor's results as an array.
630
     *
631
     * If documents in the result set use BSON objects for their "_id", the
632
     * $useKeys parameter may be set to false to avoid errors attempting to cast
633
     * arrays (i.e. BSON objects) to string keys.
634
     *
635
     * @see Iterator::toArray()
636
     * @param boolean $useIdentifierKeys
637
     * @return array
638
     */
639 54
    public function toArray($useIdentifierKeys = null)
640
    {
641 54
        $originalUseIdentifierKeys = $this->getUseIdentifierKeys();
642 54
        $useIdentifierKeys = isset($useIdentifierKeys) ? (boolean) $useIdentifierKeys : $this->baseCursor->getUseIdentifierKeys();
643
644
        /* Let iterator_to_array() decide to use keys or not. This will avoid
645
         * superfluous MongoCursor::info() from the key() method until the
646
         * cursor position is tracked internally.
647
         */
648 54
        $this->setUseIdentifierKeys(true);
649
650 54
        $results = iterator_to_array($this, $useIdentifierKeys);
651
652 52
        $this->setUseIdentifierKeys($originalUseIdentifierKeys);
653
654 52
        return $results;
655
    }
656
657
    /**
658
     * Wrapper method for MongoCursor::valid().
659
     *
660
     * @see CursorInterface::valid()
661
     * @see http://php.net/manual/en/iterator.valid.php
662
     * @see http://php.net/manual/en/mongocursor.valid.php
663
     * @return boolean
664
     */
665 65
    public function valid()
666
    {
667 65
        return $this->baseCursor->valid();
668
    }
669
670
    /**
671
     * @param array $primers
672
     * @param ReferencePrimer $referencePrimer
673
     * @return $this
674
     */
675 23
    public function enableReferencePriming(array $primers, ReferencePrimer $referencePrimer)
676
    {
677 23
        if ( ! $this->baseCursor instanceof BaseEagerCursor) {
678 1
            throw new \BadMethodCallException("Can't enable reference priming when not using eager cursors.");
679
        }
680
681 22
        $this->referencePrimer = $referencePrimer;
682 22
        $this->primers = $primers;
683 22
        return $this;
684
    }
685
686
    /**
687
     * Prime references
688
     */
689 62
    protected function primeReferences()
690
    {
691 62
        if ($this->referencesPrimed || ! $this->hydrate || empty($this->primers)) {
692 60
            return;
693
        }
694
695 16
        $this->referencesPrimed = true;
696
697 16
        foreach ($this->primers as $fieldName => $primer) {
698 16
            $primer = is_callable($primer) ? $primer : null;
699 16
            $this->referencePrimer->primeReferences($this->class, $this, $fieldName, $this->unitOfWorkHints, $primer);
700
        }
701
702 14
        $this->rewind();
703 14
    }
704
705
    /**
706
     * Primes all references for a single document only. This avoids iterating
707
     * over the entire cursor when getSingleResult() is called.
708
     *
709
     * @param object $document
710
     */
711 89
    protected function primeReferencesForSingleResult($document)
712
    {
713 89
        if ($this->referencesPrimed || ! $this->hydrate || empty($this->primers) || null === $document) {
714 85
            return;
715
        }
716
717 4 View Code Duplication
        foreach ($this->primers as $fieldName => $primer) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
718 4
            $primer = is_callable($primer) ? $primer : null;
719 4
            $this->referencePrimer->primeReferences($this->class, array($document), $fieldName, $this->unitOfWorkHints, $primer);
720
        }
721 4
    }
722
}
723