diff options
author | polo <ordipolo@gmx.fr> | 2024-08-13 23:45:21 +0200 |
---|---|---|
committer | polo <ordipolo@gmx.fr> | 2024-08-13 23:45:21 +0200 |
commit | bf6655a534a6775d30cafa67bd801276bda1d98d (patch) | |
tree | c6381e3f6c81c33eab72508f410b165ba05f7e9c /vendor/doctrine/instantiator/src/Doctrine | |
parent | 94d67a4b51f8e62e7d518cce26a526ae1ec48278 (diff) | |
download | AppliGestionPHP-bf6655a534a6775d30cafa67bd801276bda1d98d.zip |
VERSION 0.2 doctrine ORM et entités
Diffstat (limited to 'vendor/doctrine/instantiator/src/Doctrine')
5 files changed, 406 insertions, 0 deletions
diff --git a/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/ExceptionInterface.php b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/ExceptionInterface.php new file mode 100644 index 0000000..1e59192 --- /dev/null +++ b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/ExceptionInterface.php | |||
@@ -0,0 +1,14 @@ | |||
1 | <?php | ||
2 | |||
3 | declare(strict_types=1); | ||
4 | |||
5 | namespace Doctrine\Instantiator\Exception; | ||
6 | |||
7 | use Throwable; | ||
8 | |||
9 | /** | ||
10 | * Base exception marker interface for the instantiator component | ||
11 | */ | ||
12 | interface ExceptionInterface extends Throwable | ||
13 | { | ||
14 | } | ||
diff --git a/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/InvalidArgumentException.php b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/InvalidArgumentException.php new file mode 100644 index 0000000..5b91a00 --- /dev/null +++ b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/InvalidArgumentException.php | |||
@@ -0,0 +1,52 @@ | |||
1 | <?php | ||
2 | |||
3 | declare(strict_types=1); | ||
4 | |||
5 | namespace Doctrine\Instantiator\Exception; | ||
6 | |||
7 | use InvalidArgumentException as BaseInvalidArgumentException; | ||
8 | use ReflectionClass; | ||
9 | |||
10 | use function interface_exists; | ||
11 | use function sprintf; | ||
12 | use function trait_exists; | ||
13 | |||
14 | /** | ||
15 | * Exception for invalid arguments provided to the instantiator | ||
16 | */ | ||
17 | class InvalidArgumentException extends BaseInvalidArgumentException implements ExceptionInterface | ||
18 | { | ||
19 | public static function fromNonExistingClass(string $className): self | ||
20 | { | ||
21 | if (interface_exists($className)) { | ||
22 | return new self(sprintf('The provided type "%s" is an interface, and cannot be instantiated', $className)); | ||
23 | } | ||
24 | |||
25 | if (trait_exists($className)) { | ||
26 | return new self(sprintf('The provided type "%s" is a trait, and cannot be instantiated', $className)); | ||
27 | } | ||
28 | |||
29 | return new self(sprintf('The provided class "%s" does not exist', $className)); | ||
30 | } | ||
31 | |||
32 | /** | ||
33 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
34 | * | ||
35 | * @template T of object | ||
36 | */ | ||
37 | public static function fromAbstractClass(ReflectionClass $reflectionClass): self | ||
38 | { | ||
39 | return new self(sprintf( | ||
40 | 'The provided class "%s" is abstract, and cannot be instantiated', | ||
41 | $reflectionClass->getName(), | ||
42 | )); | ||
43 | } | ||
44 | |||
45 | public static function fromEnum(string $className): self | ||
46 | { | ||
47 | return new self(sprintf( | ||
48 | 'The provided class "%s" is an enum, and cannot be instantiated', | ||
49 | $className, | ||
50 | )); | ||
51 | } | ||
52 | } | ||
diff --git a/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/UnexpectedValueException.php b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/UnexpectedValueException.php new file mode 100644 index 0000000..4f70ded --- /dev/null +++ b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Exception/UnexpectedValueException.php | |||
@@ -0,0 +1,61 @@ | |||
1 | <?php | ||
2 | |||
3 | declare(strict_types=1); | ||
4 | |||
5 | namespace Doctrine\Instantiator\Exception; | ||
6 | |||
7 | use Exception; | ||
8 | use ReflectionClass; | ||
9 | use UnexpectedValueException as BaseUnexpectedValueException; | ||
10 | |||
11 | use function sprintf; | ||
12 | |||
13 | /** | ||
14 | * Exception for given parameters causing invalid/unexpected state on instantiation | ||
15 | */ | ||
16 | class UnexpectedValueException extends BaseUnexpectedValueException implements ExceptionInterface | ||
17 | { | ||
18 | /** | ||
19 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
20 | * | ||
21 | * @template T of object | ||
22 | */ | ||
23 | public static function fromSerializationTriggeredException( | ||
24 | ReflectionClass $reflectionClass, | ||
25 | Exception $exception, | ||
26 | ): self { | ||
27 | return new self( | ||
28 | sprintf( | ||
29 | 'An exception was raised while trying to instantiate an instance of "%s" via un-serialization', | ||
30 | $reflectionClass->getName(), | ||
31 | ), | ||
32 | 0, | ||
33 | $exception, | ||
34 | ); | ||
35 | } | ||
36 | |||
37 | /** | ||
38 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
39 | * | ||
40 | * @template T of object | ||
41 | */ | ||
42 | public static function fromUncleanUnSerialization( | ||
43 | ReflectionClass $reflectionClass, | ||
44 | string $errorString, | ||
45 | int $errorCode, | ||
46 | string $errorFile, | ||
47 | int $errorLine, | ||
48 | ): self { | ||
49 | return new self( | ||
50 | sprintf( | ||
51 | 'Could not produce an instance of "%s" via un-serialization, since an error was triggered ' | ||
52 | . 'in file "%s" at line "%d"', | ||
53 | $reflectionClass->getName(), | ||
54 | $errorFile, | ||
55 | $errorLine, | ||
56 | ), | ||
57 | 0, | ||
58 | new Exception($errorString, $errorCode), | ||
59 | ); | ||
60 | } | ||
61 | } | ||
diff --git a/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Instantiator.php b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Instantiator.php new file mode 100644 index 0000000..f803f89 --- /dev/null +++ b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/Instantiator.php | |||
@@ -0,0 +1,255 @@ | |||
1 | <?php | ||
2 | |||
3 | declare(strict_types=1); | ||
4 | |||
5 | namespace Doctrine\Instantiator; | ||
6 | |||
7 | use ArrayIterator; | ||
8 | use Doctrine\Instantiator\Exception\ExceptionInterface; | ||
9 | use Doctrine\Instantiator\Exception\InvalidArgumentException; | ||
10 | use Doctrine\Instantiator\Exception\UnexpectedValueException; | ||
11 | use Exception; | ||
12 | use ReflectionClass; | ||
13 | use ReflectionException; | ||
14 | use Serializable; | ||
15 | |||
16 | use function class_exists; | ||
17 | use function enum_exists; | ||
18 | use function is_subclass_of; | ||
19 | use function restore_error_handler; | ||
20 | use function set_error_handler; | ||
21 | use function sprintf; | ||
22 | use function strlen; | ||
23 | use function unserialize; | ||
24 | |||
25 | final class Instantiator implements InstantiatorInterface | ||
26 | { | ||
27 | /** | ||
28 | * Markers used internally by PHP to define whether {@see \unserialize} should invoke | ||
29 | * the method {@see \Serializable::unserialize()} when dealing with classes implementing | ||
30 | * the {@see \Serializable} interface. | ||
31 | * | ||
32 | * @deprecated This constant will be private in 2.0 | ||
33 | */ | ||
34 | private const SERIALIZATION_FORMAT_USE_UNSERIALIZER = 'C'; | ||
35 | private const SERIALIZATION_FORMAT_AVOID_UNSERIALIZER = 'O'; | ||
36 | |||
37 | /** | ||
38 | * Used to instantiate specific classes, indexed by class name. | ||
39 | * | ||
40 | * @var callable[] | ||
41 | */ | ||
42 | private static array $cachedInstantiators = []; | ||
43 | |||
44 | /** | ||
45 | * Array of objects that can directly be cloned, indexed by class name. | ||
46 | * | ||
47 | * @var object[] | ||
48 | */ | ||
49 | private static array $cachedCloneables = []; | ||
50 | |||
51 | /** | ||
52 | * @phpstan-param class-string<T> $className | ||
53 | * | ||
54 | * @phpstan-return T | ||
55 | * | ||
56 | * @throws ExceptionInterface | ||
57 | * | ||
58 | * @template T of object | ||
59 | */ | ||
60 | public function instantiate(string $className): object | ||
61 | { | ||
62 | if (isset(self::$cachedCloneables[$className])) { | ||
63 | /** @phpstan-var T */ | ||
64 | $cachedCloneable = self::$cachedCloneables[$className]; | ||
65 | |||
66 | return clone $cachedCloneable; | ||
67 | } | ||
68 | |||
69 | if (isset(self::$cachedInstantiators[$className])) { | ||
70 | $factory = self::$cachedInstantiators[$className]; | ||
71 | |||
72 | return $factory(); | ||
73 | } | ||
74 | |||
75 | return $this->buildAndCacheFromFactory($className); | ||
76 | } | ||
77 | |||
78 | /** | ||
79 | * Builds the requested object and caches it in static properties for performance | ||
80 | * | ||
81 | * @phpstan-param class-string<T> $className | ||
82 | * | ||
83 | * @phpstan-return T | ||
84 | * | ||
85 | * @template T of object | ||
86 | */ | ||
87 | private function buildAndCacheFromFactory(string $className): object | ||
88 | { | ||
89 | $factory = self::$cachedInstantiators[$className] = $this->buildFactory($className); | ||
90 | $instance = $factory(); | ||
91 | |||
92 | if ($this->isSafeToClone(new ReflectionClass($instance))) { | ||
93 | self::$cachedCloneables[$className] = clone $instance; | ||
94 | } | ||
95 | |||
96 | return $instance; | ||
97 | } | ||
98 | |||
99 | /** | ||
100 | * Builds a callable capable of instantiating the given $className without | ||
101 | * invoking its constructor. | ||
102 | * | ||
103 | * @phpstan-param class-string<T> $className | ||
104 | * | ||
105 | * @phpstan-return callable(): T | ||
106 | * | ||
107 | * @throws InvalidArgumentException | ||
108 | * @throws UnexpectedValueException | ||
109 | * @throws ReflectionException | ||
110 | * | ||
111 | * @template T of object | ||
112 | */ | ||
113 | private function buildFactory(string $className): callable | ||
114 | { | ||
115 | $reflectionClass = $this->getReflectionClass($className); | ||
116 | |||
117 | if ($this->isInstantiableViaReflection($reflectionClass)) { | ||
118 | return [$reflectionClass, 'newInstanceWithoutConstructor']; | ||
119 | } | ||
120 | |||
121 | $serializedString = sprintf( | ||
122 | '%s:%d:"%s":0:{}', | ||
123 | is_subclass_of($className, Serializable::class) ? self::SERIALIZATION_FORMAT_USE_UNSERIALIZER : self::SERIALIZATION_FORMAT_AVOID_UNSERIALIZER, | ||
124 | strlen($className), | ||
125 | $className, | ||
126 | ); | ||
127 | |||
128 | $this->checkIfUnSerializationIsSupported($reflectionClass, $serializedString); | ||
129 | |||
130 | return static fn () => unserialize($serializedString); | ||
131 | } | ||
132 | |||
133 | /** | ||
134 | * @phpstan-param class-string<T> $className | ||
135 | * | ||
136 | * @phpstan-return ReflectionClass<T> | ||
137 | * | ||
138 | * @throws InvalidArgumentException | ||
139 | * @throws ReflectionException | ||
140 | * | ||
141 | * @template T of object | ||
142 | */ | ||
143 | private function getReflectionClass(string $className): ReflectionClass | ||
144 | { | ||
145 | if (! class_exists($className)) { | ||
146 | throw InvalidArgumentException::fromNonExistingClass($className); | ||
147 | } | ||
148 | |||
149 | if (enum_exists($className, false)) { | ||
150 | throw InvalidArgumentException::fromEnum($className); | ||
151 | } | ||
152 | |||
153 | $reflection = new ReflectionClass($className); | ||
154 | |||
155 | if ($reflection->isAbstract()) { | ||
156 | throw InvalidArgumentException::fromAbstractClass($reflection); | ||
157 | } | ||
158 | |||
159 | return $reflection; | ||
160 | } | ||
161 | |||
162 | /** | ||
163 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
164 | * | ||
165 | * @throws UnexpectedValueException | ||
166 | * | ||
167 | * @template T of object | ||
168 | */ | ||
169 | private function checkIfUnSerializationIsSupported(ReflectionClass $reflectionClass, string $serializedString): void | ||
170 | { | ||
171 | set_error_handler(static function (int $code, string $message, string $file, int $line) use ($reflectionClass, &$error): bool { | ||
172 | $error = UnexpectedValueException::fromUncleanUnSerialization( | ||
173 | $reflectionClass, | ||
174 | $message, | ||
175 | $code, | ||
176 | $file, | ||
177 | $line, | ||
178 | ); | ||
179 | |||
180 | return true; | ||
181 | }); | ||
182 | |||
183 | try { | ||
184 | $this->attemptInstantiationViaUnSerialization($reflectionClass, $serializedString); | ||
185 | } finally { | ||
186 | restore_error_handler(); | ||
187 | } | ||
188 | |||
189 | if ($error) { | ||
190 | throw $error; | ||
191 | } | ||
192 | } | ||
193 | |||
194 | /** | ||
195 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
196 | * | ||
197 | * @throws UnexpectedValueException | ||
198 | * | ||
199 | * @template T of object | ||
200 | */ | ||
201 | private function attemptInstantiationViaUnSerialization(ReflectionClass $reflectionClass, string $serializedString): void | ||
202 | { | ||
203 | try { | ||
204 | unserialize($serializedString); | ||
205 | } catch (Exception $exception) { | ||
206 | throw UnexpectedValueException::fromSerializationTriggeredException($reflectionClass, $exception); | ||
207 | } | ||
208 | } | ||
209 | |||
210 | /** | ||
211 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
212 | * | ||
213 | * @template T of object | ||
214 | */ | ||
215 | private function isInstantiableViaReflection(ReflectionClass $reflectionClass): bool | ||
216 | { | ||
217 | return ! ($this->hasInternalAncestors($reflectionClass) && $reflectionClass->isFinal()); | ||
218 | } | ||
219 | |||
220 | /** | ||
221 | * Verifies whether the given class is to be considered internal | ||
222 | * | ||
223 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
224 | * | ||
225 | * @template T of object | ||
226 | */ | ||
227 | private function hasInternalAncestors(ReflectionClass $reflectionClass): bool | ||
228 | { | ||
229 | do { | ||
230 | if ($reflectionClass->isInternal()) { | ||
231 | return true; | ||
232 | } | ||
233 | |||
234 | $reflectionClass = $reflectionClass->getParentClass(); | ||
235 | } while ($reflectionClass); | ||
236 | |||
237 | return false; | ||
238 | } | ||
239 | |||
240 | /** | ||
241 | * Checks if a class is cloneable | ||
242 | * | ||
243 | * Classes implementing `__clone` cannot be safely cloned, as that may cause side-effects. | ||
244 | * | ||
245 | * @phpstan-param ReflectionClass<T> $reflectionClass | ||
246 | * | ||
247 | * @template T of object | ||
248 | */ | ||
249 | private function isSafeToClone(ReflectionClass $reflectionClass): bool | ||
250 | { | ||
251 | return $reflectionClass->isCloneable() | ||
252 | && ! $reflectionClass->hasMethod('__clone') | ||
253 | && ! $reflectionClass->isSubclassOf(ArrayIterator::class); | ||
254 | } | ||
255 | } | ||
diff --git a/vendor/doctrine/instantiator/src/Doctrine/Instantiator/InstantiatorInterface.php b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/InstantiatorInterface.php new file mode 100644 index 0000000..c6ebe35 --- /dev/null +++ b/vendor/doctrine/instantiator/src/Doctrine/Instantiator/InstantiatorInterface.php | |||
@@ -0,0 +1,24 @@ | |||
1 | <?php | ||
2 | |||
3 | declare(strict_types=1); | ||
4 | |||
5 | namespace Doctrine\Instantiator; | ||
6 | |||
7 | use Doctrine\Instantiator\Exception\ExceptionInterface; | ||
8 | |||
9 | /** | ||
10 | * Instantiator provides utility methods to build objects without invoking their constructors | ||
11 | */ | ||
12 | interface InstantiatorInterface | ||
13 | { | ||
14 | /** | ||
15 | * @phpstan-param class-string<T> $className | ||
16 | * | ||
17 | * @phpstan-return T | ||
18 | * | ||
19 | * @throws ExceptionInterface | ||
20 | * | ||
21 | * @template T of object | ||
22 | */ | ||
23 | public function instantiate(string $className): object; | ||
24 | } | ||