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/symfony/var-exporter/LazyGhostTrait.php | |
| parent | 94d67a4b51f8e62e7d518cce26a526ae1ec48278 (diff) | |
| download | AppliGestionPHP-bf6655a534a6775d30cafa67bd801276bda1d98d.tar.gz AppliGestionPHP-bf6655a534a6775d30cafa67bd801276bda1d98d.tar.bz2 AppliGestionPHP-bf6655a534a6775d30cafa67bd801276bda1d98d.zip | |
VERSION 0.2 doctrine ORM et entités
Diffstat (limited to 'vendor/symfony/var-exporter/LazyGhostTrait.php')
| -rw-r--r-- | vendor/symfony/var-exporter/LazyGhostTrait.php | 352 |
1 files changed, 352 insertions, 0 deletions
diff --git a/vendor/symfony/var-exporter/LazyGhostTrait.php b/vendor/symfony/var-exporter/LazyGhostTrait.php new file mode 100644 index 0000000..fa82ced --- /dev/null +++ b/vendor/symfony/var-exporter/LazyGhostTrait.php | |||
| @@ -0,0 +1,352 @@ | |||
| 1 | <?php | ||
| 2 | |||
| 3 | /* | ||
| 4 | * This file is part of the Symfony package. | ||
| 5 | * | ||
| 6 | * (c) Fabien Potencier <fabien@symfony.com> | ||
| 7 | * | ||
| 8 | * For the full copyright and license information, please view the LICENSE | ||
| 9 | * file that was distributed with this source code. | ||
| 10 | */ | ||
| 11 | |||
| 12 | namespace Symfony\Component\VarExporter; | ||
| 13 | |||
| 14 | use Symfony\Component\Serializer\Attribute\Ignore; | ||
| 15 | use Symfony\Component\VarExporter\Internal\Hydrator; | ||
| 16 | use Symfony\Component\VarExporter\Internal\LazyObjectRegistry as Registry; | ||
| 17 | use Symfony\Component\VarExporter\Internal\LazyObjectState; | ||
| 18 | use Symfony\Component\VarExporter\Internal\LazyObjectTrait; | ||
| 19 | |||
| 20 | trait LazyGhostTrait | ||
| 21 | { | ||
| 22 | use LazyObjectTrait; | ||
| 23 | |||
| 24 | /** | ||
| 25 | * Creates a lazy-loading ghost instance. | ||
| 26 | * | ||
| 27 | * Skipped properties should be indexed by their array-cast identifier, see | ||
| 28 | * https://php.net/manual/language.types.array#language.types.array.casting | ||
| 29 | * | ||
| 30 | * @param (\Closure(static):void $initializer The closure should initialize the object it receives as argument | ||
| 31 | * @param array<string, true>|null $skippedProperties An array indexed by the properties to skip, a.k.a. the ones | ||
| 32 | * that the initializer doesn't initialize, if any | ||
| 33 | * @param static|null $instance | ||
| 34 | */ | ||
| 35 | public static function createLazyGhost(\Closure $initializer, ?array $skippedProperties = null, ?object $instance = null): static | ||
| 36 | { | ||
| 37 | if (self::class !== $class = $instance ? $instance::class : static::class) { | ||
| 38 | $skippedProperties["\0".self::class."\0lazyObjectState"] = true; | ||
| 39 | } | ||
| 40 | |||
| 41 | if (!isset(Registry::$defaultProperties[$class])) { | ||
| 42 | Registry::$classReflectors[$class] ??= new \ReflectionClass($class); | ||
| 43 | $instance ??= Registry::$classReflectors[$class]->newInstanceWithoutConstructor(); | ||
| 44 | Registry::$defaultProperties[$class] ??= (array) $instance; | ||
| 45 | Registry::$classResetters[$class] ??= Registry::getClassResetters($class); | ||
| 46 | |||
| 47 | if (self::class === $class && \defined($class.'::LAZY_OBJECT_PROPERTY_SCOPES')) { | ||
| 48 | Hydrator::$propertyScopes[$class] ??= $class::LAZY_OBJECT_PROPERTY_SCOPES; | ||
| 49 | } | ||
| 50 | } else { | ||
| 51 | $instance ??= Registry::$classReflectors[$class]->newInstanceWithoutConstructor(); | ||
| 52 | } | ||
| 53 | |||
| 54 | $instance->lazyObjectState = new LazyObjectState($initializer, $skippedProperties ??= []); | ||
| 55 | |||
| 56 | foreach (Registry::$classResetters[$class] as $reset) { | ||
| 57 | $reset($instance, $skippedProperties); | ||
| 58 | } | ||
| 59 | |||
| 60 | return $instance; | ||
| 61 | } | ||
| 62 | |||
| 63 | /** | ||
| 64 | * Returns whether the object is initialized. | ||
| 65 | * | ||
| 66 | * @param $partial Whether partially initialized objects should be considered as initialized | ||
| 67 | */ | ||
| 68 | #[Ignore] | ||
| 69 | public function isLazyObjectInitialized(bool $partial = false): bool | ||
| 70 | { | ||
| 71 | if (!$state = $this->lazyObjectState ?? null) { | ||
| 72 | return true; | ||
| 73 | } | ||
| 74 | |||
| 75 | return LazyObjectState::STATUS_INITIALIZED_FULL === $state->status; | ||
| 76 | } | ||
| 77 | |||
| 78 | /** | ||
| 79 | * Forces initialization of a lazy object and returns it. | ||
| 80 | */ | ||
| 81 | public function initializeLazyObject(): static | ||
| 82 | { | ||
| 83 | if (!$state = $this->lazyObjectState ?? null) { | ||
| 84 | return $this; | ||
| 85 | } | ||
| 86 | |||
| 87 | if (LazyObjectState::STATUS_UNINITIALIZED_FULL === $state->status) { | ||
| 88 | $state->initialize($this, '', null); | ||
| 89 | } | ||
| 90 | |||
| 91 | return $this; | ||
| 92 | } | ||
| 93 | |||
| 94 | /** | ||
| 95 | * @return bool Returns false when the object cannot be reset, ie when it's not a lazy object | ||
| 96 | */ | ||
| 97 | public function resetLazyObject(): bool | ||
| 98 | { | ||
| 99 | if (!$state = $this->lazyObjectState ?? null) { | ||
| 100 | return false; | ||
| 101 | } | ||
| 102 | |||
| 103 | if (LazyObjectState::STATUS_UNINITIALIZED_FULL !== $state->status) { | ||
| 104 | $state->reset($this); | ||
| 105 | } | ||
| 106 | |||
| 107 | return true; | ||
| 108 | } | ||
| 109 | |||
| 110 | public function &__get($name): mixed | ||
| 111 | { | ||
| 112 | $propertyScopes = Hydrator::$propertyScopes[$this::class] ??= Hydrator::getPropertyScopes($this::class); | ||
| 113 | $scope = null; | ||
| 114 | |||
| 115 | if ([$class, , $readonlyScope] = $propertyScopes[$name] ?? null) { | ||
| 116 | $scope = Registry::getScope($propertyScopes, $class, $name); | ||
| 117 | $state = $this->lazyObjectState ?? null; | ||
| 118 | |||
| 119 | if ($state && (null === $scope || isset($propertyScopes["\0$scope\0$name"]))) { | ||
| 120 | if (LazyObjectState::STATUS_INITIALIZED_FULL === $state->status) { | ||
| 121 | // Work around php/php-src#12695 | ||
| 122 | $property = null === $scope ? $name : "\0$scope\0$name"; | ||
| 123 | $property = $propertyScopes[$property][3] | ||
| 124 | ?? Hydrator::$propertyScopes[$this::class][$property][3] = new \ReflectionProperty($scope ?? $class, $name); | ||
| 125 | } else { | ||
| 126 | $property = null; | ||
| 127 | } | ||
| 128 | |||
| 129 | if ($property?->isInitialized($this) ?? LazyObjectState::STATUS_UNINITIALIZED_PARTIAL !== $state->initialize($this, $name, $readonlyScope ?? $scope)) { | ||
| 130 | goto get_in_scope; | ||
| 131 | } | ||
| 132 | } | ||
| 133 | } | ||
| 134 | |||
| 135 | if ($parent = (Registry::$parentMethods[self::class] ??= Registry::getParentMethods(self::class))['get']) { | ||
| 136 | if (2 === $parent) { | ||
| 137 | return parent::__get($name); | ||
| 138 | } | ||
| 139 | $value = parent::__get($name); | ||
| 140 | |||
| 141 | return $value; | ||
| 142 | } | ||
| 143 | |||
| 144 | if (null === $class) { | ||
| 145 | $frame = debug_backtrace(\DEBUG_BACKTRACE_IGNORE_ARGS, 1)[0]; | ||
| 146 | trigger_error(sprintf('Undefined property: %s::$%s in %s on line %s', $this::class, $name, $frame['file'], $frame['line']), \E_USER_NOTICE); | ||
| 147 | } | ||
| 148 | |||
| 149 | get_in_scope: | ||
| 150 | |||
| 151 | try { | ||
| 152 | if (null === $scope) { | ||
| 153 | if (null === $readonlyScope) { | ||
| 154 | return $this->$name; | ||
| 155 | } | ||
| 156 | $value = $this->$name; | ||
| 157 | |||
| 158 | return $value; | ||
| 159 | } | ||
| 160 | $accessor = Registry::$classAccessors[$scope] ??= Registry::getClassAccessors($scope); | ||
| 161 | |||
| 162 | return $accessor['get']($this, $name, null !== $readonlyScope); | ||
| 163 | } catch (\Error $e) { | ||
| 164 | if (\Error::class !== $e::class || !str_starts_with($e->getMessage(), 'Cannot access uninitialized non-nullable property')) { | ||
| 165 | throw $e; | ||
| 166 | } | ||
| 167 | |||
| 168 | try { | ||
| 169 | if (null === $scope) { | ||
| 170 | $this->$name = []; | ||
| 171 | |||
| 172 | return $this->$name; | ||
| 173 | } | ||
| 174 | |||
| 175 | $accessor['set']($this, $name, []); | ||
| 176 | |||
| 177 | return $accessor['get']($this, $name, null !== $readonlyScope); | ||
| 178 | } catch (\Error) { | ||
| 179 | if (preg_match('/^Cannot access uninitialized non-nullable property ([^ ]++) by reference$/', $e->getMessage(), $matches)) { | ||
| 180 | throw new \Error('Typed property '.$matches[1].' must not be accessed before initialization', $e->getCode(), $e->getPrevious()); | ||
| 181 | } | ||
| 182 | |||
| 183 | throw $e; | ||
| 184 | } | ||
| 185 | } | ||
| 186 | } | ||
| 187 | |||
| 188 | public function __set($name, $value): void | ||
| 189 | { | ||
| 190 | $propertyScopes = Hydrator::$propertyScopes[$this::class] ??= Hydrator::getPropertyScopes($this::class); | ||
| 191 | $scope = null; | ||
| 192 | |||
| 193 | if ([$class, , $readonlyScope] = $propertyScopes[$name] ?? null) { | ||
| 194 | $scope = Registry::getScope($propertyScopes, $class, $name, $readonlyScope); | ||
| 195 | $state = $this->lazyObjectState ?? null; | ||
| 196 | |||
| 197 | if ($state && ($readonlyScope === $scope || isset($propertyScopes["\0$scope\0$name"])) | ||
| 198 | && LazyObjectState::STATUS_INITIALIZED_FULL !== $state->status | ||
| 199 | ) { | ||
| 200 | if (LazyObjectState::STATUS_UNINITIALIZED_FULL === $state->status) { | ||
| 201 | $state->initialize($this, $name, $readonlyScope ?? $scope); | ||
| 202 | } | ||
| 203 | goto set_in_scope; | ||
| 204 | } | ||
| 205 | } | ||
| 206 | |||
| 207 | if ((Registry::$parentMethods[self::class] ??= Registry::getParentMethods(self::class))['set']) { | ||
| 208 | parent::__set($name, $value); | ||
| 209 | |||
| 210 | return; | ||
| 211 | } | ||
| 212 | |||
| 213 | set_in_scope: | ||
| 214 | |||
| 215 | if (null === $scope) { | ||
| 216 | $this->$name = $value; | ||
| 217 | } else { | ||
| 218 | $accessor = Registry::$classAccessors[$scope] ??= Registry::getClassAccessors($scope); | ||
| 219 | $accessor['set']($this, $name, $value); | ||
| 220 | } | ||
| 221 | } | ||
| 222 | |||
| 223 | public function __isset($name): bool | ||
| 224 | { | ||
| 225 | $propertyScopes = Hydrator::$propertyScopes[$this::class] ??= Hydrator::getPropertyScopes($this::class); | ||
| 226 | $scope = null; | ||
| 227 | |||
| 228 | if ([$class, , $readonlyScope] = $propertyScopes[$name] ?? null) { | ||
| 229 | $scope = Registry::getScope($propertyScopes, $class, $name); | ||
| 230 | $state = $this->lazyObjectState ?? null; | ||
| 231 | |||
| 232 | if ($state && (null === $scope || isset($propertyScopes["\0$scope\0$name"])) | ||
| 233 | && LazyObjectState::STATUS_INITIALIZED_FULL !== $state->status | ||
| 234 | && LazyObjectState::STATUS_UNINITIALIZED_PARTIAL !== $state->initialize($this, $name, $readonlyScope ?? $scope) | ||
| 235 | ) { | ||
| 236 | goto isset_in_scope; | ||
| 237 | } | ||
| 238 | } | ||
| 239 | |||
| 240 | if ((Registry::$parentMethods[self::class] ??= Registry::getParentMethods(self::class))['isset']) { | ||
| 241 | return parent::__isset($name); | ||
| 242 | } | ||
| 243 | |||
| 244 | isset_in_scope: | ||
| 245 | |||
| 246 | if (null === $scope) { | ||
| 247 | return isset($this->$name); | ||
| 248 | } | ||
| 249 | $accessor = Registry::$classAccessors[$scope] ??= Registry::getClassAccessors($scope); | ||
| 250 | |||
| 251 | return $accessor['isset']($this, $name); | ||
| 252 | } | ||
| 253 | |||
| 254 | public function __unset($name): void | ||
| 255 | { | ||
| 256 | $propertyScopes = Hydrator::$propertyScopes[$this::class] ??= Hydrator::getPropertyScopes($this::class); | ||
| 257 | $scope = null; | ||
| 258 | |||
| 259 | if ([$class, , $readonlyScope] = $propertyScopes[$name] ?? null) { | ||
| 260 | $scope = Registry::getScope($propertyScopes, $class, $name, $readonlyScope); | ||
| 261 | $state = $this->lazyObjectState ?? null; | ||
| 262 | |||
| 263 | if ($state && ($readonlyScope === $scope || isset($propertyScopes["\0$scope\0$name"])) | ||
| 264 | && LazyObjectState::STATUS_INITIALIZED_FULL !== $state->status | ||
| 265 | ) { | ||
| 266 | if (LazyObjectState::STATUS_UNINITIALIZED_FULL === $state->status) { | ||
| 267 | $state->initialize($this, $name, $readonlyScope ?? $scope); | ||
| 268 | } | ||
| 269 | goto unset_in_scope; | ||
| 270 | } | ||
| 271 | } | ||
| 272 | |||
| 273 | if ((Registry::$parentMethods[self::class] ??= Registry::getParentMethods(self::class))['unset']) { | ||
| 274 | parent::__unset($name); | ||
| 275 | |||
| 276 | return; | ||
| 277 | } | ||
| 278 | |||
| 279 | unset_in_scope: | ||
| 280 | |||
| 281 | if (null === $scope) { | ||
| 282 | unset($this->$name); | ||
| 283 | } else { | ||
| 284 | $accessor = Registry::$classAccessors[$scope] ??= Registry::getClassAccessors($scope); | ||
| 285 | $accessor['unset']($this, $name); | ||
| 286 | } | ||
| 287 | } | ||
| 288 | |||
| 289 | public function __clone(): void | ||
| 290 | { | ||
| 291 | if ($state = $this->lazyObjectState ?? null) { | ||
| 292 | $this->lazyObjectState = clone $state; | ||
| 293 | } | ||
| 294 | |||
| 295 | if ((Registry::$parentMethods[self::class] ??= Registry::getParentMethods(self::class))['clone']) { | ||
| 296 | parent::__clone(); | ||
| 297 | } | ||
| 298 | } | ||
| 299 | |||
| 300 | public function __serialize(): array | ||
| 301 | { | ||
| 302 | $class = self::class; | ||
| 303 | |||
| 304 | if ((Registry::$parentMethods[$class] ??= Registry::getParentMethods($class))['serialize']) { | ||
| 305 | $properties = parent::__serialize(); | ||
| 306 | } else { | ||
| 307 | $this->initializeLazyObject(); | ||
| 308 | $properties = (array) $this; | ||
| 309 | } | ||
| 310 | unset($properties["\0$class\0lazyObjectState"]); | ||
| 311 | |||
| 312 | if (Registry::$parentMethods[$class]['serialize'] || !Registry::$parentMethods[$class]['sleep']) { | ||
| 313 | return $properties; | ||
| 314 | } | ||
| 315 | |||
| 316 | $scope = get_parent_class($class); | ||
| 317 | $data = []; | ||
| 318 | |||
| 319 | foreach (parent::__sleep() as $name) { | ||
| 320 | $value = $properties[$k = $name] ?? $properties[$k = "\0*\0$name"] ?? $properties[$k = "\0$class\0$name"] ?? $properties[$k = "\0$scope\0$name"] ?? $k = null; | ||
| 321 | |||
| 322 | if (null === $k) { | ||
| 323 | trigger_error(sprintf('serialize(): "%s" returned as member variable from __sleep() but does not exist', $name), \E_USER_NOTICE); | ||
| 324 | } else { | ||
| 325 | $data[$k] = $value; | ||
| 326 | } | ||
| 327 | } | ||
| 328 | |||
| 329 | return $data; | ||
| 330 | } | ||
| 331 | |||
| 332 | public function __destruct() | ||
| 333 | { | ||
| 334 | $state = $this->lazyObjectState ?? null; | ||
| 335 | |||
| 336 | if (LazyObjectState::STATUS_UNINITIALIZED_FULL === $state?->status) { | ||
| 337 | return; | ||
| 338 | } | ||
| 339 | |||
| 340 | if ((Registry::$parentMethods[self::class] ??= Registry::getParentMethods(self::class))['destruct']) { | ||
| 341 | parent::__destruct(); | ||
| 342 | } | ||
| 343 | } | ||
| 344 | |||
| 345 | #[Ignore] | ||
| 346 | private function setLazyObjectAsInitialized(bool $initialized): void | ||
| 347 | { | ||
| 348 | if ($state = $this->lazyObjectState ?? null) { | ||
| 349 | $state->status = $initialized ? LazyObjectState::STATUS_INITIALIZED_FULL : LazyObjectState::STATUS_UNINITIALIZED_FULL; | ||
| 350 | } | ||
| 351 | } | ||
| 352 | } | ||
