This commit is contained in:
cutemeli
2025-12-22 10:35:30 +00:00
parent 0bfc6c8425
commit 5ce7ca2c5d
38927 changed files with 0 additions and 4594700 deletions

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
/**
* Interface for advanced Metadata Factory implementations.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
* @author Jordan Stout <j@jrdn.org>
*/
interface AdvancedMetadataFactoryInterface extends MetadataFactoryInterface
{
/**
* Gets all the possible classes.
*
* @return string[]
*
* @throws \RuntimeException When driver does not an advanced driver.
*/
public function getAllClassNames() : array;
}

View File

@@ -1,21 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Cache;
use PleskRestApi\Metadata\ClassMetadata;
interface CacheInterface
{
/**
* Loads a class metadata instance from the cache
*/
public function load(string $class) : ?ClassMetadata;
/**
* Puts a class metadata instance into the cache
*/
public function put(ClassMetadata $metadata) : void;
/**
* Evicts the class metadata for the given class from the cache.
*/
public function evict(string $class) : void;
}

View File

@@ -1,15 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Cache;
/**
* @author Alexander Strizhak <gam6itko@gmail.com>
*/
interface ClearableCacheInterface
{
/**
* Clear all classes metadata from the cache.
*/
public function clear() : bool;
}

View File

@@ -1,47 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Cache;
use PleskRestApi\Doctrine\Common\Cache\Cache;
use PleskRestApi\Metadata\ClassMetadata;
/**
* @author Henrik Bjornskov <henrik@bjrnskov.dk>
*/
class DoctrineCacheAdapter implements CacheInterface, ClearableCacheInterface
{
/**
* @var string
*/
private $prefix;
/**
* @var Cache
*/
private $cache;
public function __construct(string $prefix, Cache $cache)
{
$this->prefix = $prefix;
$this->cache = $cache;
}
public function load(string $class) : ?ClassMetadata
{
$cache = $this->cache->fetch($this->prefix . $class);
return \false === $cache ? null : $cache;
}
public function put(ClassMetadata $metadata) : void
{
$this->cache->save($this->prefix . $metadata->name, $metadata);
}
public function evict(string $class) : void
{
$this->cache->delete($this->prefix . $class);
}
public function clear() : bool
{
if (\method_exists($this->cache, 'deleteAll')) {
// or $this->cache instanceof ClearableCache
return \call_user_func([$this->cache, 'deleteAll']);
}
return \false;
}
}

View File

@@ -1,111 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Cache;
use PleskRestApi\Metadata\ClassMetadata;
class FileCache implements CacheInterface, ClearableCacheInterface
{
/**
* @var string
*/
private $dir;
public function __construct(string $dir)
{
if (!\is_dir($dir) && \false === @\mkdir($dir, 0777, \true)) {
throw new \InvalidArgumentException(\sprintf('Can\'t create directory for cache at "%s"', $dir));
}
$this->dir = \rtrim($dir, '\\/');
}
public function load(string $class) : ?ClassMetadata
{
$path = $this->getCachePath($class);
if (!\is_readable($path)) {
return null;
}
try {
$metadata = (include $path);
if ($metadata instanceof ClassMetadata) {
return $metadata;
}
// if the file does not return anything, the return value is integer `1`.
} catch (\Error $e) {
// ignore corrupted cache
}
return null;
}
public function put(ClassMetadata $metadata) : void
{
if (!\is_writable($this->dir)) {
throw new \InvalidArgumentException(\sprintf('The directory "%s" is not writable.', $this->dir));
}
$path = $this->getCachePath($metadata->name);
if (!\is_writable(\dirname($path))) {
throw new \RuntimeException(\sprintf('Cache file "%s" is not writable.', $path));
}
$tmpFile = \tempnam($this->dir, 'metadata-cache');
if (\false === $tmpFile) {
$this->evict($metadata->name);
return;
}
$data = '<?php return unserialize(' . \var_export(\serialize($metadata), \true) . ');';
$bytesWritten = \file_put_contents($tmpFile, $data);
// use strlen and not mb_strlen. if there is utf8 in the code, it also writes more bytes.
if ($bytesWritten !== \strlen($data)) {
@\unlink($tmpFile);
// also evict the cache to not use an outdated version.
$this->evict($metadata->name);
return;
}
// Let's not break filesystems which do not support chmod.
@\chmod($tmpFile, 0666 & ~\umask());
$this->renameFile($tmpFile, $path);
}
/**
* Renames a file with fallback for windows
*/
private function renameFile(string $source, string $target) : void
{
if (\false === @\rename($source, $target)) {
if (\defined('PHP_WINDOWS_VERSION_BUILD')) {
if (\false === \copy($source, $target)) {
throw new \RuntimeException(\sprintf('(WIN) Could not write new cache file to %s.', $target));
}
if (\false === \unlink($source)) {
throw new \RuntimeException(\sprintf('(WIN) Could not delete temp cache file to %s.', $source));
}
} else {
throw new \RuntimeException(\sprintf('Could not write new cache file to %s.', $target));
}
}
}
public function evict(string $class) : void
{
$path = $this->getCachePath($class);
if (\file_exists($path)) {
@\unlink($path);
}
}
public function clear() : bool
{
$result = \true;
$files = \glob($this->dir . '/*.cache.php');
foreach ($files as $file) {
if (\is_file($file)) {
$result = $result && @\unlink($file);
}
}
return $result;
}
/**
* This function computes the cache file path.
*
* If anonymous class is to be cached, it contains invalid path characters that need to be removed/replaced
* Example of anonymous class name: class@anonymous\x00/app/src/Controller/DefaultController.php0x7f82a7e026ec
*/
private function getCachePath(string $key) : string
{
$fileName = \str_replace(['\\', "\x00", '@', '/', '$', '{', '}', ':'], '-', $key);
return $this->dir . '/' . $fileName . '.cache.php';
}
}

View File

@@ -1,56 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Cache;
use PleskRestApi\Metadata\ClassMetadata;
use Psr\Cache\CacheItemPoolInterface;
class PsrCacheAdapter implements CacheInterface, ClearableCacheInterface
{
/**
* @var string
*/
private $prefix;
/**
* @var CacheItemPoolInterface
*/
private $pool;
/**
* @var CacheItemPoolInterface
*/
private $lastItem;
public function __construct(string $prefix, CacheItemPoolInterface $pool)
{
$this->prefix = $prefix;
$this->pool = $pool;
}
public function load(string $class) : ?ClassMetadata
{
$this->lastItem = $this->pool->getItem($this->sanitizeCacheKey($this->prefix . $class));
return $this->lastItem->get();
}
public function put(ClassMetadata $metadata) : void
{
$key = $this->sanitizeCacheKey($this->prefix . $metadata->name);
if (null === $this->lastItem || $this->lastItem->getKey() !== $key) {
$this->lastItem = $this->pool->getItem($key);
}
$this->pool->save($this->lastItem->set($metadata));
}
public function evict(string $class) : void
{
$this->pool->deleteItem($this->sanitizeCacheKey($this->prefix . $class));
}
public function clear() : bool
{
return $this->pool->clear();
}
/**
* If anonymous class is to be cached, it contains invalid path characters that need to be removed/replaced
* Example of anonymous class name: class@anonymous\x00/app/src/Controller/DefaultController.php0x7f82a7e026ec
*/
private function sanitizeCacheKey(string $key) : string
{
return \str_replace(['\\', "\x00", '@', '/', '$', '{', '}', ':'], '-', $key);
}
}

View File

@@ -1,38 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
/**
* Represents the metadata for the entire class hierarchy.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
class ClassHierarchyMetadata
{
/**
* @var ClassMetadata[]
*/
public $classMetadata = [];
public function addClassMetadata(ClassMetadata $metadata) : void
{
$this->classMetadata[$metadata->name] = $metadata;
}
public function getRootClassMetadata() : ?ClassMetadata
{
return \reset($this->classMetadata);
}
public function getOutsideClassMetadata() : ?ClassMetadata
{
return \end($this->classMetadata);
}
public function isFresh(int $timestamp) : bool
{
foreach ($this->classMetadata as $metadata) {
if (!$metadata->isFresh($timestamp)) {
return \false;
}
}
return \true;
}
}

View File

@@ -1,73 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
/**
* Base class for class metadata.
*
* This class is intended to be extended to add your own application specific
* properties, and flags.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
class ClassMetadata implements \Serializable
{
use SerializationHelper;
/**
* @var string
*/
public $name;
/**
* @var MethodMetadata[]
*/
public $methodMetadata = [];
/**
* @var PropertyMetadata[]
*/
public $propertyMetadata = [];
/**
* @var string[]
*/
public $fileResources = [];
/**
* @var int
*/
public $createdAt;
public function __construct(string $name)
{
$this->name = $name;
$this->createdAt = \time();
}
public function addMethodMetadata(MethodMetadata $metadata) : void
{
$this->methodMetadata[$metadata->name] = $metadata;
}
public function addPropertyMetadata(PropertyMetadata $metadata) : void
{
$this->propertyMetadata[$metadata->name] = $metadata;
}
public function isFresh(?int $timestamp = null) : bool
{
if (null === $timestamp) {
$timestamp = $this->createdAt;
}
foreach ($this->fileResources as $filepath) {
if (!\file_exists($filepath)) {
return \false;
}
if ($timestamp < \filemtime($filepath)) {
return \false;
}
}
return \true;
}
protected function serializeToArray() : array
{
return [$this->name, $this->methodMetadata, $this->propertyMetadata, $this->fileResources, $this->createdAt];
}
protected function unserializeFromArray(array $data) : void
{
[$this->name, $this->methodMetadata, $this->propertyMetadata, $this->fileResources, $this->createdAt] = $data;
}
}

View File

@@ -1,47 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
use PleskRestApi\Metadata\ClassMetadata;
/**
* Base file driver implementation.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
abstract class AbstractFileDriver implements AdvancedDriverInterface
{
/**
* @var FileLocatorInterface|FileLocator
*/
private $locator;
public function __construct(FileLocatorInterface $locator)
{
$this->locator = $locator;
}
public function loadMetadataForClass(\ReflectionClass $class) : ?ClassMetadata
{
if (null === ($path = $this->locator->findFileForClass($class, $this->getExtension()))) {
return null;
}
return $this->loadMetadataFromFile($class, $path);
}
/**
* {@inheritDoc}
*/
public function getAllClassNames() : array
{
if (!$this->locator instanceof AdvancedFileLocatorInterface) {
throw new \RuntimeException(\sprintf('Locator "%s" must be an instance of "AdvancedFileLocatorInterface".', \get_class($this->locator)));
}
return $this->locator->findAllClasses($this->getExtension());
}
/**
* Parses the content of the file, and converts it to the desired metadata.
*/
protected abstract function loadMetadataFromFile(\ReflectionClass $class, string $file) : ?ClassMetadata;
/**
* Returns the extension of the file.
*/
protected abstract function getExtension() : string;
}

View File

@@ -1,19 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
/**
* Forces advanced logic to drivers.
*
* @author Jordan Stout <j@jrdn.org>
*/
interface AdvancedDriverInterface extends DriverInterface
{
/**
* Gets all the metadata class names known to this driver.
*
* @return string[]
*/
public function getAllClassNames() : array;
}

View File

@@ -1,19 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
/**
* Forces advanced logic on a file locator.
*
* @author Jordan Stout <j@jrdn.org>
*/
interface AdvancedFileLocatorInterface extends FileLocatorInterface
{
/**
* Finds all possible metadata files.*
*
* @return string[]
*/
public function findAllClasses(string $extension) : array;
}

View File

@@ -1,50 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
use PleskRestApi\Metadata\ClassMetadata;
final class DriverChain implements AdvancedDriverInterface
{
/**
* @var DriverInterface[]
*/
private $drivers;
/**
* @param DriverInterface[] $drivers
*/
public function __construct(array $drivers = [])
{
$this->drivers = $drivers;
}
public function addDriver(DriverInterface $driver) : void
{
$this->drivers[] = $driver;
}
public function loadMetadataForClass(\ReflectionClass $class) : ?ClassMetadata
{
foreach ($this->drivers as $driver) {
if (null !== ($metadata = $driver->loadMetadataForClass($class))) {
return $metadata;
}
}
return null;
}
/**
* {@inheritDoc}
*/
public function getAllClassNames() : array
{
$classes = [];
foreach ($this->drivers as $driver) {
if (!$driver instanceof AdvancedDriverInterface) {
throw new \RuntimeException(\sprintf('Driver "%s" must be an instance of "AdvancedDriverInterface" to use ' . '"DriverChain::getAllClassNames()".', \get_class($driver)));
}
$driverClasses = $driver->getAllClassNames();
if (!empty($driverClasses)) {
$classes = \array_merge($classes, $driverClasses);
}
}
return $classes;
}
}

View File

@@ -1,10 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
use PleskRestApi\Metadata\ClassMetadata;
interface DriverInterface
{
public function loadMetadataForClass(\ReflectionClass $class) : ?ClassMetadata;
}

View File

@@ -1,67 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
class FileLocator implements AdvancedFileLocatorInterface, TraceableFileLocatorInterface
{
/**
* @var string[]
*/
private $dirs;
/**
* @param string[] $dirs
*/
public function __construct(array $dirs)
{
$this->dirs = $dirs;
}
/**
* @return array<string, bool>
*/
public function getPossibleFilesForClass(\ReflectionClass $class, string $extension) : array
{
$possibleFiles = [];
foreach ($this->dirs as $prefix => $dir) {
if ('' !== $prefix && 0 !== \strpos($class->getNamespaceName(), $prefix)) {
continue;
}
$len = '' === $prefix ? 0 : \strlen($prefix) + 1;
$path = $dir . '/' . \str_replace('\\', '.', \substr($class->name, $len)) . '.' . $extension;
$existsPath = \file_exists($path);
$possibleFiles[$path] = $existsPath;
if ($existsPath) {
return $possibleFiles;
}
}
return $possibleFiles;
}
public function findFileForClass(\ReflectionClass $class, string $extension) : ?string
{
foreach ($this->getPossibleFilesForClass($class, $extension) as $path => $existsPath) {
if ($existsPath) {
return $path;
}
}
return null;
}
/**
* {@inheritDoc}
*/
public function findAllClasses(string $extension) : array
{
$classes = [];
foreach ($this->dirs as $prefix => $dir) {
/** @var \RecursiveIteratorIterator|\SplFileInfo[] $iterator */
$iterator = new \RecursiveIteratorIterator(new \RecursiveDirectoryIterator($dir), \RecursiveIteratorIterator::LEAVES_ONLY);
$nsPrefix = '' !== $prefix ? $prefix . '\\' : '';
foreach ($iterator as $file) {
if (($fileName = $file->getBasename('.' . $extension)) === $file->getBasename()) {
continue;
}
$classes[] = $nsPrefix . \str_replace('.', '\\', $fileName);
}
}
return $classes;
}
}

View File

@@ -1,9 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
interface FileLocatorInterface
{
public function findFileForClass(\ReflectionClass $class, string $extension) : ?string;
}

View File

@@ -1,34 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
use PleskRestApi\Metadata\ClassMetadata;
use Psr\Container\ContainerInterface as PsrContainerInterface;
use PleskRestApi\Symfony\Component\DependencyInjection\ContainerInterface;
class LazyLoadingDriver implements DriverInterface
{
/**
* @var ContainerInterface|PsrContainerInterface
*/
private $container;
/**
* @var string
*/
private $realDriverId;
/**
* @param ContainerInterface|PsrContainerInterface $container
*/
public function __construct($container, string $realDriverId)
{
if (!$container instanceof PsrContainerInterface && !$container instanceof ContainerInterface) {
throw new \InvalidArgumentException(\sprintf('The container must be an instance of %s or %s (%s given).', PsrContainerInterface::class, ContainerInterface::class, \is_object($container) ? \get_class($container) : \gettype($container)));
}
$this->container = $container;
$this->realDriverId = $realDriverId;
}
public function loadMetadataForClass(\ReflectionClass $class) : ?ClassMetadata
{
return $this->container->get($this->realDriverId)->loadMetadataForClass($class);
}
}

View File

@@ -1,14 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata\Driver;
interface TraceableFileLocatorInterface extends FileLocatorInterface
{
/**
* Finds all possible metadata files for a class
*
* @return string[]
*/
public function getPossibleFilesForClass(\ReflectionClass $class, string $extension) : array;
}

View File

@@ -1,21 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
class MergeableClassMetadata extends ClassMetadata implements MergeableInterface
{
public function merge(MergeableInterface $object) : void
{
if (!$object instanceof MergeableClassMetadata) {
throw new \InvalidArgumentException('$object must be an instance of MergeableClassMetadata.');
}
$this->name = $object->name;
$this->methodMetadata = \array_merge($this->methodMetadata, $object->methodMetadata);
$this->propertyMetadata = \array_merge($this->propertyMetadata, $object->propertyMetadata);
$this->fileResources = \array_merge($this->fileResources, $object->fileResources);
if ($object->createdAt < $this->createdAt) {
$this->createdAt = $object->createdAt;
}
}
}

View File

@@ -1,9 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
interface MergeableInterface
{
public function merge(MergeableInterface $object) : void;
}

View File

@@ -1,173 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
use PleskRestApi\Metadata\Cache\CacheInterface;
use PleskRestApi\Metadata\Driver\AdvancedDriverInterface;
use PleskRestApi\Metadata\Driver\DriverInterface;
class MetadataFactory implements AdvancedMetadataFactoryInterface
{
/**
* @var DriverInterface
*/
private $driver;
/**
* @var CacheInterface
*/
private $cache;
/**
* @var ClassMetadata[]
*/
private $loadedMetadata = [];
/**
* @var ClassMetadata[]
*/
private $loadedClassMetadata = [];
/**
* @var string|null
*/
private $hierarchyMetadataClass;
/**
* @var bool
*/
private $includeInterfaces = \false;
/**
* @var bool
*/
private $debug = \false;
public function __construct(DriverInterface $driver, ?string $hierarchyMetadataClass = 'PleskRestApi\\Metadata\\ClassHierarchyMetadata', bool $debug = \false)
{
$this->driver = $driver;
$this->hierarchyMetadataClass = $hierarchyMetadataClass;
$this->debug = $debug;
}
public function setIncludeInterfaces(bool $include) : void
{
$this->includeInterfaces = $include;
}
public function setCache(CacheInterface $cache) : void
{
$this->cache = $cache;
}
/**
* {@inheritDoc}
*/
public function getMetadataForClass(string $className)
{
if (isset($this->loadedMetadata[$className])) {
return $this->filterNullMetadata($this->loadedMetadata[$className]);
}
$metadata = null;
foreach ($this->getClassHierarchy($className) as $class) {
if (isset($this->loadedClassMetadata[$name = $class->getName()])) {
if (null !== ($classMetadata = $this->filterNullMetadata($this->loadedClassMetadata[$name]))) {
$this->addClassMetadata($metadata, $classMetadata);
}
continue;
}
// check the cache
if (null !== $this->cache) {
if (($classMetadata = $this->cache->load($class->getName())) instanceof NullMetadata) {
$this->loadedClassMetadata[$name] = $classMetadata;
continue;
}
if (null !== $classMetadata) {
if (!$classMetadata instanceof ClassMetadata) {
throw new \LogicException(\sprintf('The cache must return instances of ClassMetadata for class %s, but got %s.', $className, \var_export($classMetadata, \true)));
}
if ($this->debug && !$classMetadata->isFresh()) {
$this->cache->evict($classMetadata->name);
} else {
$this->loadedClassMetadata[$name] = $classMetadata;
$this->addClassMetadata($metadata, $classMetadata);
continue;
}
}
}
// load from source
if (null !== ($classMetadata = $this->driver->loadMetadataForClass($class))) {
$this->loadedClassMetadata[$name] = $classMetadata;
$this->addClassMetadata($metadata, $classMetadata);
if (null !== $this->cache) {
$this->cache->put($classMetadata);
}
continue;
}
if (null !== $this->cache && !$this->debug) {
$this->cache->put(new NullMetadata($class->getName()));
}
}
if (null === $metadata) {
$metadata = new NullMetadata($className);
}
return $this->filterNullMetadata($this->loadedMetadata[$className] = $metadata);
}
/**
* {@inheritDoc}
*/
public function getAllClassNames() : array
{
if (!$this->driver instanceof AdvancedDriverInterface) {
throw new \RuntimeException(\sprintf('Driver "%s" must be an instance of "AdvancedDriverInterface".', \get_class($this->driver)));
}
return $this->driver->getAllClassNames();
}
/**
* @param MergeableInterface|ClassHierarchyMetadata $metadata
*/
private function addClassMetadata(&$metadata, ClassMetadata $toAdd) : void
{
if ($toAdd instanceof MergeableInterface) {
if (null === $metadata) {
$metadata = clone $toAdd;
} else {
$metadata->merge($toAdd);
}
} else {
if (null === $metadata) {
$class = $this->hierarchyMetadataClass;
$metadata = new $class();
}
$metadata->addClassMetadata($toAdd);
}
}
/**
* @return \ReflectionClass[]
*/
private function getClassHierarchy(string $class) : array
{
$classes = [];
$refl = new \ReflectionClass($class);
do {
$classes[] = $refl;
$refl = $refl->getParentClass();
} while (\false !== $refl);
$classes = \array_reverse($classes, \false);
if (!$this->includeInterfaces) {
return $classes;
}
$addedInterfaces = [];
$newHierarchy = [];
foreach ($classes as $class) {
foreach ($class->getInterfaces() as $interface) {
if (isset($addedInterfaces[$interface->getName()])) {
continue;
}
$addedInterfaces[$interface->getName()] = \true;
$newHierarchy[] = $interface;
}
$newHierarchy[] = $class;
}
return $newHierarchy;
}
/**
* @param ClassMetadata|ClassHierarchyMetadata|MergeableInterface $metadata
*
* @return ClassMetadata|ClassHierarchyMetadata|MergeableInterface
*/
private function filterNullMetadata($metadata = null)
{
return !$metadata instanceof NullMetadata ? $metadata : null;
}
}

View File

@@ -1,28 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
/**
* Interface for Metadata Factory implementations.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
interface MetadataFactoryInterface
{
/**
* Returns the gathered metadata for the given class name.
*
* If the drivers return instances of MergeableClassMetadata, these will be
* merged prior to returning. Otherwise, all metadata for the inheritance
* hierarchy will be returned as ClassHierarchyMetadata unmerged.
*
* If no metadata is available, null is returned.
*
* @return ClassHierarchyMetadata|MergeableClassMetadata|null
*
* @phpcsSuppress SlevomatCodingStandard.TypeHints.ReturnTypeHint.MissingNativeTypeHint
* @phpcsSuppress SlevomatCodingStandard.TypeHints.TypeHintDeclaration.UselessReturnAnnotation
*/
public function getMetadataForClass(string $className);
}

View File

@@ -1,77 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
/**
* Base class for method metadata.
*
* This class is intended to be extended to add your application specific
* properties, and flags.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
* @property $reflection
*/
class MethodMetadata implements \Serializable
{
use SerializationHelper;
/**
* @var string
*/
public $class;
/**
* @var string
*/
public $name;
/**
* @var \ReflectionMethod
*/
private $reflection;
public function __construct(string $class, string $name)
{
$this->class = $class;
$this->name = $name;
}
/**
* @param mixed[] $args
*
* @return mixed
*/
public function invoke(object $obj, array $args = [])
{
return $this->getReflection()->invokeArgs($obj, $args);
}
/**
* @return mixed
*/
public function __get(string $propertyName)
{
if ('reflection' === $propertyName) {
return $this->getReflection();
}
return $this->{$propertyName};
}
/**
* @param mixed $value
*/
public function __set(string $propertyName, $value) : void
{
$this->{$propertyName} = $value;
}
private function getReflection() : \ReflectionMethod
{
if (null === $this->reflection) {
$this->reflection = new \ReflectionMethod($this->class, $this->name);
$this->reflection->setAccessible(\true);
}
return $this->reflection;
}
protected function serializeToArray() : array
{
return [$this->class, $this->name];
}
protected function unserializeFromArray(array $data) : void
{
[$this->class, $this->name] = $data;
}
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
/**
* Represents the metadata for a class that has not metadata.
*
* @author Adrien Brault <adrien.brault@gmail.com>
*/
class NullMetadata extends ClassMetadata
{
}

View File

@@ -1,38 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
/**
* Base class for property metadata.
*
* This class is intended to be extended to add your application specific
* properties, and flags.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
class PropertyMetadata implements \Serializable
{
use SerializationHelper;
/**
* @var string
*/
public $class;
/**
* @var string
*/
public $name;
public function __construct(string $class, string $name)
{
$this->class = $class;
$this->name = $name;
}
protected function serializeToArray() : array
{
return [$this->class, $this->name];
}
protected function unserializeFromArray(array $data) : void
{
[$this->class, $this->name] = $data;
}
}

View File

@@ -1,36 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\Metadata;
trait SerializationHelper
{
/**
* @deprecated Use serializeToArray
*
* @return string
*/
public function serialize()
{
return \serialize($this->serializeToArray());
}
/**
* @deprecated Use unserializeFromArray
*
* @param string $str
*
* @return void
*/
public function unserialize($str)
{
$this->unserializeFromArray(\unserialize($str));
}
public function __serialize() : array
{
return [$this->serialize()];
}
public function __unserialize(array $data) : void
{
$this->unserialize($data[0]);
}
}

View File

@@ -1,15 +0,0 @@
{
"runner.bootstrap": "tests/bootstrap.php",
"runner.iterations": 3,
"runner.revs": 1,
"report.generators": {
"memory": {
"extends": "aggregate",
"cols": [
"benchmark",
"mem_peak"
]
}
}
}

View File

@@ -1,7 +0,0 @@
<?php
declare (strict_types=1);
namespace {
use PleskRestApi\Rector\Config\RectorConfig;
return RectorConfig::configure()->withPaths([__DIR__ . '/src'])->withPhp74Sets();
}

View File

@@ -1,103 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer;
use PleskRestApi\JMS\Serializer\Exception\NonFloatCastableTypeException;
use PleskRestApi\JMS\Serializer\Exception\NonIntCastableTypeException;
use PleskRestApi\JMS\Serializer\Exception\NonStringCastableTypeException;
use PleskRestApi\JMS\Serializer\Type\Type;
/**
* @internal
*
* @phpstan-import-type TypeArray from Type
*/
abstract class AbstractVisitor implements VisitorInterface
{
/**
* @var GraphNavigatorInterface|null
*/
protected $navigator;
public function setNavigator(GraphNavigatorInterface $navigator) : void
{
$this->navigator = $navigator;
}
/**
* {@inheritdoc}
*/
public function prepare($data)
{
return $data;
}
/**
* @param TypeArray $typeArray
*/
protected function getElementType(array $typeArray) : ?array
{
if (\false === isset($typeArray['params'][0])) {
return null;
}
if (isset($typeArray['params'][1]) && \is_array($typeArray['params'][1])) {
return $typeArray['params'][1];
} else {
return $typeArray['params'][0];
}
}
/**
* logic according to strval https://www.php.net/manual/en/function.strval.php
* "You cannot use strval() on arrays or on objects that do not implement the __toString() method."
*
* @param mixed $value
*/
protected function assertValueCanBeCastToString($value) : void
{
if (\is_array($value)) {
throw new NonStringCastableTypeException($value);
}
if (\is_object($value) && !\method_exists($value, '__toString')) {
throw new NonStringCastableTypeException($value);
}
}
/**
* logic according to intval https://www.php.net/manual/en/function.intval.php
* "intval() should not be used on objects, as doing so will emit an E_NOTICE level error and return 1."
*
* @param mixed $value
*/
protected function assertValueCanBeCastToInt($value) : void
{
if (\is_object($value) && !$value instanceof \SimpleXMLElement) {
throw new NonIntCastableTypeException($value);
}
}
/**
* logic according to floatval https://www.php.net/manual/en/function.floatval.php
* "floatval() should not be used on objects, as doing so will emit an E_NOTICE level error and return 1."
*
* @param mixed $value
*/
protected function assertValueCanCastToFloat($value) : void
{
if (\is_object($value) && !$value instanceof \SimpleXMLElement) {
throw new NonFloatCastableTypeException($value);
}
}
protected function mapRoundMode(?string $roundMode = null) : int
{
switch ($roundMode) {
case 'HALF_DOWN':
$roundMode = \PHP_ROUND_HALF_DOWN;
break;
case 'HALF_EVEN':
$roundMode = \PHP_ROUND_HALF_EVEN;
break;
case 'HALF_ODD':
$roundMode = \PHP_ROUND_HALF_ODD;
break;
case 'HALF_UP':
default:
$roundMode = \PHP_ROUND_HALF_UP;
}
return $roundMode;
}
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Accessor;
use PleskRestApi\JMS\Serializer\DeserializationContext;
use PleskRestApi\JMS\Serializer\Metadata\PropertyMetadata;
use PleskRestApi\JMS\Serializer\SerializationContext;
/**
* @author Asmir Mustafic <goetas@gmail.com>
*/
interface AccessorStrategyInterface
{
/**
* @return mixed
*/
public function getValue(object $object, PropertyMetadata $metadata, SerializationContext $context);
/**
* @param mixed $value
*/
public function setValue(object $object, $value, PropertyMetadata $metadata, DeserializationContext $context) : void;
}

View File

@@ -1,118 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Accessor;
use PleskRestApi\JMS\Serializer\DeserializationContext;
use PleskRestApi\JMS\Serializer\Exception\ExpressionLanguageRequiredException;
use PleskRestApi\JMS\Serializer\Exception\LogicException;
use PleskRestApi\JMS\Serializer\Exception\UninitializedPropertyException;
use PleskRestApi\JMS\Serializer\Expression\CompilableExpressionEvaluatorInterface;
use PleskRestApi\JMS\Serializer\Expression\Expression;
use PleskRestApi\JMS\Serializer\Expression\ExpressionEvaluatorInterface;
use PleskRestApi\JMS\Serializer\Metadata\ExpressionPropertyMetadata;
use PleskRestApi\JMS\Serializer\Metadata\PropertyMetadata;
use PleskRestApi\JMS\Serializer\Metadata\StaticPropertyMetadata;
use PleskRestApi\JMS\Serializer\SerializationContext;
/**
* @author Asmir Mustafic <goetas@gmail.com>
*/
final class DefaultAccessorStrategy implements AccessorStrategyInterface
{
/**
* @var callable[]
*/
private $readAccessors = [];
/**
* @var callable[]
*/
private $writeAccessors = [];
/**
* @var \ReflectionProperty[]
*/
private $propertyReflectionCache = [];
/**
* @var ExpressionEvaluatorInterface
*/
private $evaluator;
public function __construct(?ExpressionEvaluatorInterface $evaluator = null)
{
$this->evaluator = $evaluator;
}
/**
* {@inheritdoc}
*/
public function getValue(object $object, PropertyMetadata $metadata, SerializationContext $context)
{
if ($metadata instanceof StaticPropertyMetadata) {
return $metadata->getValue();
}
if ($metadata instanceof ExpressionPropertyMetadata) {
if (null === $this->evaluator) {
throw new ExpressionLanguageRequiredException(\sprintf('The property %s on %s requires the expression accessor strategy to be enabled.', $metadata->name, $metadata->class));
}
$variables = ['object' => $object, 'context' => $context, 'property_metadata' => $metadata];
if ($metadata->expression instanceof Expression && $this->evaluator instanceof CompilableExpressionEvaluatorInterface) {
return $this->evaluator->evaluateParsed($metadata->expression, $variables);
}
return $this->evaluator->evaluate($metadata->expression, $variables);
}
if (null !== $metadata->getter) {
return $object->{$metadata->getter}();
}
if ($metadata->forceReflectionAccess) {
$ref = $this->propertyReflectionCache[$metadata->class][$metadata->name] ?? null;
if (null === $ref) {
$ref = new \ReflectionProperty($metadata->class, $metadata->name);
$ref->setAccessible(\true);
$this->propertyReflectionCache[$metadata->class][$metadata->name] = $ref;
}
return $ref->getValue($object);
}
$accessor = $this->readAccessors[$metadata->class] ?? null;
if (null === $accessor) {
$accessor = \Closure::bind(static fn($o, $name) => $o->{$name}, null, $metadata->class);
$this->readAccessors[$metadata->class] = $accessor;
}
try {
return $accessor($object, $metadata->name);
} catch (\Error $e) {
// handle uninitialized properties in PHP >= 7.4
if (\preg_match('/^Typed property ([\\w\\\\@]+)::\\$(\\w+) must not be accessed before initialization$/', $e->getMessage(), $matches)) {
throw new UninitializedPropertyException(\sprintf('Uninitialized property "%s::$%s".', $metadata->class, $metadata->name), 0, $e);
}
throw $e;
}
}
/**
* {@inheritdoc}
*/
public function setValue(object $object, $value, PropertyMetadata $metadata, DeserializationContext $context) : void
{
if (\true === $metadata->readOnly) {
throw new LogicException(\sprintf('%s on %s is read only.', $metadata->name, $metadata->class));
}
if (null !== $metadata->setter) {
$object->{$metadata->setter}($value);
return;
}
if ($metadata->forceReflectionAccess) {
$ref = $this->propertyReflectionCache[$metadata->class][$metadata->name] ?? null;
if (null === $ref) {
$ref = new \ReflectionProperty($metadata->class, $metadata->name);
$ref->setAccessible(\true);
$this->propertyReflectionCache[$metadata->class][$metadata->name] = $ref;
}
$ref->setValue($object, $value);
return;
}
$accessor = $this->writeAccessors[$metadata->class] ?? null;
if (null === $accessor) {
$accessor = \Closure::bind(static function ($o, $name, $value) : void {
$o->{$name} = $value;
}, null, $metadata->class);
$this->writeAccessors[$metadata->class] = $accessor;
}
$accessor($object, $metadata->name, $value);
}
}

View File

@@ -1,25 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"CLASS", "PROPERTY"})
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
#[\Attribute(\Attribute::TARGET_CLASS | \Attribute::TARGET_PROPERTY)]
final class AccessType implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @Required
* @var string|null
*/
public $type;
public function __construct(array $values = [], ?string $type = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,28 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target("PROPERTY")
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
#[\Attribute(\Attribute::TARGET_PROPERTY)]
final class Accessor implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var string|null
*/
public $getter = null;
/**
* @var string|null
*/
public $setter = null;
public function __construct(array $values = [], ?string $getter = null, ?string $setter = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,31 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* Controls the order of properties in a class.
*
* @Annotation
* @Target("CLASS")
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
#[\Attribute(\Attribute::TARGET_CLASS)]
final class AccessorOrder implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @Required
* @var string|null
*/
public $order = null;
/**
* @var array<string>
*/
public $custom = [];
public function __construct(array $values = [], ?string $order = null, array $custom = [])
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,33 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
use PleskRestApi\JMS\Serializer\Exception\InvalidArgumentException;
trait AnnotationUtilsTrait
{
private function loadAnnotationParameters(array $vars) : void
{
if (!\array_key_exists('values', $vars)) {
$values = [];
} elseif (!\is_array($vars['values'])) {
$values = ['value' => $vars['values']];
} else {
$values = $vars['values'];
}
unset($vars['values']);
if (\array_key_exists('value', $values)) {
$values[\key($vars)] = $values['value'];
unset($values['value']);
}
foreach ($values as $key => $value) {
$vars[$key] = $value;
}
foreach ($vars as $key => $value) {
if (!\property_exists(static::class, $key)) {
throw new InvalidArgumentException(\sprintf('Unknown property "%s" on annotation "%s".', $key, static::class));
}
$this->{$key} = $value;
}
}
}

View File

@@ -1,15 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"CLASS","PROPERTY"})
*
* @deprecated use `@ReadOnlyProperty` instead
*/
#[\Attribute(\Attribute::TARGET_CLASS | \Attribute::TARGET_PROPERTY)]
final class DeprecatedReadOnly extends ReadOnlyProperty
{
}

View File

@@ -1,26 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target("CLASS")
*/
#[\Attribute(\Attribute::TARGET_CLASS)]
class Discriminator implements SerializerAttribute
{
use AnnotationUtilsTrait;
/** @var array<string> */
public $map = [];
/** @var string */
public $field = 'type';
/** @var bool */
public $disabled = \false;
/** @var string[] */
public $groups = [];
public function __construct(array $values = [], string $field = 'type', array $groups = [], array $map = [], bool $disabled = \false)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "CLASS", "METHOD", "ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_CLASS | \Attribute::TARGET_PROPERTY | \Attribute::TARGET_METHOD)]
final class Exclude implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var string|null
*/
public $if;
public function __construct(array $values = [], ?string $if = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,29 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
use PleskRestApi\JMS\Serializer\Exception\RuntimeException;
/**
* @Annotation
* @Target("CLASS")
*/
#[\Attribute(\Attribute::TARGET_CLASS)]
final class ExclusionPolicy implements SerializerAttribute
{
use AnnotationUtilsTrait;
public const NONE = 'NONE';
public const ALL = 'ALL';
/**
* @var string|null
*/
public $policy = 'NONE';
public function __construct($values = [], ?string $policy = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
$this->policy = \strtoupper($this->policy);
if (self::NONE !== $this->policy && self::ALL !== $this->policy) {
throw new RuntimeException('Exclusion policy must either be "ALL", or "NONE".');
}
}
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "METHOD", "ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class Expose implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var string|null
*/
public $if = null;
public function __construct(array $values = [], ?string $if = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,31 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class Groups implements SerializerAttribute
{
use AnnotationUtilsTrait;
/** @var array<string> @Required */
public $groups = [];
public function __construct(array $values = [], array $groups = [])
{
$vars = \get_defined_vars();
/*
if someone wants to set as Groups(['value' => '...']) this check will miserably fail (only one group with 'value' as only key).
That is because doctrine annotations uses for @Groups("abc") the same values content (buy validation will fail since groups has to be an array).
All the other cases should work as expected.
The alternative here is to use the explicit syntax Groups(groups=['value' => '...'])
*/
if (\count($values) > 0 && (!isset($values['value']) && !isset($values['groups']) || \count($values) > 1) && 0 === \count($groups)) {
$vars['groups'] = $values;
$vars['values'] = [];
}
$this->loadAnnotationParameters($vars);
}
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class Inline implements SerializerAttribute
{
}

View File

@@ -1,23 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class MaxDepth implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @Required
* @var int
*/
public $depth;
public function __construct($values = [], int $depth = 0)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,20 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* This annotation can be defined on methods which are called after the
* deserialization of the object is complete.
*
* These methods do not necessarily have to be public.
*
* @Annotation
* @Target("METHOD")
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
#[\Attribute(\Attribute::TARGET_METHOD)]
final class PostDeserialize implements SerializerAttribute
{
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target("METHOD")
*/
#[\Attribute(\Attribute::TARGET_METHOD)]
final class PostSerialize implements SerializerAttribute
{
}

View File

@@ -1,21 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* This annotation can be declared on methods which should be called
* before the Serialization process.
*
* These methods do not need to be public, and should do any clean-up, or
* preparation of the object that is necessary.
*
* @Annotation
* @Target("METHOD")
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
#[\Attribute(\Attribute::TARGET_METHOD)]
final class PreSerialize implements SerializerAttribute
{
}

View File

@@ -1,7 +0,0 @@
<?php
declare (strict_types=1);
namespace {
use PleskRestApi\JMS\Serializer\Annotation\DeprecatedReadOnly;
\class_alias(DeprecatedReadOnly::class, 'PleskRestApi\\JMS\\Serializer\\Annotation\\ReadOnly');
}

View File

@@ -1,24 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"CLASS","PROPERTY"})
*
* @final
*/
#[\Attribute(\Attribute::TARGET_CLASS | \Attribute::TARGET_PROPERTY)]
class ReadOnlyProperty implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var bool
*/
public $readOnly = \true;
public function __construct(array $values = [], bool $readOnly = \true)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD", "ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class SerializedName implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var string|null
*/
public $name = null;
public function __construct($values = [], ?string $name = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,11 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* Marker interface for serializer attributes
*/
interface SerializerAttribute
{
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "METHOD", "ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class Since extends Version
{
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class SkipWhenEmpty implements SerializerAttribute
{
}

View File

@@ -1,35 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class Type implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @Required
* @var string|\Stringable|null
*/
public $name = null;
public function __construct($values = [], $name = null)
{
if (null !== $name && !\is_string($name) && !(\is_object($name) && \method_exists($name, '__toString'))) {
throw new \RuntimeException('Type must be either string, null or object implements __toString() method.');
}
if (\is_object($name)) {
$name = (string) $name;
}
if (\is_object($values)) {
if (\false === \method_exists($values, '__toString')) {
throw new \RuntimeException('Type must be either string or object implements __toString() method.');
}
$values = (string) $values;
}
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY"})
*/
#[\Attribute(\Attribute::TARGET_PROPERTY)]
final class UnionDiscriminator implements SerializerAttribute
{
use AnnotationUtilsTrait;
/** @var array<string> */
public $map = [];
/** @var string */
public $field = 'type';
public function __construct(array $values = [], string $field = 'type', array $map = [])
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "METHOD", "ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class Until extends Version
{
}

View File

@@ -1,18 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
abstract class Version implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @Required
* @var string|null
*/
public $version = null;
public function __construct($values = [], ?string $version = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,44 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"METHOD", "CLASS"})
*
* @author Alexander Klimenkov <alx.devel@gmail.com>
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_CLASS | \Attribute::IS_REPEATABLE)]
final class VirtualProperty implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var string|null
*/
public $exp = null;
/**
* @var string|null
*/
public $name = null;
/**
* @var array
*/
public $options = [];
public function __construct($values = [], ?string $name = null, ?string $exp = null, array $options = [])
{
$vars = \get_defined_vars();
unset($vars['options']);
$this->loadAnnotationParameters($vars);
if (0 !== \count($options)) {
$this->options = $options;
}
foreach ($options as $option) {
if (\is_array($option) && \class_exists($option[0])) {
$this->options[] = new $option[0]([], ...$option[1]);
continue;
}
$this->options[] = $option;
}
}
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class XmlAttribute implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var string|null
*/
public $namespace = null;
public function __construct($values = [], ?string $namespace = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "METHOD"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class XmlAttributeMap implements SerializerAttribute
{
}

View File

@@ -1,29 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
abstract class XmlCollection implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var string
*/
public $entry = 'entry';
/**
* @var bool
*/
public $inline = \false;
/**
* @var string|null
*/
public $namespace = null;
/**
* @var bool
*/
public $skipWhenEmpty = \true;
public function __construct(array $values = [], string $entry = 'entry', bool $inline = \false, ?string $namespace = null, bool $skipWhenEmpty = \true)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,30 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target("CLASS")
*/
#[\Attribute(\Attribute::TARGET_CLASS)]
class XmlDiscriminator implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var bool
*/
public $attribute = \false;
/**
* @var bool
*/
public $cdata = \true;
/**
* @var string|null
*/
public $namespace = null;
public function __construct(array $values = [], bool $attribute = \false, bool $cdata = \false, ?string $namespace = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,26 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY", "METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class XmlElement implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var bool
*/
public $cdata = \true;
/**
* @var string|null
*/
public $namespace = null;
public function __construct(array $values = [], bool $cdata = \true, ?string $namespace = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class XmlKeyValuePairs implements SerializerAttribute
{
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class XmlList extends XmlCollection
{
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class XmlMap extends XmlCollection
{
use AnnotationUtilsTrait;
/**
* @var string
*/
public $keyAttribute = '_key';
public function __construct(array $values = [], string $keyAttribute = '_key', string $entry = 'entry', bool $inline = \false, ?string $namespace = null, bool $skipWhenEmpty = \true)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,27 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target("CLASS")
*/
#[\Attribute(\Attribute::TARGET_CLASS | \Attribute::IS_REPEATABLE)]
final class XmlNamespace implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @Required
* @var string|null
*/
public $uri = null;
/**
* @var string
*/
public $prefix = '';
public function __construct(array $values = [], ?string $uri = null, string $prefix = '')
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,31 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target("CLASS")
*/
#[\Attribute(\Attribute::TARGET_CLASS)]
final class XmlRoot implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @Required
* @var string|null
*/
public $name = null;
/**
* @var string|null
*/
public $namespace = null;
/**
* @var string|null
*/
public $prefix = null;
public function __construct($values = [], ?string $name = null, ?string $namespace = null, ?string $prefix = null)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,22 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Annotation;
/**
* @Annotation
* @Target({"PROPERTY","METHOD","ANNOTATION"})
*/
#[\Attribute(\Attribute::TARGET_METHOD | \Attribute::TARGET_PROPERTY)]
final class XmlValue implements SerializerAttribute
{
use AnnotationUtilsTrait;
/**
* @var bool
*/
public $cdata = \true;
public function __construct(array $values = [], bool $cdata = \true)
{
$this->loadAnnotationParameters(\get_defined_vars());
}
}

View File

@@ -1,31 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer;
/**
* Interface for array transformation.
*
* @author Daniel Bojdo <daniel@bojdo.eu>
*/
interface ArrayTransformerInterface
{
/**
* Converts objects to an array structure.
*
* This is useful when the data needs to be passed on to other methods which expect array data.
*
* @param mixed $data anything that converts to an array, typically an object or an array of objects
*
* @return array
*/
public function toArray($data, ?SerializationContext $context = null, ?string $type = null) : array;
/**
* Restores objects from an array structure.
*
* @param array $data
*
* @return mixed this returns whatever the passed type is, typically an object or an array of objects
*/
public function fromArray(array $data, string $type, ?DeserializationContext $context = null);
}

View File

@@ -1,31 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Builder;
use PleskRestApi\Doctrine\Common\Annotations\Reader;
use PleskRestApi\JMS\Serializer\Exception\LogicException;
use PleskRestApi\Metadata\Driver\DriverInterface;
final class CallbackDriverFactory implements DriverFactoryInterface
{
/**
* @var callable
* @phpstan-var callable(array $metadataDirs, Reader|null $reader): DriverInterface
*/
private $callback;
/**
* @phpstan-param callable(array $metadataDirs, Reader|null $reader): DriverInterface $callable
*/
public function __construct(callable $callable)
{
$this->callback = $callable;
}
public function createDriver(array $metadataDirs, ?Reader $reader = null) : DriverInterface
{
$driver = \call_user_func($this->callback, $metadataDirs, $reader);
if (!$driver instanceof DriverInterface) {
throw new LogicException('The callback must return an instance of DriverInterface.');
}
return $driver;
}
}

View File

@@ -1,86 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Builder;
use PleskRestApi\Doctrine\Common\Annotations\Reader;
use PleskRestApi\JMS\Serializer\Exception\RuntimeException;
use PleskRestApi\JMS\Serializer\Expression\CompilableExpressionEvaluatorInterface;
use PleskRestApi\JMS\Serializer\Metadata\Driver\AnnotationOrAttributeDriver;
use PleskRestApi\JMS\Serializer\Metadata\Driver\DefaultValuePropertyDriver;
use PleskRestApi\JMS\Serializer\Metadata\Driver\EnumPropertiesDriver;
use PleskRestApi\JMS\Serializer\Metadata\Driver\NullDriver;
use PleskRestApi\JMS\Serializer\Metadata\Driver\TypedPropertiesDriver;
use PleskRestApi\JMS\Serializer\Metadata\Driver\XmlDriver;
use PleskRestApi\JMS\Serializer\Metadata\Driver\YamlDriver;
use PleskRestApi\JMS\Serializer\Naming\PropertyNamingStrategyInterface;
use PleskRestApi\JMS\Serializer\Type\Parser;
use PleskRestApi\JMS\Serializer\Type\ParserInterface;
use PleskRestApi\Metadata\Driver\DriverChain;
use PleskRestApi\Metadata\Driver\DriverInterface;
use PleskRestApi\Metadata\Driver\FileLocator;
use PleskRestApi\Symfony\Component\Yaml\Yaml;
final class DefaultDriverFactory implements DriverFactoryInterface
{
/**
* @var ParserInterface
*/
private $typeParser;
/**
* @var bool
*/
private $enableEnumSupport = \false;
/**
* @var PropertyNamingStrategyInterface
*/
private $propertyNamingStrategy;
/**
* @var CompilableExpressionEvaluatorInterface
*/
private $expressionEvaluator;
public function __construct(PropertyNamingStrategyInterface $propertyNamingStrategy, ?ParserInterface $typeParser = null, ?CompilableExpressionEvaluatorInterface $expressionEvaluator = null)
{
$this->typeParser = $typeParser ?: new Parser();
$this->propertyNamingStrategy = $propertyNamingStrategy;
$this->expressionEvaluator = $expressionEvaluator;
}
public function enableEnumSupport(bool $enableEnumSupport = \true) : void
{
$this->enableEnumSupport = $enableEnumSupport;
}
public function createDriver(array $metadataDirs, ?Reader $annotationReader = null) : DriverInterface
{
if (\PHP_VERSION_ID < 80000 && empty($metadataDirs) && !\interface_exists(Reader::class)) {
throw new RuntimeException(\sprintf('To use "%s", either a list of metadata directories must be provided, the "doctrine/annotations" package installed, or use PHP 8.0 or later.', self::class));
}
/*
* Build the sorted list of metadata drivers based on the environment. The final order should be:
*
* - YAML Driver
* - XML Driver
* - Annotations/Attributes Driver
* - Null (Fallback) Driver
*/
$metadataDrivers = [];
if (\PHP_VERSION_ID >= 80000 || $annotationReader instanceof Reader) {
$metadataDrivers[] = new AnnotationOrAttributeDriver($this->propertyNamingStrategy, $this->typeParser, $this->expressionEvaluator, $annotationReader);
}
if (!empty($metadataDirs)) {
$fileLocator = new FileLocator($metadataDirs);
\array_unshift($metadataDrivers, new XmlDriver($fileLocator, $this->propertyNamingStrategy, $this->typeParser, $this->expressionEvaluator));
if (\class_exists(Yaml::class)) {
\array_unshift($metadataDrivers, new YamlDriver($fileLocator, $this->propertyNamingStrategy, $this->typeParser, $this->expressionEvaluator));
}
}
$driver = new DriverChain($metadataDrivers);
$driver->addDriver(new NullDriver($this->propertyNamingStrategy));
if ($this->enableEnumSupport) {
$driver = new EnumPropertiesDriver($driver);
}
$driver = new TypedPropertiesDriver($driver, $this->typeParser);
if (\PHP_VERSION_ID >= 80000) {
$driver = new DefaultValuePropertyDriver($driver);
}
return $driver;
}
}

View File

@@ -1,30 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Builder;
use PleskRestApi\Doctrine\Common\Annotations\Reader;
use PleskRestApi\JMS\Serializer\Metadata\Driver\DocBlockDriver;
use PleskRestApi\JMS\Serializer\Type\ParserInterface;
use PleskRestApi\Metadata\Driver\DriverInterface;
class DocBlockDriverFactory implements DriverFactoryInterface
{
/**
* @var DriverFactoryInterface
*/
private $driverFactoryToDecorate;
/**
* @var ParserInterface|null
*/
private $typeParser;
public function __construct(DriverFactoryInterface $driverFactoryToDecorate, ?ParserInterface $typeParser = null)
{
$this->driverFactoryToDecorate = $driverFactoryToDecorate;
$this->typeParser = $typeParser;
}
public function createDriver(array $metadataDirs, ?Reader $annotationReader = null) : DriverInterface
{
$driver = $this->driverFactoryToDecorate->createDriver($metadataDirs, $annotationReader);
return new DocBlockDriver($driver, $this->typeParser);
}
}

View File

@@ -1,11 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Builder;
use PleskRestApi\Doctrine\Common\Annotations\Reader;
use PleskRestApi\Metadata\Driver\DriverInterface;
interface DriverFactoryInterface
{
public function createDriver(array $metadataDirs, ?Reader $annotationReader = null) : DriverInterface;
}

View File

@@ -1,128 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Construction;
use PleskRestApi\Doctrine\ODM\PHPCR\DocumentManagerInterface;
use PleskRestApi\Doctrine\ORM\EntityManagerInterface;
use PleskRestApi\Doctrine\Persistence\ManagerRegistry;
use PleskRestApi\JMS\Serializer\DeserializationContext;
use PleskRestApi\JMS\Serializer\Exception\InvalidArgumentException;
use PleskRestApi\JMS\Serializer\Exception\ObjectConstructionException;
use PleskRestApi\JMS\Serializer\Exclusion\ExpressionLanguageExclusionStrategy;
use PleskRestApi\JMS\Serializer\Metadata\ClassMetadata;
use PleskRestApi\JMS\Serializer\Metadata\PropertyMetadata;
use PleskRestApi\JMS\Serializer\Visitor\DeserializationVisitorInterface;
use function is_array;
/**
* Doctrine object constructor for new (or existing) objects during deserialization.
*/
final class DoctrineObjectConstructor implements ObjectConstructorInterface
{
public const ON_MISSING_NULL = 'null';
public const ON_MISSING_EXCEPTION = 'exception';
public const ON_MISSING_FALLBACK = 'fallback';
/**
* @var string
*/
private $fallbackStrategy;
/**
* @var ManagerRegistry
*/
private $managerRegistry;
/**
* @var ObjectConstructorInterface
*/
private $fallbackConstructor;
/**
* @var ExpressionLanguageExclusionStrategy|null
*/
private $expressionLanguageExclusionStrategy;
/**
* @param ManagerRegistry $managerRegistry Manager registry
* @param ObjectConstructorInterface $fallbackConstructor Fallback object constructor
*/
public function __construct(ManagerRegistry $managerRegistry, ObjectConstructorInterface $fallbackConstructor, string $fallbackStrategy = self::ON_MISSING_NULL, ?ExpressionLanguageExclusionStrategy $expressionLanguageExclusionStrategy = null)
{
$this->managerRegistry = $managerRegistry;
$this->fallbackConstructor = $fallbackConstructor;
$this->fallbackStrategy = $fallbackStrategy;
$this->expressionLanguageExclusionStrategy = $expressionLanguageExclusionStrategy;
}
/**
* {@inheritdoc}
*/
public function construct(DeserializationVisitorInterface $visitor, ClassMetadata $metadata, $data, array $type, DeserializationContext $context) : ?object
{
$objectManager = $this->managerRegistry->getManagerForClass($metadata->name);
if (!$objectManager) {
// No ObjectManager found, proceed with normal deserialization
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
}
// Locate possible ClassMetadata
$classMetadataFactory = $objectManager->getMetadataFactory();
if ($classMetadataFactory->isTransient($metadata->name)) {
// No ClassMetadata found, proceed with normal deserialization
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
}
// Managed entity, check for proxy load
if (!is_array($data) && !(\is_object($data) && 'SimpleXMLElement' === \get_class($data))) {
\assert($objectManager instanceof EntityManagerInterface || $objectManager instanceof DocumentManagerInterface);
// Single identifier, load proxy
return $objectManager->getReference($metadata->name, $data);
}
// Fallback to default constructor if missing identifier(s)
$classMetadata = $objectManager->getClassMetadata($metadata->name);
$identifierList = [];
foreach ($classMetadata->getIdentifierFieldNames() as $name) {
// Avoid calling objectManager->find if some identification properties are excluded
if (!isset($metadata->propertyMetadata[$name])) {
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
}
$propertyMetadata = $metadata->propertyMetadata[$name];
// Avoid calling objectManager->find if some identification properties are excluded by some exclusion strategy
if ($this->isIdentifierFieldExcluded($propertyMetadata, $context)) {
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
}
if (is_array($data) && !\array_key_exists($propertyMetadata->serializedName, $data)) {
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
} elseif (\is_object($data) && !\property_exists($data, $propertyMetadata->serializedName)) {
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
}
if (\is_object($data) && 'SimpleXMLElement' === \get_class($data)) {
$identifierList[$name] = (string) $data->{$propertyMetadata->serializedName};
} else {
$identifierList[$name] = $data[$propertyMetadata->serializedName];
}
}
if (empty($identifierList)) {
// $classMetadataFactory->isTransient() fails on embeddable class with file metadata driver
// https://github.com/doctrine/persistence/issues/37
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
}
// Entity update, load it from database
$object = $objectManager->find($metadata->name, $identifierList);
if (null === $object) {
switch ($this->fallbackStrategy) {
case self::ON_MISSING_NULL:
return null;
case self::ON_MISSING_EXCEPTION:
throw new ObjectConstructionException(\sprintf('Entity %s can not be found', $metadata->name));
case self::ON_MISSING_FALLBACK:
return $this->fallbackConstructor->construct($visitor, $metadata, $data, $type, $context);
default:
throw new InvalidArgumentException('The provided fallback strategy for the object constructor is not valid');
}
}
$objectManager->initializeObject($object);
return $object;
}
private function isIdentifierFieldExcluded(PropertyMetadata $propertyMetadata, DeserializationContext $context) : bool
{
$exclusionStrategy = $context->getExclusionStrategy();
if (null !== $exclusionStrategy && $exclusionStrategy->shouldSkipProperty($propertyMetadata, $context)) {
return \true;
}
return null !== $this->expressionLanguageExclusionStrategy && $this->expressionLanguageExclusionStrategy->shouldSkipProperty($propertyMetadata, $context);
}
}

View File

@@ -1,29 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Construction;
use PleskRestApi\JMS\Serializer\DeserializationContext;
use PleskRestApi\JMS\Serializer\Metadata\ClassMetadata;
use PleskRestApi\JMS\Serializer\Type\Type;
use PleskRestApi\JMS\Serializer\Visitor\DeserializationVisitorInterface;
/**
* Implementations of this interface construct new objects during deserialization.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*
* @phpstan-import-type TypeArray from Type
*/
interface ObjectConstructorInterface
{
/**
* Constructs a new object.
*
* Implementations could for example create a new object calling "new", use
* "unserialize" techniques, reflection, or other means.
*
* @param mixed $data
* @param TypeArray $type
*/
public function construct(DeserializationVisitorInterface $visitor, ClassMetadata $metadata, $data, array $type, DeserializationContext $context) : ?object;
}

View File

@@ -1,28 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Construction;
use PleskRestApi\Doctrine\Instantiator\Instantiator;
use PleskRestApi\JMS\Serializer\DeserializationContext;
use PleskRestApi\JMS\Serializer\Metadata\ClassMetadata;
use PleskRestApi\JMS\Serializer\Visitor\DeserializationVisitorInterface;
final class UnserializeObjectConstructor implements ObjectConstructorInterface
{
/** @var Instantiator */
private $instantiator;
/**
* {@inheritdoc}
*/
public function construct(DeserializationVisitorInterface $visitor, ClassMetadata $metadata, $data, array $type, DeserializationContext $context) : ?object
{
return $this->getInstantiator()->instantiate($metadata->name);
}
private function getInstantiator() : Instantiator
{
if (null === $this->instantiator) {
$this->instantiator = new Instantiator();
}
return $this->instantiator;
}
}

View File

@@ -1,211 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer;
use PleskRestApi\JMS\Serializer\Exception\LogicException;
use PleskRestApi\JMS\Serializer\Exception\RuntimeException;
use PleskRestApi\JMS\Serializer\Exclusion\DepthExclusionStrategy;
use PleskRestApi\JMS\Serializer\Exclusion\DisjunctExclusionStrategy;
use PleskRestApi\JMS\Serializer\Exclusion\ExclusionStrategyInterface;
use PleskRestApi\JMS\Serializer\Exclusion\GroupsExclusionStrategy;
use PleskRestApi\JMS\Serializer\Exclusion\VersionExclusionStrategy;
use PleskRestApi\JMS\Serializer\Metadata\ClassMetadata;
use PleskRestApi\JMS\Serializer\Metadata\PropertyMetadata;
use PleskRestApi\Metadata\MetadataFactoryInterface;
abstract class Context
{
/**
* @var array
*/
private $attributes = [];
/**
* @var string
*/
private $format;
/**
* @var VisitorInterface
*/
private $visitor;
/**
* @var GraphNavigatorInterface
*/
private $navigator;
/**
* @var MetadataFactoryInterface
*/
private $metadataFactory;
/** @var ExclusionStrategyInterface */
private $exclusionStrategy;
/**
* @var bool
*/
private $initialized = \false;
/** @var \SplStack */
private $metadataStack;
public function __construct()
{
$this->metadataStack = new \SplStack();
}
public function initialize(string $format, VisitorInterface $visitor, GraphNavigatorInterface $navigator, MetadataFactoryInterface $factory) : void
{
if ($this->initialized) {
throw new LogicException('This context was already initialized, and cannot be re-used.');
}
$this->format = $format;
$this->visitor = $visitor;
$this->navigator = $navigator;
$this->metadataFactory = $factory;
$this->metadataStack = new \SplStack();
if (isset($this->attributes['groups'])) {
$this->addExclusionStrategy(new GroupsExclusionStrategy($this->attributes['groups']));
}
if (isset($this->attributes['version'])) {
$this->addExclusionStrategy(new VersionExclusionStrategy($this->attributes['version']));
}
if (!empty($this->attributes['max_depth_checks'])) {
$this->addExclusionStrategy(new DepthExclusionStrategy());
}
$this->initialized = \true;
}
public function getMetadataFactory() : MetadataFactoryInterface
{
return $this->metadataFactory;
}
public function getVisitor() : VisitorInterface
{
return $this->visitor;
}
public function getNavigator() : GraphNavigatorInterface
{
return $this->navigator;
}
public function getExclusionStrategy() : ?ExclusionStrategyInterface
{
return $this->exclusionStrategy;
}
/**
* @return mixed
*/
public function getAttribute(string $key)
{
return $this->attributes[$key];
}
public function hasAttribute(string $key) : bool
{
return isset($this->attributes[$key]);
}
/**
* @param mixed $value
*
* @return $this
*/
public function setAttribute(string $key, $value) : self
{
$this->assertMutable();
$this->attributes[$key] = $value;
return $this;
}
protected final function assertMutable() : void
{
if (!$this->initialized) {
return;
}
throw new LogicException('This context was already initialized and is immutable; you cannot modify it anymore.');
}
/**
* @return $this
*/
public function addExclusionStrategy(ExclusionStrategyInterface $strategy) : self
{
$this->assertMutable();
if (null === $this->exclusionStrategy) {
$this->exclusionStrategy = $strategy;
return $this;
}
if ($this->exclusionStrategy instanceof DisjunctExclusionStrategy) {
$this->exclusionStrategy->addStrategy($strategy);
return $this;
}
$this->exclusionStrategy = new DisjunctExclusionStrategy([$this->exclusionStrategy, $strategy]);
return $this;
}
/**
* @return $this
*/
public function setVersion(string $version) : self
{
$this->attributes['version'] = $version;
return $this;
}
/**
* @param array|string $groups
*
* @return $this
*/
public function setGroups($groups) : self
{
if (empty($groups)) {
throw new LogicException('The groups must not be empty.');
}
$this->attributes['groups'] = (array) $groups;
return $this;
}
/**
* @return $this
*/
public function enableMaxDepthChecks() : self
{
$this->attributes['max_depth_checks'] = \true;
return $this;
}
public function getFormat() : string
{
return $this->format;
}
public function pushClassMetadata(ClassMetadata $metadata) : void
{
$this->metadataStack->push($metadata);
}
public function pushPropertyMetadata(PropertyMetadata $metadata) : void
{
$this->metadataStack->push($metadata);
}
public function popPropertyMetadata() : void
{
$metadata = $this->metadataStack->pop();
if (!$metadata instanceof PropertyMetadata) {
throw new RuntimeException('Context metadataStack not working well');
}
}
public function popClassMetadata() : void
{
$metadata = $this->metadataStack->pop();
if (!$metadata instanceof ClassMetadata) {
throw new RuntimeException('Context metadataStack not working well');
}
}
public function getMetadataStack() : \SplStack
{
return $this->metadataStack;
}
public function getCurrentPath() : array
{
if (!$this->metadataStack) {
return [];
}
$paths = [];
foreach ($this->metadataStack as $metadata) {
if ($metadata instanceof PropertyMetadata) {
\array_unshift($paths, $metadata->name);
}
}
return $paths;
}
public abstract function getDepth() : int;
public abstract function getDirection() : int;
public function close() : void
{
unset($this->visitor, $this->navigator);
}
}

View File

@@ -1,11 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\ContextFactory;
/**
* @deprecated
*/
abstract class CallableContextFactory
{
}

View File

@@ -1,25 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\ContextFactory;
use PleskRestApi\JMS\Serializer\DeserializationContext;
final class CallableDeserializationContextFactory implements DeserializationContextFactoryInterface
{
/**
* @var callable():DeserializationContext
*/
private $callable;
/**
* @param callable():DeserializationContext $callable
*/
public function __construct(callable $callable)
{
$this->callable = $callable;
}
public function createDeserializationContext() : DeserializationContext
{
$callable = $this->callable;
return $callable();
}
}

View File

@@ -1,28 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\ContextFactory;
use PleskRestApi\JMS\Serializer\SerializationContext;
/**
* Serialization Context Factory using a callable.
*/
final class CallableSerializationContextFactory implements SerializationContextFactoryInterface
{
/**
* @var callable():SerializationContext
*/
private $callable;
/**
* @param callable():SerializationContext $callable
*/
public function __construct(callable $callable)
{
$this->callable = $callable;
}
public function createSerializationContext() : SerializationContext
{
$callable = $this->callable;
return $callable();
}
}

View File

@@ -1,16 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\ContextFactory;
use PleskRestApi\JMS\Serializer\DeserializationContext;
/**
* Default Deserialization Context Factory.
*/
final class DefaultDeserializationContextFactory implements DeserializationContextFactoryInterface
{
public function createDeserializationContext() : DeserializationContext
{
return new DeserializationContext();
}
}

View File

@@ -1,16 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\ContextFactory;
use PleskRestApi\JMS\Serializer\SerializationContext;
/**
* Default Serialization Context Factory.
*/
final class DefaultSerializationContextFactory implements SerializationContextFactoryInterface
{
public function createSerializationContext() : SerializationContext
{
return new SerializationContext();
}
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\ContextFactory;
use PleskRestApi\JMS\Serializer\DeserializationContext;
/**
* Deserialization Context Factory Interface.
*/
interface DeserializationContextFactoryInterface
{
public function createDeserializationContext() : DeserializationContext;
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\ContextFactory;
use PleskRestApi\JMS\Serializer\SerializationContext;
/**
* Serialization Context Factory Interface.
*/
interface SerializationContextFactoryInterface
{
public function createSerializationContext() : SerializationContext;
}

View File

@@ -1,36 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer;
use PleskRestApi\JMS\Serializer\Exception\LogicException;
class DeserializationContext extends Context
{
/**
* @var int
*/
private $depth = 0;
public static function create() : self
{
return new self();
}
public function getDirection() : int
{
return GraphNavigatorInterface::DIRECTION_DESERIALIZATION;
}
public function getDepth() : int
{
return $this->depth;
}
public function increaseDepth() : void
{
$this->depth += 1;
}
public function decreaseDepth() : void
{
if ($this->depth <= 0) {
throw new LogicException('Depth cannot be smaller than zero.');
}
$this->depth -= 1;
}
}

View File

@@ -1,68 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
use PleskRestApi\JMS\Serializer\Context;
use PleskRestApi\JMS\Serializer\Type\Type;
use PleskRestApi\JMS\Serializer\VisitorInterface;
/**
* @phpstan-import-type TypeArray from Type
*/
class Event
{
/**
* @var bool Whether no further event listeners should be triggered
*/
private $propagationStopped = \false;
/**
* @var TypeArray
*/
protected $type;
/**
* @var Context
*/
private $context;
/**
* @param TypeArray $type
*/
public function __construct(Context $context, array $type)
{
$this->context = $context;
$this->type = $type;
}
public function getVisitor() : VisitorInterface
{
return $this->context->getVisitor();
}
public function getContext() : Context
{
return $this->context;
}
public function getType() : array
{
return $this->type;
}
/**
* Returns whether further event listeners should be triggered.
*
* @see Event::stopPropagation()
*
* @return bool Whether propagation was already stopped for this event
*/
public function isPropagationStopped() : bool
{
return $this->propagationStopped;
}
/**
* Stops the propagation of the event to further event listeners.
*
* If multiple event listeners are connected to the same event, no
* further event listener will be triggered once any trigger calls
* stopPropagation().
*/
public function stopPropagation() : void
{
$this->propagationStopped = \true;
}
}

View File

@@ -1,118 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
use PleskRestApi\JMS\Serializer\Exception\InvalidArgumentException;
/**
* Light-weight event dispatcher.
*
* This implementation focuses primarily on performance, and dispatching
* events for certain classes. It is not a general purpose event dispatcher.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
class EventDispatcher implements EventDispatcherInterface
{
/**
* @var array
*/
private $listeners = [];
/**
* ClassListeners cache
*
* @var array
*/
private $classListeners = [];
public static function getDefaultMethodName(string $eventName) : string
{
return 'on' . \str_replace(['_', '.'], '', $eventName);
}
/**
* Sets the listeners.
*
* @param array $listeners
*/
public function setListeners(array $listeners) : void
{
$this->listeners = $listeners;
$this->classListeners = [];
}
/**
* @internal Used for profiling
*/
public function getListeners() : array
{
return $this->listeners;
}
/**
* {@inheritdoc}
*/
public function addListener(string $eventName, $callable, ?string $class = null, ?string $format = null, ?string $interface = null) : void
{
$this->listeners[$eventName][] = [$callable, $class, $format, $interface];
unset($this->classListeners[$eventName]);
}
public function addSubscriber(EventSubscriberInterface $subscriber) : void
{
foreach ($subscriber->getSubscribedEvents() as $eventData) {
if (!isset($eventData['event'])) {
throw new InvalidArgumentException(\sprintf('Each event must have a "event" key.'));
}
$method = $eventData['method'] ?? self::getDefaultMethodName($eventData['event']);
$class = $eventData['class'] ?? null;
$format = $eventData['format'] ?? null;
$interface = $eventData['interface'] ?? null;
$this->listeners[$eventData['event']][] = [[$subscriber, $method], $class, $format, $interface];
unset($this->classListeners[$eventData['event']]);
}
}
public function hasListeners(string $eventName, string $class, string $format) : bool
{
if (!isset($this->listeners[$eventName])) {
return \false;
}
if (!isset($this->classListeners[$eventName][$class][$format])) {
$this->classListeners[$eventName][$class][$format] = $this->initializeListeners($eventName, $class, $format);
}
return !!$this->classListeners[$eventName][$class][$format];
}
public function dispatch(string $eventName, string $class, string $format, Event $event) : void
{
if (!isset($this->listeners[$eventName])) {
return;
}
$object = $event instanceof ObjectEvent ? $event->getObject() : null;
$realClass = \is_object($object) ? \get_class($object) : '';
$objectClass = $realClass !== $class ? $realClass . $class : $class;
if (!isset($this->classListeners[$eventName][$objectClass][$format])) {
$this->classListeners[$eventName][$objectClass][$format] = $this->initializeListeners($eventName, $class, $format);
}
foreach ($this->classListeners[$eventName][$objectClass][$format] as $listener) {
if (!empty($listener[3]) && !$object instanceof $listener[3]) {
continue;
}
\call_user_func($listener[0], $event, $eventName, $class, $format, $this);
if ($event->isPropagationStopped()) {
break;
}
}
}
/**
* @return array An array of listeners
*/
protected function initializeListeners(string $eventName, string $loweredClass, string $format) : array
{
$listeners = [];
foreach ($this->listeners[$eventName] as $listener) {
if (null !== $listener[1] && $loweredClass !== $listener[1]) {
continue;
}
if (null !== $listener[2] && $format !== $listener[2]) {
continue;
}
$listeners[] = $listener;
}
return $listeners;
}
}

View File

@@ -1,29 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
interface EventDispatcherInterface
{
/**
* Returns whether there are listeners.
*/
public function hasListeners(string $eventName, string $class, string $format) : bool;
/**
* Dispatches an event.
*
* The listeners/subscribers are called in the same order in which they
* were added to the dispatcher.
*/
public function dispatch(string $eventName, string $class, string $format, Event $event) : void;
/**
* Adds a listener.
*
* @param mixed $callable
*/
public function addListener(string $eventName, $callable, ?string $class = null, ?string $format = null, ?string $interface = null) : void;
/**
* Adds a subscribers.
*/
public function addSubscriber(EventSubscriberInterface $subscriber) : void;
}

View File

@@ -1,25 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
interface EventSubscriberInterface
{
/**
* Returns the events to which this class has subscribed.
*
* Return format:
* array(
* array('event' => 'the-event-name', 'method' => 'onEventName', 'class' => 'some-class', 'format' => 'json'),
* array(...),
* )
*
* The class may be omitted if the class wants to subscribe to events of all classes.
* Same goes for the format key.
*
* @return array
*
* @phpcsSuppress SlevomatCodingStandard.TypeHints.TypeHintDeclaration.MissingReturnTypeHint
*/
public static function getSubscribedEvents();
}

View File

@@ -1,15 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
abstract class Events
{
public const PRE_SERIALIZE = 'serializer.pre_serialize';
public const POST_SERIALIZE = 'serializer.post_serialize';
public const PRE_DESERIALIZE = 'serializer.pre_deserialize';
public const POST_DESERIALIZE = 'serializer.post_deserialize';
private final function __construct()
{
}
}

View File

@@ -1,42 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
use PleskRestApi\JMS\Serializer\Exception\InvalidArgumentException;
use Psr\Container\ContainerInterface as PsrContainerInterface;
use PleskRestApi\Symfony\Component\DependencyInjection\ContainerInterface;
class LazyEventDispatcher extends EventDispatcher
{
/**
* @var PsrContainerInterface|ContainerInterface
*/
private $container;
/**
* @param PsrContainerInterface|ContainerInterface $container
*/
public function __construct($container)
{
if (!$container instanceof PsrContainerInterface && !$container instanceof ContainerInterface) {
throw new InvalidArgumentException(\sprintf('The container must be an instance of %s or %s (%s given).', PsrContainerInterface::class, ContainerInterface::class, \is_object($container) ? \get_class($container) : \gettype($container)));
}
$this->container = $container;
}
/**
* {@inheritdoc}
*/
protected function initializeListeners(string $eventName, string $loweredClass, string $format) : array
{
$listeners = parent::initializeListeners($eventName, $loweredClass, $format);
foreach ($listeners as &$listener) {
if (!\is_array($listener[0]) || !\is_string($listener[0][0])) {
continue;
}
if (!$this->container->has($listener[0][0])) {
continue;
}
$listener[0][0] = $this->container->get($listener[0][0]);
}
return $listeners;
}
}

View File

@@ -1,33 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
use PleskRestApi\JMS\Serializer\Context;
use PleskRestApi\JMS\Serializer\Type\Type;
/**
* @phpstan-import-type TypeArray from Type
*/
class ObjectEvent extends Event
{
/**
* @var mixed
*/
private $object;
/**
* @param mixed $object
* @param TypeArray $type
*/
public function __construct(Context $context, $object, array $type)
{
parent::__construct($context, $type);
$this->object = $object;
}
/**
* @return mixed
*/
public function getObject()
{
return $this->object;
}
}

View File

@@ -1,44 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
use PleskRestApi\JMS\Serializer\DeserializationContext;
use PleskRestApi\JMS\Serializer\Type\Type;
/**
* @phpstan-import-type TypeArray from Type
*/
class PreDeserializeEvent extends Event
{
/**
* @var mixed
*/
private $data;
/**
* @param mixed $data
* @param TypeArray $type
*/
public function __construct(DeserializationContext $context, $data, array $type)
{
parent::__construct($context, $type);
$this->data = $data;
}
public function setType(string $name, array $params = []) : void
{
$this->type = ['name' => $name, 'params' => $params];
}
/**
* @return mixed
*/
public function getData()
{
return $this->data;
}
/**
* @param mixed $data
*/
public function setData($data) : void
{
$this->data = $data;
}
}

View File

@@ -1,12 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher;
class PreSerializeEvent extends ObjectEvent
{
public function setType(string $typeName, array $params = []) : void
{
$this->type = ['name' => $typeName, 'params' => $params];
}
}

View File

@@ -1,93 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher\Subscriber;
use PleskRestApi\Doctrine\Common\Persistence\Proxy as LegacyProxy;
use PleskRestApi\Doctrine\ODM\MongoDB\PersistentCollection as MongoDBPersistentCollection;
use PleskRestApi\Doctrine\ODM\PHPCR\PersistentCollection as PHPCRPersistentCollection;
use PleskRestApi\Doctrine\ORM\PersistentCollection;
use PleskRestApi\Doctrine\Persistence\Proxy;
use PleskRestApi\JMS\Serializer\EventDispatcher\EventDispatcherInterface;
use PleskRestApi\JMS\Serializer\EventDispatcher\EventSubscriberInterface;
use PleskRestApi\JMS\Serializer\EventDispatcher\PreSerializeEvent;
use PleskRestApi\ProxyManager\Proxy\LazyLoadingInterface;
final class DoctrineProxySubscriber implements EventSubscriberInterface
{
/**
* @var bool
*/
private $skipVirtualTypeInit;
/**
* @var bool
*/
private $initializeExcluded;
public function __construct(bool $skipVirtualTypeInit = \true, bool $initializeExcluded = \false)
{
$this->skipVirtualTypeInit = $skipVirtualTypeInit;
$this->initializeExcluded = $initializeExcluded;
}
public function onPreSerialize(PreSerializeEvent $event) : void
{
$object = $event->getObject();
$type = $event->getType();
// If the set type name is not an actual class, but a faked type for which a custom handler exists, we do not
// modify it with this subscriber. Also, we forgo autoloading here as an instance of this type is already created,
// so it must be loaded if its a real class.
$virtualType = !\class_exists($type['name'], \false);
if ($object instanceof PersistentCollection || $object instanceof MongoDBPersistentCollection || $object instanceof PHPCRPersistentCollection) {
if (!$virtualType) {
$event->setType('ArrayCollection');
}
return;
}
if ($this->skipVirtualTypeInit && $virtualType || !$object instanceof Proxy && !$object instanceof LazyLoadingInterface) {
return;
}
// do not initialize the proxy if is going to be excluded by-class by some exclusion strategy
if (\false === $this->initializeExcluded && !$virtualType) {
$context = $event->getContext();
$exclusionStrategy = $context->getExclusionStrategy();
$metadata = $context->getMetadataFactory()->getMetadataForClass(\get_parent_class($object));
if (null !== $metadata && null !== $exclusionStrategy && $exclusionStrategy->shouldSkipClass($metadata, $context)) {
return;
}
}
if ($object instanceof LazyLoadingInterface) {
$object->initializeProxy();
} else {
$object->__load();
}
if (!$virtualType) {
$event->setType(\get_parent_class($object), $type['params']);
}
}
public function onPreSerializeTypedProxy(PreSerializeEvent $event, string $eventName, string $class, string $format, EventDispatcherInterface $dispatcher) : void
{
$type = $event->getType();
// is a virtual type? then there is no need to change the event name
if (!\class_exists($type['name'], \false)) {
return;
}
$object = $event->getObject();
if ($object instanceof Proxy) {
$parentClassName = \get_parent_class($object);
// check if this is already a re-dispatch
if (\strtolower($class) !== \strtolower($parentClassName)) {
$event->stopPropagation();
$newEvent = new PreSerializeEvent($event->getContext(), $object, ['name' => $parentClassName, 'params' => $type['params']]);
$dispatcher->dispatch($eventName, $parentClassName, $format, $newEvent);
// update the type in case some listener changed it
$newType = $newEvent->getType();
$event->setType($newType['name'], $newType['params']);
}
}
}
/**
* {@inheritdoc}
*/
public static function getSubscribedEvents()
{
return [['event' => 'serializer.pre_serialize', 'method' => 'onPreSerializeTypedProxy', 'interface' => Proxy::class], ['event' => 'serializer.pre_serialize', 'method' => 'onPreSerializeTypedProxy', 'interface' => LegacyProxy::class], ['event' => 'serializer.pre_serialize', 'method' => 'onPreSerialize', 'interface' => PersistentCollection::class], ['event' => 'serializer.pre_serialize', 'method' => 'onPreSerialize', 'interface' => MongoDBPersistentCollection::class], ['event' => 'serializer.pre_serialize', 'method' => 'onPreSerialize', 'interface' => PHPCRPersistentCollection::class], ['event' => 'serializer.pre_serialize', 'method' => 'onPreSerialize', 'interface' => Proxy::class], ['event' => 'serializer.pre_serialize', 'method' => 'onPreSerialize', 'interface' => LegacyProxy::class], ['event' => 'serializer.pre_serialize', 'method' => 'onPreSerialize', 'interface' => LazyLoadingInterface::class]];
}
}

View File

@@ -1,27 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher\Subscriber;
use PleskRestApi\JMS\Serializer\EventDispatcher\EventSubscriberInterface;
use PleskRestApi\JMS\Serializer\EventDispatcher\PreSerializeEvent;
final class EnumSubscriber implements EventSubscriberInterface
{
public function onPreSerializeEnum(PreSerializeEvent $event) : void
{
$type = $event->getType();
if (isset($type['name']) && ('enum' === $type['name'] || !\is_a($type['name'], \UnitEnum::class, \true))) {
return;
}
$object = $event->getObject();
$params = [\get_class($object), $object instanceof \BackedEnum ? 'value' : 'name'];
$event->setType('enum', $params);
}
/**
* {@inheritdoc}
*/
public static function getSubscribedEvents()
{
return [['event' => 'serializer.pre_serialize', 'method' => 'onPreSerializeEnum', 'interface' => \UnitEnum::class]];
}
}

View File

@@ -1,44 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\EventDispatcher\Subscriber;
use PleskRestApi\JMS\Serializer\EventDispatcher\EventSubscriberInterface;
use PleskRestApi\JMS\Serializer\EventDispatcher\ObjectEvent;
use PleskRestApi\JMS\Serializer\Exception\ValidationFailedException;
use PleskRestApi\Symfony\Component\Validator\Validator\ValidatorInterface;
final class SymfonyValidatorValidatorSubscriber implements EventSubscriberInterface
{
/**
* @var ValidatorInterface
*/
private $validator;
public function __construct(ValidatorInterface $validator)
{
$this->validator = $validator;
}
/**
* {@inheritdoc}
*/
public static function getSubscribedEvents()
{
return [['event' => 'serializer.post_deserialize', 'method' => 'onPostDeserialize']];
}
public function onPostDeserialize(ObjectEvent $event) : void
{
$context = $event->getContext();
if ($context->getDepth() > 0) {
return;
}
$validator = $this->validator;
$groups = $context->hasAttribute('validation_groups') ? $context->getAttribute('validation_groups') : null;
if (!$groups) {
return;
}
$constraints = $context->hasAttribute('validation_constraints') ? $context->getAttribute('validation_constraints') : null;
$list = $validator->validate($event->getObject(), $constraints, $groups);
if ($list->count() > 0) {
throw new ValidationFailedException($list);
}
}
}

View File

@@ -1,11 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Exception;
/**
* @author Asmir Mustafic <goetas@gmail.com>
*/
class CircularReferenceDetectedException extends NotAcceptableException
{
}

View File

@@ -1,13 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Exception;
/**
* Base exception for the Serializer.
*
* @author Johannes M. Schmitt <schmittjoh@gmail.com>
*/
interface Exception extends \Throwable
{
}

View File

@@ -1,11 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Exception;
/**
* @author Asmir Mustafic <goetas@gmail.com>
*/
class ExcludedClassException extends NotAcceptableException
{
}

View File

@@ -1,11 +0,0 @@
<?php
declare (strict_types=1);
namespace PleskRestApi\JMS\Serializer\Exception;
/**
* @author Asmir Mustafic <goetas@gmail.com>
*/
class ExpressionLanguageRequiredException extends LogicException
{
}

Some files were not shown because too many files have changed in this diff Show More