allow vendord
All checks were successful
Build, Push and Deploy / build-and-push (push) Successful in 3m3s
Gitea Actions Demo / Explore-Gitea-Actions (push) Successful in 16s
Build, Push and Deploy / deploy-staging (push) Successful in 32s
Build, Push and Deploy / deploy-production (push) Has been skipped
Build, Push and Deploy / cleanup (push) Successful in 1s

This commit is contained in:
2026-03-30 14:54:57 +07:00
parent 66aed7c4e8
commit b5e3a778ce
21316 changed files with 2777892 additions and 13 deletions

View File

@@ -0,0 +1,99 @@
<?php
declare(strict_types=1);
namespace Doctrine\Persistence\Reflection;
use BackedEnum;
use ReflectionProperty;
use function array_map;
use function is_array;
use function reset;
/**
* PHP Enum Reflection Property - special override for backed enums.
*/
class EnumReflectionProperty extends ReflectionProperty
{
/** @param class-string<BackedEnum> $enumType */
public function __construct(private readonly ReflectionProperty $originalReflectionProperty, private readonly string $enumType)
{
parent::__construct($originalReflectionProperty->class, $originalReflectionProperty->name);
}
/**
* {@inheritDoc}
*
* Converts enum instance to its value.
*
* @param object|null $object
*
* @return int|string|int[]|string[]|null
*/
public function getValue($object = null): int|string|array|null
{
if ($object === null) {
return null;
}
$enum = $this->originalReflectionProperty->getValue($object);
if ($enum === null) {
return null;
}
return $this->fromEnum($enum);
}
/**
* Converts enum value to enum instance.
*
* @param object|null $object
*/
public function setValue(mixed $object, mixed $value = null): void
{
if ($value !== null) {
$value = $this->toEnum($value);
}
$this->originalReflectionProperty->setValue($object, $value);
}
/**
* @param BackedEnum|BackedEnum[] $enum
*
* @return ($enum is BackedEnum ? (string|int) : (string[]|int[]))
*/
private function fromEnum(BackedEnum|array $enum)
{
if (is_array($enum)) {
return array_map(static fn (BackedEnum $enum) => $enum->value, $enum);
}
return $enum->value;
}
/**
* @param int|string|int[]|string[]|BackedEnum|BackedEnum[] $value
*
* @return ($value is int|string|BackedEnum ? BackedEnum : BackedEnum[])
*/
private function toEnum(int|string|array|BackedEnum $value)
{
if ($value instanceof BackedEnum) {
return $value;
}
if (is_array($value)) {
$v = reset($value);
if ($v instanceof BackedEnum) {
return $value;
}
return array_map([$this->enumType, 'from'], $value);
}
return $this->enumType::from($value);
}
}

View File

@@ -0,0 +1,63 @@
<?php
declare(strict_types=1);
namespace Doctrine\Persistence\Reflection;
use Doctrine\Persistence\Proxy;
use ReflectionProperty;
use function ltrim;
use function method_exists;
/**
* PHP Runtime Reflection Property.
*
* Avoids triggering lazy loading if the provided object
* is a {@see \Doctrine\Persistence\Proxy}.
*/
class RuntimeReflectionProperty extends ReflectionProperty
{
private readonly string $key;
/** @param class-string $class */
public function __construct(string $class, string $name)
{
parent::__construct($class, $name);
$this->key = $this->isPrivate() ? "\0" . ltrim($class, '\\') . "\0" . $name : ($this->isProtected() ? "\0*\0" . $name : $name);
}
public function getValue(object|null $object = null): mixed
{
if ($object === null) {
return parent::getValue($object);
}
return ((array) $object)[$this->key] ?? null;
}
/**
* {@inheritDoc}
*
* @param object|null $object
*/
public function setValue(mixed $object, mixed $value = null): void
{
if (! ($object instanceof Proxy && ! $object->__isInitialized())) {
parent::setValue($object, $value);
return;
}
if (! method_exists($object, '__setInitialized')) {
return;
}
$object->__setInitialized(true);
parent::setValue($object, $value);
$object->__setInitialized(false);
}
}

View File

@@ -0,0 +1,57 @@
<?php
declare(strict_types=1);
namespace Doctrine\Persistence\Reflection;
use Closure;
use function assert;
/**
* PHP Typed No Default Reflection Property - special override for typed properties without a default value.
*/
class TypedNoDefaultReflectionProperty extends RuntimeReflectionProperty
{
/**
* {@inheritDoc}
*
* Checks that a typed property is initialized before accessing its value.
* This is necessary to avoid PHP error "Error: Typed property must not be accessed before initialization".
* Should be used only for reflecting typed properties without a default value.
*/
public function getValue(object|null $object = null): mixed
{
return $object !== null && $this->isInitialized($object) ? parent::getValue($object) : null;
}
/**
* {@inheritDoc}
*
* Works around the problem with setting typed no default properties to
* NULL which is not supported, instead unset() to uninitialize.
*
* @link https://github.com/doctrine/orm/issues/7999
*
* @param object|null $object
*/
public function setValue(mixed $object, mixed $value = null): void
{
if ($value === null && $this->hasType() && ! $this->getType()->allowsNull()) {
$propertyName = $this->getName();
$unsetter = function () use ($propertyName): void {
unset($this->$propertyName);
};
$unsetter = $unsetter->bindTo($object, $this->getDeclaringClass()->getName());
assert($unsetter instanceof Closure);
$unsetter();
return;
}
parent::setValue($object, $value);
}
}