Passed
Pull Request — develop (#6935)
by Michael
503:01 queued 406:10
created

Configuration::getEntityNamespace()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 7
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 4
CRAP Score 2

Importance

Changes 0
Metric Value
cc 2
eloc 3
nc 2
nop 1
dl 0
loc 7
rs 9.4285
c 0
b 0
f 0
ccs 4
cts 4
cp 1
crap 2
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Doctrine\ORM;
6
7
use Doctrine\Common\Annotations\AnnotationReader;
8
use Doctrine\Common\Annotations\AnnotationRegistry;
9
use Doctrine\Common\Annotations\CachedReader;
10
use Doctrine\Common\Cache\ArrayCache;
11
use Doctrine\Common\Cache\Cache as CacheDriver;
12
use Doctrine\Common\Persistence\ObjectRepository;
13
use Doctrine\DBAL\Configuration as DBALConfiguration;
14
use Doctrine\ORM\Cache\CacheConfiguration;
15
use Doctrine\ORM\Mapping\ClassMetadataFactory;
16
use Doctrine\ORM\Mapping\DefaultEntityListenerResolver;
17
use Doctrine\ORM\Mapping\Driver\AnnotationDriver;
18
use Doctrine\ORM\Mapping\Driver\MappingDriver;
19
use Doctrine\ORM\Mapping\EntityListenerResolver;
20
use Doctrine\ORM\Mapping\Factory\DefaultNamingStrategy;
21
use Doctrine\ORM\Mapping\Factory\NamingStrategy;
22
use Doctrine\ORM\Proxy\Factory\ProxyFactory;
23
use Doctrine\ORM\Query\ResultSetMapping;
24
use Doctrine\ORM\Repository\DefaultRepositoryFactory;
25
use Doctrine\ORM\Repository\RepositoryFactory;
26
use ProxyManager\Configuration as ProxyManagerConfiguration;
27
use ProxyManager\Factory\LazyLoadingGhostFactory;
28
use ProxyManager\FileLocator\FileLocator;
29
use ProxyManager\GeneratorStrategy\EvaluatingGeneratorStrategy;
30
use ProxyManager\GeneratorStrategy\FileWriterGeneratorStrategy;
31
32
/**
33
 * Configuration container for all configuration options of Doctrine.
34
 * It combines all configuration options from DBAL & ORM.
35
 *
36
 * Internal note: When adding a new configuration option just write a getter/setter pair.
37
 *
38
 * @since 2.0
39
 * @author  Benjamin Eberlei <[email protected]>
40
 * @author  Guilherme Blanco <[email protected]>
41
 * @author  Jonathan Wage <[email protected]>
42
 * @author  Roman Borschel <[email protected]>
43
 */
44
class Configuration extends DBALConfiguration
45
{
46
    /**
47
     * @var ProxyManagerConfiguration|null
48
     */
49
    private $proxyManagerConfiguration;
50
51
    /**
52
     * @var MappingDriver|null
53
     */
54
    private $metadataDriver;
55
56
    /**
57
     * @var CacheDriver|null
58
     */
59
    private $queryCache;
60
61
    /**
62
     * @var CacheDriver|null
63
     */
64
    private $hydrationCache;
65
66
    /**
67
     * @var CacheDriver|null
68
     */
69
    private $metadataCache;
70
71
    /**
72
     * @var string[] indexed by alias
73
     */
74
    private $entityNamespaces = [];
0 ignored issues
show
introduced by
The private property $entityNamespaces is not used, and could be removed.
Loading history...
75
76
    /**
77
     * @var string[] of DQL, indexed by query name
78
     */
79
    private $namedQueries = [];
80
81
    /**
82
     * @var string[][]|ResultSetMapping[][] tuples of [$sqlString, $resultSetMapping] indexed by query name
83
     */
84
    private $namedNativeQueries = [];
85
86
    /**
87
     * @var string[][]|ResultSetMapping[][] tuples of [$sqlString, $resultSetMapping] indexed by query name
88
     */
89
    private $customStringFunctions = [];
90
91
    /**
92
     * @var string[][]|ResultSetMapping[][] tuples of [$sqlString, $resultSetMapping] indexed by query name
93
     */
94
    private $customNumericFunctions = [];
95
96
    /**
97
     * @var string[][]|ResultSetMapping[][] tuples of [$sqlString, $resultSetMapping] indexed by query name
98
     */
99
    private $customDatetimeFunctions = [];
100
101
    /**
102
     * @var string[] of hydrator class names, indexed by mode name
103
     */
104
    private $customHydrationModes = [];
105
106
    /**
107
     * @var string
108
     */
109
    private $classMetadataFactoryClassName = ClassMetadataFactory::class;
110
111
    /**
112
     * @var string[] of filter class names, indexed by filter name
113
     */
114
    private $filters;
115
116
    /**
117
     * @var string
118
     */
119
    private $defaultRepositoryClassName = EntityRepository::class;
120
121
    /**
122
     * @var NamingStrategy|null
123
     */
124
    private $namingStrategy;
125
126
    /**
127
     * @var EntityListenerResolver|null
128
     */
129
    private $entityListenerResolver;
130
131
    /**
132
     * @var RepositoryFactory|null
133
     */
134
    private $repositoryFactory;
135
136
    /**
137
     * @var bool
138
     */
139
    private $isSecondLevelCacheEnabled = false;
140
141
    /**
142
     * @var CacheConfiguration|null
143
     */
144
    private $secondLevelCacheConfiguration;
145
146
    /**
147
     * @var mixed[] indexed by hint name
148
     */
149
    private $defaultQueryHints = [];
150
151
    /**
152
     * Sets the directory where Doctrine generates any necessary proxy class files.
153
     */
154 53
    public function setProxyDir(string $directory) : void
155
    {
156 53
        $this->getProxyManagerConfiguration()->setProxiesTargetDir($directory);
157 53
        $this->setAutoGenerateProxyClasses(ProxyFactory::AUTOGENERATE_FILE_NOT_EXISTS);
158 53
    }
159
160
    /**
161
     * Sets the strategy for automatically generating proxy classes.
162
     *
163
     * @param boolean|int $autoGenerate Possible values are constants of Doctrine\ORM\Proxy\Factory\ProxyFactory.
164
     *                                  True is converted to AUTOGENERATE_ALWAYS, false to AUTOGENERATE_NEVER.
165
     */
166 1142
    public function setAutoGenerateProxyClasses($autoGenerate) : void
167
    {
168 1142
        $proxyManagerConfig = $this->getProxyManagerConfiguration();
169
170 1142
        switch ((int) $autoGenerate) {
171 1142
            case ProxyFactory::AUTOGENERATE_ALWAYS:
172 1140
            case ProxyFactory::AUTOGENERATE_FILE_NOT_EXISTS:
173 62
                $proxyManagerConfig->setGeneratorStrategy(new FileWriterGeneratorStrategy(
174 62
                    new FileLocator($proxyManagerConfig->getProxiesTargetDir())
175
                ));
176
177 62
                return;
178 1084
            case ProxyFactory::AUTOGENERATE_NEVER:
179 1079
            case ProxyFactory::AUTOGENERATE_EVAL:
180
            default:
181 1084
                $proxyManagerConfig->setGeneratorStrategy(new EvaluatingGeneratorStrategy());
182
183 1084
                return;
184
        }
185
    }
186
187
    /**
188
     * Sets the namespace where proxy classes reside.
189
     */
190 1129
    public function setProxyNamespace(string $namespace) : void
191
    {
192 1129
        $this->getProxyManagerConfiguration()->setProxiesNamespace($namespace);
193 1129
    }
194
195
    /**
196
     * Sets the cache driver implementation that is used for metadata caching.
197
     *
198
     * @todo Force parameter to be a Closure to ensure lazy evaluation
199
     *       (as soon as a metadata cache is in effect, the driver never needs to initialize).
200
     */
201 1125
    public function setMetadataDriverImpl(MappingDriver $metadataDriver) : void
202
    {
203 1125
        $this->metadataDriver = $metadataDriver;
204 1125
    }
205
206
    /**
207
     * Adds a new default annotation driver with a correctly configured annotation reader.
208
     *
209
     * @param string[] $paths
210
     *
211
     * @return AnnotationDriver
212
     */
213 1113
    public function newDefaultAnnotationDriver(array $paths = []) : AnnotationDriver
214
    {
215 1113
        AnnotationRegistry::registerFile(__DIR__ . '/Annotation/DoctrineAnnotations.php');
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\Common\Annotati...egistry::registerFile() has been deprecated: this method is deprecated and will be removed in doctrine/annotations 2.0 autoloading should be deferred to the globally registered autoloader by then. For now, use @example AnnotationRegistry::registerLoader('class_exists') ( Ignorable by Annotation )

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

215
        /** @scrutinizer ignore-deprecated */ AnnotationRegistry::registerFile(__DIR__ . '/Annotation/DoctrineAnnotations.php');

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...
216
217 1113
        $reader = new CachedReader(new AnnotationReader(), new ArrayCache());
218
219 1113
        return new AnnotationDriver($reader, $paths);
220
    }
221
222
    /**
223
     * Gets the cache driver implementation that is used for the mapping metadata.
224
     */
225 3
    public function getMetadataDriverImpl() : ?MappingDriver
226
    {
227 3
        return $this->metadataDriver;
228 3
    }
229
230
    /**
231
     * Gets the cache driver implementation that is used for the query cache (SQL cache).
232
     */
233
    public function getQueryCacheImpl() : ?CacheDriver
234
    {
235 8
        return $this->queryCache;
236
    }
237 8
238 1
    /**
239
     * Sets the cache driver implementation that is used for the query cache (SQL cache).
240
     */
241 8
    public function setQueryCacheImpl(CacheDriver $queryCache) : void
242
    {
243
        $this->queryCache = $queryCache;
244
    }
245
246
    /**
247
     * Gets the cache driver implementation that is used for the hydration cache (SQL cache).
248
     */
249 42
    public function getHydrationCacheImpl() : ?CacheDriver
250
    {
251 42
        return $this->hydrationCache;
252 42
    }
253
254
    /**
255
     * Sets the cache driver implementation that is used for the hydration cache (SQL cache).
256
     */
257
    public function setHydrationCacheImpl(CacheDriver $hydrationCache) : void
258
    {
259 1
        $this->hydrationCache = $hydrationCache;
260
    }
261 1
262
    /**
263
     * Gets the cache driver implementation that is used for metadata caching.
264
     */
265
    public function getMetadataCacheImpl() : ?CacheDriver
266
    {
267 1123
        return $this->metadataCache;
268
    }
269 1123
270
    /**
271
     * Sets the cache driver implementation that is used for metadata caching.
272
     */
273
    public function setMetadataCacheImpl(CacheDriver $metadataCache) : void
274
    {
275 166
        $this->metadataCache = $metadataCache;
276
    }
277 166
278
    /**
279
     * Adds a named DQL query to the configuration.
280
     */
281
    public function addNamedQuery(string $queryName, string $dqlQuery) : void
282
    {
283 1091
        $this->namedQueries[$queryName] = $dqlQuery;
284
    }
285 1091
286 1091
    /**
287
     * Gets a previously registered named DQL query.
288
     *
289
     * @throws ORMException
290
     */
291 1
    public function getNamedQuery(string $queryName) : string
292
    {
293 1
        if ( ! isset($this->namedQueries[$queryName])) {
294
            throw ORMException::namedQueryNotFound($queryName);
295
        }
296
297
        return $this->namedQueries[$queryName];
298
    }
299 1
300
    /**
301 1
     * Adds a named native query to the configuration.
302 1
     */
303
    public function addNamedNativeQuery(string $queryName, string $sql, ResultSetMapping $resultSetMapping) : void
304
    {
305
        $this->namedNativeQueries[$queryName] = [$sql, $resultSetMapping];
306
    }
307 1130
308
    /**
309 1130
     * Gets the components of a previously registered named native query.
310
     *
311
     * @return string[]|ResultSetMapping[] tuple of [$sqlString, $resultSetMaping]
312
     *
313
     * @throws ORMException
314
     */
315 1091
    public function getNamedNativeQuery(string $queryName) : array
316
    {
317 1091
        if ( ! isset($this->namedNativeQueries[$queryName])) {
318 1091
            throw ORMException::namedNativeQueryNotFound($queryName);
319
        }
320
321
        return $this->namedNativeQueries[$queryName];
322
    }
323 1
324
    /**
325 1
     * Ensures that this Configuration instance contains settings that are
326 1
     * suitable for a production environment.
327
     *
328
     * @throws ORMException If a configuration setting has a value that is not
329
     *                      suitable for a production environment.
330
     */
331
    public function ensureProductionSettings() : void
332
    {
333 1
        $queryCacheImpl = $this->getQueryCacheImpl();
334
335 1
        if ( ! $queryCacheImpl) {
336 1
            throw ORMException::queryCacheNotConfigured();
337
        }
338
339 1
        if ($queryCacheImpl instanceof ArrayCache) {
340
            throw ORMException::queryCacheUsesNonPersistentCache($queryCacheImpl);
341
        }
342
343
        $metadataCacheImpl = $this->getMetadataCacheImpl();
344
345 1
        if ( ! $metadataCacheImpl) {
346
            throw ORMException::metadataCacheNotConfigured();
347 1
        }
348 1
349
        if ($metadataCacheImpl instanceof ArrayCache) {
350
            throw ORMException::metadataCacheUsesNonPersistentCache($metadataCacheImpl);
351
        }
352
353
        if ($this->getProxyManagerConfiguration()->getGeneratorStrategy() instanceof EvaluatingGeneratorStrategy) {
354
            throw ORMException::proxyClassesAlwaysRegenerating();
355
        }
356
    }
357 1
358
    /**
359 1
     * Registers a custom DQL function that produces a string value.
360 1
     * Such a function can then be used in any DQL statement in any place where string
361
     * functions are allowed.
362
     *
363 1
     * DQL function names are case-insensitive.
364
     *
365
     * @param string|callable $classNameOrFactory Class name or a callable that returns the function.
366
     */
367
    public function addCustomStringFunction(string $functionName, $classNameOrFactory) : void
368
    {
369
        $this->customStringFunctions[\strtolower($functionName)] = $classNameOrFactory;
370
    }
371
372
    /**
373 6
     * Gets the implementation class name of a registered custom string DQL function.
374
     *
375 6
     * @return string|callable|null
376
     */
377 6
    public function getCustomStringFunction(string $functionName)
378 1
    {
379
        return $this->customStringFunctions[\strtolower($functionName)] ?? null;
380
    }
381 5
382 1
    /**
383
     * Sets a map of custom DQL string functions.
384
     *
385 4
     * Keys must be function names and values the FQCN of the implementing class.
386
     * The function names will be case-insensitive in DQL.
387 4
     *
388 1
     * Any previously added string functions are discarded.
389
     *
390
     * @param array $functions The map of custom DQL string functions.
391 3
     */
392 1
    public function setCustomStringFunctions(array $functions) : void
393
    {
394
        foreach ($functions as $name => $className) {
395 2
            $this->addCustomStringFunction($name, $className);
396 1
        }
397
    }
398 1
399
    /**
400
     * Registers a custom DQL function that produces a numeric value.
401
     * Such a function can then be used in any DQL statement in any place where numeric
402
     * functions are allowed.
403
     *
404
     * DQL function names are case-insensitive.
405
     *
406
     * @param string|callable $classNameOrFactory Class name or a callable that returns the function.
407
     */
408
    public function addCustomNumericFunction(string $functionName, $classNameOrFactory) : void
409 2
    {
410
        $this->customNumericFunctions[\strtolower($functionName)] = $classNameOrFactory;
411 2
    }
412 2
413
    /**
414
     * Gets the implementation class name of a registered custom numeric DQL function.
415
     *
416
     * @return string|callable|null
417
     */
418
    public function getCustomNumericFunction(string $functionName)
419 99
    {
420
        return $this->customNumericFunctions[\strtolower($functionName)] ?? null;
421 99
    }
422
423
    /**
424
     * Sets a map of custom DQL numeric functions.
425
     *
426
     * Keys must be function names and values the FQCN of the implementing class.
427
     * The function names will be case-insensitive in DQL.
428
     *
429
     * Any previously added numeric functions are discarded.
430
     *
431
     * @param array $functions The map of custom DQL numeric functions.
432
     */
433
    public function setCustomNumericFunctions(array $functions) : void
434 1
    {
435
        foreach ($functions as $name => $className) {
436 1
            $this->addCustomNumericFunction($name, $className);
437 1
        }
438
    }
439 1
440
    /**
441
     * Registers a custom DQL function that produces a date/time value.
442
     * Such a function can then be used in any DQL statement in any place where date/time
443
     * functions are allowed.
444
     *
445
     * DQL function names are case-insensitive.
446
     *
447
     * @param string|callable $classNameOrFactory Class name or a callable that returns the function.
448
     */
449
    public function addCustomDatetimeFunction(string $functionName, $classNameOrFactory)
450 2
    {
451
        $this->customDatetimeFunctions[\strtolower($functionName)] = $classNameOrFactory;
452 2
    }
453 2
454
    /**
455
     * Gets the implementation class name of a registered custom date/time DQL function.
456
     *
457
     * @return string|callable|null
458
     */
459
    public function getCustomDatetimeFunction(string $functionName)
460 98
    {
461
        return $this->customDatetimeFunctions[\strtolower($functionName)] ?? null;
462 98
    }
463
464
    /**
465
     * Sets a map of custom DQL date/time functions.
466
     *
467
     * Keys must be function names and values the FQCN of the implementing class.
468
     * The function names will be case-insensitive in DQL.
469
     *
470
     * Any previously added date/time functions are discarded.
471
     *
472
     * @param array $functions The map of custom DQL date/time functions.
473
     */
474
    public function setCustomDatetimeFunctions(array $functions) : void
475 2
    {
476
        foreach ($functions as $name => $className) {
477 2
            $this->addCustomDatetimeFunction($name, $className);
478 1
        }
479
    }
480 2
481
    /**
482
     * Sets the custom hydrator modes in one pass.
483
     *
484
     * @param iterable $modes An iterable of string $modeName => string $hydratorClassName
485
     */
486
    public function setCustomHydrationModes(iterable $modes) : void
487
    {
488
        $this->customHydrationModes = [];
489
490
        foreach ($modes as $modeName => $hydrator) {
491 1
            $this->addCustomHydrationMode($modeName, $hydrator);
492
        }
493 1
    }
494 1
495
    /**
496
     * Gets the hydrator class for the given hydration mode name.
497
     *
498
     * @return string|null The hydrator class name.
499
     */
500
    public function getCustomHydrationMode(string $modeName) : ?string
501 97
    {
502
        return $this->customHydrationModes[$modeName] ?? null;
503 97
    }
504
505
    /**
506
     * Adds a custom hydration mode.
507
     */
508
    public function addCustomHydrationMode(string $modeName, string $hydratorClassName) : void
509
    {
510
        $this->customHydrationModes[$modeName] = $hydratorClassName;
511
    }
512
513
    /**
514
     * Sets a class metadata factory.
515
     */
516 1
    public function setClassMetadataFactoryName(string $classMetadataFactoryClassName) : void
517
    {
518 1
        $this->classMetadataFactoryClassName = $classMetadataFactoryClassName;
519 1
    }
520
521 1
    public function getClassMetadataFactoryName() : string
522
    {
523
        return $this->classMetadataFactoryClassName;
524
    }
525
526
    /**
527
     * Adds a filter to the list of possible filters.
528 1
     */
529
    public function addFilter(string $filterName, string $filterClassName) : void
530 1
    {
531
        $this->filters[$filterName] = $filterClassName;
532 1
    }
533 1
534
    /**
535 1
     * Gets the class name for a given filter name.
536
     *
537
     * @return string|null The class name of the filter
538
     */
539
    public function getFilterClassName(string $filterName) : ?string
540
    {
541
        return $this->filters[$filterName] ?? null;
542 3
    }
543
544 3
    /**
545
     * Sets default repository class.
546
     *
547
     * @since 2.2
548
     *
549
     * @throws ORMException If not is a \Doctrine\Common\Persistence\ObjectRepository implementation
550 3
     */
551
    public function setDefaultRepositoryClassName(string $repositoryClassName) : void
552 3
    {
553 3
        $reflectionClass = new \ReflectionClass($repositoryClassName);
554
555
        if ( ! $reflectionClass->implementsInterface(ObjectRepository::class)) {
556
            throw ORMException::invalidEntityRepository($repositoryClassName);
557
        }
558 1
559
        $this->defaultRepositoryClassName = $repositoryClassName;
560 1
    }
561 1
562
    /**
563 1121
     * Get default repository class.
564
     *
565 1121
     * @since 2.2
566
     */
567
    public function getDefaultRepositoryClassName() : string
568
    {
569
        return $this->defaultRepositoryClassName;
570
    }
571 14
572
    /**
573 14
     * Sets naming strategy.
574 14
     *
575
     * @since 2.3
576
     */
577
    public function setNamingStrategy(NamingStrategy $namingStrategy) : void
578
    {
579
        $this->namingStrategy = $namingStrategy;
580
    }
581 13
582
    /**
583 13
     * Gets naming strategy..
584
     *
585
     * @since 2.3
586
     */
587
    public function getNamingStrategy() : ?NamingStrategy
588
    {
589
        return $this->namingStrategy
590
            ?? $this->namingStrategy = new DefaultNamingStrategy();
591
    }
592
593 2
    /**
594
     * Set the entity listener resolver.
595 2
     *
596
     * @since 2.4
597 2
     */
598 1
    public function setEntityListenerResolver(EntityListenerResolver $resolver) : void
599
    {
600
        $this->entityListenerResolver = $resolver;
601 1
    }
602 1
603
    /**
604
     * Get the entity listener resolver.
605
     *
606
     * @since 2.4
607
     */
608
    public function getEntityListenerResolver() : EntityListenerResolver
609 2
    {
610
        return $this->entityListenerResolver
611 2
            ?? $this->entityListenerResolver = new DefaultEntityListenerResolver();
612
    }
613
614
    /**
615
     * Set the entity repository factory.
616
     *
617
     * @since 2.4
618
     */
619 3
    public function setRepositoryFactory(RepositoryFactory $repositoryFactory) : void
620
    {
621 3
        $this->repositoryFactory = $repositoryFactory;
622 3
    }
623
624
    /**
625
     * Get the entity repository factory.
626
     *
627
     * @since 2.4
628
     */
629 809
    public function getRepositoryFactory() : RepositoryFactory
630
    {
631 809
        return $this->repositoryFactory
632 809
            ?? $this->repositoryFactory = new DefaultRepositoryFactory();
633
    }
634
635
    /**
636
     * @since 2.5
637
     */
638
    public function isSecondLevelCacheEnabled() : bool
639
    {
640 1
        return $this->isSecondLevelCacheEnabled;
641
    }
642 1
643 1
    /**
644
     * @since 2.5
645
     */
646
    public function setSecondLevelCacheEnabled(bool $flag = true) : void
647
    {
648
        $this->isSecondLevelCacheEnabled = $flag;
649
    }
650 1121
651
    /**
652 1121
     * @since 2.5
653 1121
     */
654
    public function setSecondLevelCacheConfiguration(CacheConfiguration $cacheConfig) : void
655
    {
656
        $this->secondLevelCacheConfiguration = $cacheConfig;
657
    }
658
659
    /**
660
     * @since 2.5
661
     *
662
     * @return  \Doctrine\ORM\Cache\CacheConfiguration|null
663
     */
664
    public function getSecondLevelCacheConfiguration() : ?CacheConfiguration
665
    {
666
        if ($this->isSecondLevelCacheEnabled && ! $this->secondLevelCacheConfiguration) {
667
            $this->secondLevelCacheConfiguration = new CacheConfiguration();
668
        }
669
670
        return $this->secondLevelCacheConfiguration;
671 1120
    }
672
673 1120
    /**
674 1120
     * Returns query hints, which will be applied to every query in application
675
     *
676
     * @since 2.5
677
     */
678
    public function getDefaultQueryHints() : array
679
    {
680 1120
        return $this->defaultQueryHints;
681
    }
682 1120
683
    /**
684
     * Sets array of query hints, which will be applied to every query in application
685
     *
686
     * @since 2.5
687
     */
688 119
    public function setDefaultQueryHints(array $defaultQueryHints) : void
689
    {
690 119
        $this->defaultQueryHints = $defaultQueryHints;
691 119
    }
692
693
    /**
694
     * Gets the value of a default query hint. If the hint name is not recognized, FALSE is returned.
695
     *
696 120
     * @since 2.5
697
     *
698 120
     * @return mixed The value of the hint or FALSE, if the hint name is not recognized.
699 120
     */
700
    public function getDefaultQueryHint(string $hintName)
701
    {
702
        return $this->defaultQueryHints[$hintName] ?? false;
703
    }
704
705
    /**
706 120
     * Sets a default query hint. If the hint name is not recognized, it is silently ignored.
707
     *
708 120
     * @since 2.5
709
     *
710
     * @param mixed  $value The value of the hint.
711
     */
712 120
    public function setDefaultQueryHint(string $hintName, $value) : void
713
    {
714
        $this->defaultQueryHints[$hintName] = $value;
715
    }
716
717
    public function buildGhostObjectFactory() : LazyLoadingGhostFactory
718
    {
719
        return new LazyLoadingGhostFactory(clone $this->getProxyManagerConfiguration());
720 541
    }
721
722 541
    public function getProxyManagerConfiguration() : ProxyManagerConfiguration
723
    {
724
        return $this->proxyManagerConfiguration
725
            ?? $this->proxyManagerConfiguration = new ProxyManagerConfiguration();
726
    }
727
}
728