diff --git a/README.md b/README.md index d860128..41612eb 100644 --- a/README.md +++ b/README.md @@ -19,12 +19,24 @@ composer require micro/dto ``` xml - + xsi:schemaLocation="micro:dto-1.6 https://raw.githubusercontent.com/Micro-PHP/dto/master/src/Resource/schema/dto-1.6.xsd"> - - + + + + + + + + + + + + + + @@ -32,16 +44,37 @@ composer require micro/dto ``` * And run generator ```php -use Micro\Library\DTO\ClassGeneratorFacadeDefault; - -$classGenerator = new ClassGeneratorFacadeDefault( +$classGenerator = new \Micro\Library\DTO\ClassGeneratorFacadeDefault( ['./example.xml'], // List of class declaration files './out', // Path to the folder where to generate 'Transfer' // Suffix for the all DTO classes (optional) ); - $classGenerator->generate(); +// Usage example +$user = new \User\User(); +$user + ->setAge(19) + ->setEmail('demo@micro-php.net'); +// OR +// +$user['age'] = 19; +$user['email'] = 'demo@micro-php.net'; + +// Validation example +$validator = new \Micro\Library\DTO\ValidatorFacadeDefault(); +$validator->validate($user); // Validation groups by default ["Default"] +$validator->validate($user, ['patch', 'put']); // Set validation groups ["patch", "put"] + +// Serialize example +$serializer = new \Micro\Library\DTO\SerializerFacadeDefault(); +$serializer->toArray($user); // Simple array +$serializer->toJson($user); // Simple Json + +// Deserialize example +$serialized = $serializer->toJsonTransfer($user); +$deserialized = $serializer->fromJsonTransfer($serialized); + ``` ### [See full example](./example/) diff --git a/composer.json b/composer.json index 3a3c6bc..48e716d 100755 --- a/composer.json +++ b/composer.json @@ -20,7 +20,7 @@ } ], "require": { - "php": ">= 8.1", + "php": ">= 8.0", "ext-dom": "*", "ext-intl": "*", "ext-libxml": "*", diff --git a/example/out/Simple/SimpleUserTransfer.php b/example/out/Simple/SimpleUserTransfer.php index 0a571be..00f8ebd 100644 --- a/example/out/Simple/SimpleUserTransfer.php +++ b/example/out/Simple/SimpleUserTransfer.php @@ -44,7 +44,7 @@ final class SimpleUserTransfer extends \Micro\Library\DTO\Object\AbstractDto protected string|null $json = null; #[\Symfony\Component\Validator\Constraints\NotBlank(groups: ['Default'], allowNull: false)] - #[\Symfony\Component\Validator\Constraints\Uuid(groups: ['Default'], versions: [1, 2, 3, 4, 5, 6, 7], strict: true)] + #[\Symfony\Component\Validator\Constraints\Uuid(groups: ['Default'], versions: [1, 2, 3, 4, 5, 6], strict: true)] protected string|null $uuid = null; #[\Symfony\Component\Validator\Constraints\DateTime(groups: ['Default'], format: 'Y-m-d H:i:s')] @@ -78,6 +78,7 @@ final class SimpleUserTransfer extends \Micro\Library\DTO\Object\AbstractDto protected string|null $isbn = null; #[\Symfony\Component\Validator\Constraints\NotBlank(groups: ['Default'], allowNull: false)] + #[\Symfony\Component\Validator\Constraints\Issn(groups: ['Default'])] protected string|null $issn = null; #[\Symfony\Component\Validator\Constraints\NotBlank(groups: ['Default'], allowNull: false)] diff --git a/example/test.php b/example/test.php index de5f278..3aff912 100755 --- a/example/test.php +++ b/example/test.php @@ -2,86 +2,95 @@ require dirname(__FILE__) . '/../vendor/autoload.php'; -// Create Logger -$logger = new class extends \Psr\Log\NullLogger { - public function debug(\Stringable|string $message, array $context = []): void - { - print_r("$message\r\n"); - } -}; - -// Create default class generator facade +/** + * Create default class generator facade + */ $classGenerator = new \Micro\Library\DTO\ClassGeneratorFacadeDefault( ['./example.xml'], './out', 'Transfer', 'Transfer', - $logger ); $classGenerator->generate(); -// Require generated classes +/** + * Require generated classes + */ require_once 'out/Simple/SimpleObjectTransfer.php'; require_once 'out/Simple/SimpleUserTransfer.php'; require_once 'out/UserTransfer.php'; +use Transfer\UserTransfer; +use Transfer\Simple\SimpleObjectTransfer; +use Micro\Library\DTO\SerializerFacadeDefault; +use Micro\Library\DTO\ValidatorFacadeDefault; +use Transfer\Simple\SimpleUserTransfer; -$user = new \Transfer\UserTransfer(); +/** + * Iterate DTO values + */ +$user = new UserTransfer(); $user ->setFirstName('Stas') ->setUsername('Asisyas') ->setUpdatedAt(new DateTime('11.08.1989')) ->setBooks( [ - (new Transfer\Simple\SimpleObjectTransfer()) + (new SimpleObjectTransfer()) ->setHeight(1) ->setWeight(20) ->setParent( - (new Transfer\Simple\SimpleObjectTransfer()) + (new SimpleObjectTransfer()) ->setHeight(100) ->setWeight(2000) ) ]) ->setSomeclass( - (new \Transfer\Simple\SimpleObjectTransfer()) + (new SimpleObjectTransfer()) ->setWeight(1) ->setHeight(2) ) ; -// Iterate as array foreach ($user as $key => $value) { -// print_r("\r\nPROPERTY: " . $key . " ==== " . (is_scalar($value) ? $value : serialize($value))); + print_r("\r\nPROPERTY: " . $key . " ==== " . (is_scalar($value) ? $value : serialize($value))); } -// -//print_r('FISRT BOOK HEIGHT : ' . $user['books'][0]['height'] . "\r\n"); -//print_r('FISRT BOOK PARENT HEIGHT : ' . $user['books'][0]['parent']['height'] . "\r\n"); +/** + * Array access example + */ +print_r("\r\n\r\nFISRT BOOK HEIGHT : " . $user['books'][0]['height'] . "\r\n"); +print_r('FISRT BOOK PARENT HEIGHT : ' . $user['books'][0]['parent']['height'] . "\r\n\r\n"); +// Allowed too +$user['books'][0]['height'] = 12; -$classSerializerFacade = new \Micro\Library\DTO\SerializerFacadeDefault(); +/** + * Serialization example + */ +$classSerializerFacade = new SerializerFacadeDefault(); +$jsonDto = $classSerializerFacade->toJsonTransfer($user); +$json = $classSerializerFacade->toJson($user); +print_r('Serialized DTO: ' . $jsonDto . "\r\n\r\n"); +print_r('Serialize DTO as JSON: ' . $json . "\r\n\r\n"); -$json = $classSerializerFacade->toJsonTransfer($user); +$deserialized = $classSerializerFacade->fromJsonTransfer($jsonDto); -//dump($json); +$className = get_class($user); +$okNo = get_class($deserialized) === $className ?'true' : 'false'; +print_r( "Deserialize $className: $okNo \r\n"); -$result = $classSerializerFacade->fromJsonTransfer($json); - -$mf = new \Symfony\Component\Validator\Mapping\Factory\LazyLoadingMetadataFactory(new \Symfony\Component\Validator\Mapping\Loader\AnnotationLoader()); - -$vb = \Symfony\Component\Validator\Validation::createValidatorBuilder(); -$vb->setMetadataFactory($mf); -$vb->disableAnnotationMapping(); -$validator = $vb->getValidator(); - -$simpleUserParent = new \Transfer\Simple\SimpleObjectTransfer(); +/** + * Validate DTO example + */ +$simpleUserParent = new SimpleObjectTransfer(); $simpleUserParent ->setWeight(9) ->setHeight(8); -$simpleUser = new \Transfer\Simple\SimpleUserTransfer(); +$simpleUser = new SimpleUserTransfer(); $simpleUser ->setParent($simpleUserParent) ->setIp('192.168.0.1') @@ -105,10 +114,10 @@ public function debug(\Stringable|string $message, array $context = []): void ->setIsin('US0378331005') ; +$validator = new ValidatorFacadeDefault(); $constraints = $validator->validate($simpleUser); -dump($constraints); - -//dump($result); +$validationStatus = !count($constraints) ? 'Validated': 'Validation error'; +print_r("Validation status: $validationStatus\r\n"); diff --git a/src/ClassGeneratorFacadeDefault.php b/src/ClassGeneratorFacadeDefault.php index ad1652d..e261f21 100755 --- a/src/ClassGeneratorFacadeDefault.php +++ b/src/ClassGeneratorFacadeDefault.php @@ -14,7 +14,6 @@ namespace Micro\Library\DTO; use Psr\Log\LoggerInterface; -use Psr\Log\NullLogger; class ClassGeneratorFacadeDefault extends GeneratorFacade { @@ -26,11 +25,11 @@ class ClassGeneratorFacadeDefault extends GeneratorFacade * @param LoggerInterface|null $logger */ public function __construct( - private readonly array $filesSchemeCollection, - private readonly string $outputPath, - private readonly string $namespaceGeneral = '', - private readonly string $classSuffix = 'Transfer', - private readonly null|LoggerInterface $logger = new NullLogger(), + private array $filesSchemeCollection, + private string $outputPath, + private string $namespaceGeneral = '', + private string $classSuffix = 'Transfer', + private null|LoggerInterface $logger = null ) { parent::__construct($this->createDefaultDependencyInjectionObject()); } diff --git a/src/DependencyInjection.php b/src/DependencyInjection.php index 1a468af..58b477f 100755 --- a/src/DependencyInjection.php +++ b/src/DependencyInjection.php @@ -42,6 +42,7 @@ use Micro\Library\DTO\Preparation\Processor\Property\Assert\IpStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\IsbnStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\IsinStrategy; +use Micro\Library\DTO\Preparation\Processor\Property\Assert\IssnStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\JsonStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\LengthStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\LessThanOrEqualStrategy; @@ -56,6 +57,7 @@ use Micro\Library\DTO\Preparation\Processor\Property\Assert\PositiveStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\RangeStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\RegexStrategy; +use Micro\Library\DTO\Preparation\Processor\Property\Assert\TimeStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\TimeZoneStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\UrlStrategy; use Micro\Library\DTO\Preparation\Processor\Property\Assert\UuidStrategy; @@ -85,11 +87,11 @@ class DependencyInjection implements DependencyInjectionInterface * @param string[] $filesSchemeCollection */ public function __construct( - private readonly array $filesSchemeCollection, - private readonly string $namespaceGeneral, - private readonly string $classSuffix, - private readonly string $outputPath, - private readonly ?LoggerInterface $logger + private array $filesSchemeCollection, + private string $namespaceGeneral, + private string $classSuffix, + private string $outputPath, + private ?LoggerInterface $logger ) { } @@ -182,6 +184,7 @@ protected function createPropertyValidationProcessorCollection(): iterable new JsonStrategy(), new UuidStrategy(), new DateStrategy(), + new TimeStrategy(), new DateTimeStrategy(), new TimeZoneStrategy(), new NegativeStrategy(), @@ -204,6 +207,7 @@ protected function createPropertyValidationProcessorCollection(): iterable new IbanStrategy(), new IsbnStrategy(), new IsinStrategy(), + new IssnStrategy(), ]; } } diff --git a/src/Generator/Generator.php b/src/Generator/Generator.php index e45790c..c7048d7 100755 --- a/src/Generator/Generator.php +++ b/src/Generator/Generator.php @@ -23,11 +23,11 @@ class Generator { public function __construct( - private readonly ReaderInterface $reader, - private readonly WriterInterface $writer, - private readonly RendererInterface $renderer, - private readonly CollectionPreparationInterface $classCollectionPreparation, - private readonly LoggerInterface $logger + private ReaderInterface $reader, + private WriterInterface $writer, + private RendererInterface $renderer, + private CollectionPreparationInterface $classCollectionPreparation, + private LoggerInterface $logger ) { } diff --git a/src/GeneratorFacade.php b/src/GeneratorFacade.php index 467055b..9241387 100755 --- a/src/GeneratorFacade.php +++ b/src/GeneratorFacade.php @@ -18,7 +18,7 @@ class GeneratorFacade implements GeneratorFacadeInterface { public function __construct( - private readonly DependencyInjectionInterface $dependencyInjection + private DependencyInjectionInterface $dependencyInjection ) { } diff --git a/src/Helper/ClassMetadataHelper.php b/src/Helper/ClassMetadataHelper.php index 6fde8fa..f36a4e4 100755 --- a/src/Helper/ClassMetadataHelper.php +++ b/src/Helper/ClassMetadataHelper.php @@ -22,8 +22,8 @@ class ClassMetadataHelper implements ClassMetadataHelperInterface * @param string $classSuffix */ public function __construct( - private readonly string $namespaceGeneral, - private readonly string $classSuffix + private string $namespaceGeneral, + private string $classSuffix ) { } diff --git a/src/Merger/Merger.php b/src/Merger/Merger.php index eecef10..9edc1d4 100644 --- a/src/Merger/Merger.php +++ b/src/Merger/Merger.php @@ -18,7 +18,7 @@ class Merger implements MergerInterface /** * @param array $classCollection */ - public function __construct(private readonly array $classCollection) + public function __construct(private array $classCollection) { } diff --git a/src/Preparation/CollectionPreparation.php b/src/Preparation/CollectionPreparation.php index 614fa37..74b0a94 100755 --- a/src/Preparation/CollectionPreparation.php +++ b/src/Preparation/CollectionPreparation.php @@ -21,7 +21,7 @@ class CollectionPreparation implements CollectionPreparationInterface /** * @param iterable $preparationProcessor */ - public function __construct(private readonly iterable $preparationProcessor) + public function __construct(private iterable $preparationProcessor) { } diff --git a/src/Preparation/Processor/ClassNameProcessor.php b/src/Preparation/Processor/ClassNameProcessor.php index a2f8a5f..da098af 100644 --- a/src/Preparation/Processor/ClassNameProcessor.php +++ b/src/Preparation/Processor/ClassNameProcessor.php @@ -19,7 +19,7 @@ class ClassNameProcessor implements PreparationProcessorInterface { - public function __construct(private readonly ClassMetadataHelperInterface $classMetadataHelper) + public function __construct(private ClassMetadataHelperInterface $classMetadataHelper) { } diff --git a/src/Preparation/Processor/ClassPropertyProcessor.php b/src/Preparation/Processor/ClassPropertyProcessor.php index 8213a81..d498618 100644 --- a/src/Preparation/Processor/ClassPropertyProcessor.php +++ b/src/Preparation/Processor/ClassPropertyProcessor.php @@ -23,7 +23,7 @@ class ClassPropertyProcessor implements PreparationProcessorInterface /** * @param iterable $propertyProcessorCollection */ - public function __construct(private readonly iterable $propertyProcessorCollection) + public function __construct(private iterable $propertyProcessorCollection) { } diff --git a/src/Preparation/Processor/MethodAttributesMetadataProcessor.php b/src/Preparation/Processor/MethodAttributesMetadataProcessor.php index 343e59b..4d24bc3 100644 --- a/src/Preparation/Processor/MethodAttributesMetadataProcessor.php +++ b/src/Preparation/Processor/MethodAttributesMetadataProcessor.php @@ -20,7 +20,7 @@ class MethodAttributesMetadataProcessor implements PreparationProcessorInterface { - public function __construct(private readonly NameNormalizerInterface $nameNormalizer) + public function __construct(private NameNormalizerInterface $nameNormalizer) { } diff --git a/src/Preparation/Processor/MethodGetProcessor.php b/src/Preparation/Processor/MethodGetProcessor.php index 3b2cf0b..82503e0 100644 --- a/src/Preparation/Processor/MethodGetProcessor.php +++ b/src/Preparation/Processor/MethodGetProcessor.php @@ -21,7 +21,7 @@ class MethodGetProcessor implements PreparationProcessorInterface { - public function __construct(private readonly NameNormalizerInterface $nameNormalizer) + public function __construct(private NameNormalizerInterface $nameNormalizer) { } diff --git a/src/Preparation/Processor/MethodSetProcessor.php b/src/Preparation/Processor/MethodSetProcessor.php index e31dbe9..6afb113 100644 --- a/src/Preparation/Processor/MethodSetProcessor.php +++ b/src/Preparation/Processor/MethodSetProcessor.php @@ -24,7 +24,7 @@ class MethodSetProcessor implements PreparationProcessorInterface /** * @param NameNormalizerInterface $nameNormalizer */ - public function __construct(private readonly NameNormalizerInterface $nameNormalizer) + public function __construct(private NameNormalizerInterface $nameNormalizer) { } diff --git a/src/Preparation/Processor/Property/Assert/AbstractComparisonStrategy.php b/src/Preparation/Processor/Property/Assert/AbstractComparisonStrategy.php index fea0cc0..e573fa7 100644 --- a/src/Preparation/Processor/Property/Assert/AbstractComparisonStrategy.php +++ b/src/Preparation/Processor/Property/Assert/AbstractComparisonStrategy.php @@ -18,11 +18,11 @@ abstract class AbstractComparisonStrategy extends AbstractConstraintStrategy protected function generateArguments(array $config): array { $parent = parent::generateArguments($config); - - return array_filter([ - ...$parent, + $current = [ 'propertyPath' => $config['property_path'] ?? null, 'value' => $config['value'] ?? null, - ]); + ]; + + return array_filter(array_merge($parent, $current)); } } diff --git a/src/Preparation/Processor/Property/Assert/AbstractConstraintStrategy.php b/src/Preparation/Processor/Property/Assert/AbstractConstraintStrategy.php index f1263e4..bef77a6 100644 --- a/src/Preparation/Processor/Property/Assert/AbstractConstraintStrategy.php +++ b/src/Preparation/Processor/Property/Assert/AbstractConstraintStrategy.php @@ -64,7 +64,7 @@ protected function addAttribute(PropertyDefinition $propertyDefinition, string $ /** * @param array $config * - * @return array + * @return array */ protected function generateArguments(array $config): array { diff --git a/src/Preparation/Processor/Property/Assert/BicStrategy.php b/src/Preparation/Processor/Property/Assert/BicStrategy.php index 8849cf8..14bb53d 100644 --- a/src/Preparation/Processor/Property/Assert/BicStrategy.php +++ b/src/Preparation/Processor/Property/Assert/BicStrategy.php @@ -19,12 +19,14 @@ class BicStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - return array_filter([ - ...parent::generateArguments($config), + $parent = parent::generateArguments($config); + $current = [ 'iban' => $config['iban'] ?? null, 'ibanMessage' => $config['message_iban'] ?? null, 'ibanPropertyPath' => $config['iban_property_path'] ?? null, - ]); + ]; + + return array_filter(array_merge($parent, $current)); } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/CardSchemeStrategy.php b/src/Preparation/Processor/Property/Assert/CardSchemeStrategy.php index d4f2336..bb2e77d 100644 --- a/src/Preparation/Processor/Property/Assert/CardSchemeStrategy.php +++ b/src/Preparation/Processor/Property/Assert/CardSchemeStrategy.php @@ -19,10 +19,10 @@ class CardSchemeStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - return array_filter([ - ...parent::generateArguments($config), - 'schemes' => $this->extractSchemes($config), - ]); + $parent = parent::generateArguments($config); + $parent['schemes'] = $this->extractSchemes($config); + + return array_filter($parent); } /** diff --git a/src/Preparation/Processor/Property/Assert/DateTimeStrategy.php b/src/Preparation/Processor/Property/Assert/DateTimeStrategy.php index 73cb984..ba321df 100644 --- a/src/Preparation/Processor/Property/Assert/DateTimeStrategy.php +++ b/src/Preparation/Processor/Property/Assert/DateTimeStrategy.php @@ -20,11 +20,9 @@ class DateTimeStrategy extends AbstractConstraintStrategy protected function generateArguments(array $config): array { $parent = parent::generateArguments($config); + $parent['format'] = $config['format'] ?? 'Y-m-d H:i:s'; - return [ - ...$parent, - 'format' => $config['format'] ?? 'Y-m-d H:i:s', - ]; + return $parent; } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/EmailStrategy.php b/src/Preparation/Processor/Property/Assert/EmailStrategy.php index 852e17a..5ae420f 100644 --- a/src/Preparation/Processor/Property/Assert/EmailStrategy.php +++ b/src/Preparation/Processor/Property/Assert/EmailStrategy.php @@ -19,12 +19,10 @@ class EmailStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - $parentArgs = parent::generateArguments($config); + $parent = parent::generateArguments($config); + $parent['mode'] = $config['mode'] ?? 'html5'; - return [ - ...$parentArgs, - 'mode' => $config['mode'] ?? 'html5', - ]; + return $parent; } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/HostnameStrategy.php b/src/Preparation/Processor/Property/Assert/HostnameStrategy.php index 84a48ac..2f1f8d6 100644 --- a/src/Preparation/Processor/Property/Assert/HostnameStrategy.php +++ b/src/Preparation/Processor/Property/Assert/HostnameStrategy.php @@ -19,14 +19,10 @@ class HostnameStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - $arguments = parent::generateArguments($config); - - return [ - ...$arguments, - ...[ - 'requireTld' => $this->stringToBool($config['ltd_required'] ?? 'false'), - ], - ]; + $parent = parent::generateArguments($config); + $parent['requireTld'] = $this->stringToBool($config['ltd_required'] ?? 'false'); + + return $parent; } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/IpStrategy.php b/src/Preparation/Processor/Property/Assert/IpStrategy.php index 176a312..3a6ded1 100644 --- a/src/Preparation/Processor/Property/Assert/IpStrategy.php +++ b/src/Preparation/Processor/Property/Assert/IpStrategy.php @@ -20,11 +20,9 @@ class IpStrategy extends AbstractConstraintStrategy protected function generateArguments(array $config): array { $parent = parent::generateArguments($config); + $parent['version'] = $config['version'] ?? '4'; - return [ - ...$parent, - 'version' => $config['version'] ?? '4', - ]; + return $parent; } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/IsbnStrategy.php b/src/Preparation/Processor/Property/Assert/IsbnStrategy.php index ceb9b2c..e3c0712 100644 --- a/src/Preparation/Processor/Property/Assert/IsbnStrategy.php +++ b/src/Preparation/Processor/Property/Assert/IsbnStrategy.php @@ -19,13 +19,15 @@ class IsbnStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - return array_filter([ - ...parent::generateArguments($config), + $parent = parent::generateArguments($config); + $current = [ 'type' => $config['type'] ?? null, 'isbn10Message' => $config['message_isbn_10'] ?? null, 'isbn13Message' => $config['message_isbn_13'] ?? null, 'bothIsbnMessage' => $config['message_isbn_both'] ?? null, - ]); + ]; + + return array_filter(array_merge($parent, $current)); } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/IssnStrategy.php b/src/Preparation/Processor/Property/Assert/IssnStrategy.php index 704a4bb..e39ba3d 100644 --- a/src/Preparation/Processor/Property/Assert/IssnStrategy.php +++ b/src/Preparation/Processor/Property/Assert/IssnStrategy.php @@ -19,11 +19,13 @@ class IssnStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - return array_filter([ - ...parent::generateArguments($config), + $parent = parent::generateArguments($config); + $current = [ 'caseSensitive' => $this->stringToBool($config['case_sensitive'] ?? 'false'), 'requireHyphen' => $this->stringToBool($config['require_hyphen'] ?? 'false'), - ]); + ]; + + return array_filter(array_merge($parent, $current)); } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/LengthStrategy.php b/src/Preparation/Processor/Property/Assert/LengthStrategy.php index da77616..0cd63e3 100644 --- a/src/Preparation/Processor/Property/Assert/LengthStrategy.php +++ b/src/Preparation/Processor/Property/Assert/LengthStrategy.php @@ -29,13 +29,14 @@ protected function generateArguments(array $config): array $config[$attribute] = (int) $config[$attribute]; } - return array_filter([ - ...$parent, + $current = [ 'max' => $config['max'] ?? null, 'min' => $config['min'] ?? null, 'minMessage' => $config['min_message'] ?? null, 'maxMessage' => $config['max_message'] ?? null, - ]); + ]; + + return array_filter(array_merge($parent, $current)); } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/NotBlankStrategy.php b/src/Preparation/Processor/Property/Assert/NotBlankStrategy.php index 40232f4..a77ef04 100644 --- a/src/Preparation/Processor/Property/Assert/NotBlankStrategy.php +++ b/src/Preparation/Processor/Property/Assert/NotBlankStrategy.php @@ -20,11 +20,9 @@ class NotBlankStrategy extends AbstractConstraintStrategy protected function generateArguments(array $config): array { $parent = parent::generateArguments($config); + $parent['allowNull'] = $this->stringToBool($config['allow_null'] ?? 'false'); - return [ - ...$parent, - 'allowNull' => $this->stringToBool($config['allow_null'] ?? 'false'), - ]; + return $parent; } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/RangeStrategy.php b/src/Preparation/Processor/Property/Assert/RangeStrategy.php index aed65e0..e6aecb7 100644 --- a/src/Preparation/Processor/Property/Assert/RangeStrategy.php +++ b/src/Preparation/Processor/Property/Assert/RangeStrategy.php @@ -19,14 +19,16 @@ class RangeStrategy extends LengthStrategy { protected function generateArguments(array $config): array { - return array_filter([ - ...parent::generateArguments($config), + $parent = parent::generateArguments($config); + $current = [ 'invalidDateTimeMessage' => $config['invalid_datetime_message'] ?? null, 'invalidMessage' => $config['invalid_message'] ?? null, 'maxPropertyPath' => $config['property_path_max'] ?? null, 'minPropertyPath' => $config['property_path_min'] ?? null, 'notInRangeMessage' => $config['message_not_in_range'] ?? null, - ]); + ]; + + return array_filter(array_merge($parent, $current)); } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/RegexStrategy.php b/src/Preparation/Processor/Property/Assert/RegexStrategy.php index 7159ac1..6e95607 100644 --- a/src/Preparation/Processor/Property/Assert/RegexStrategy.php +++ b/src/Preparation/Processor/Property/Assert/RegexStrategy.php @@ -19,15 +19,12 @@ class RegexStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - $parentArgs = parent::generateArguments($config); + $parent = parent::generateArguments($config); - $match = $config['match'] ?? 'true'; + $parent['pattern'] = $config['pattern']; + $parent['match'] = $this->stringToBool($config['match'] ?? 'true'); - return [ - ...$parentArgs, - 'pattern' => $config['pattern'], - 'match' => $this->stringToBool($match), - ]; + return $parent; } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/TimeZoneStrategy.php b/src/Preparation/Processor/Property/Assert/TimeZoneStrategy.php index 22fa7bd..4c7e321 100644 --- a/src/Preparation/Processor/Property/Assert/TimeZoneStrategy.php +++ b/src/Preparation/Processor/Property/Assert/TimeZoneStrategy.php @@ -21,12 +21,11 @@ protected function generateArguments(array $config): array { $parent = parent::generateArguments($config); - return array_filter([ - ...$parent, - 'countryCode' => $config['country_code'] ?? null, - 'intlCompatible' => $this->stringToBool($config['intl_compatible'] ?? 'false'), - 'zone' => (int) ($config['zone'] ?? \DateTimeZone::ALL), - ]); + $parent['countryCode'] = $config['country_code'] ?? null; + $parent['intlCompatible'] = $this->stringToBool($config['intl_compatible'] ?? 'false'); + $parent['zone'] = (int) ($config['zone'] ?? \DateTimeZone::ALL); + + return array_filter($parent); } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/UrlStrategy.php b/src/Preparation/Processor/Property/Assert/UrlStrategy.php index 068ee8e..761d687 100644 --- a/src/Preparation/Processor/Property/Assert/UrlStrategy.php +++ b/src/Preparation/Processor/Property/Assert/UrlStrategy.php @@ -19,13 +19,11 @@ class UrlStrategy extends AbstractConstraintStrategy { protected function generateArguments(array $config): array { - $parentArgs = parent::generateArguments($config); - // TODO: protocols + $parent = parent::generateArguments($config); - return [ - ...$parentArgs, - 'relativeProtocol' => $this->stringToBool($config['is_relative'] ?? 'false'), - ]; + $parent['relativeProtocol'] = $this->stringToBool($config['is_relative'] ?? 'false'); + + return $parent; } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/Assert/UuidStrategy.php b/src/Preparation/Processor/Property/Assert/UuidStrategy.php index 01e1181..81bf342 100644 --- a/src/Preparation/Processor/Property/Assert/UuidStrategy.php +++ b/src/Preparation/Processor/Property/Assert/UuidStrategy.php @@ -37,11 +37,15 @@ public function getAvailableVersions(): array protected function generateArguments(array $config): array { /** @psalm-suppress PossiblyInvalidArgument */ - return array_filter([ - ...parent::generateArguments($config), - 'versions' => $this->parseVersions(trim($config['versions'] ?? '')), - 'strict' => $this->stringToBool($config['strict'] ?? 'true'), - ]); + return array_filter( + array_merge( + parent::generateArguments($config), + [ + 'versions' => $this->parseVersions(trim($config['versions'] ?? '')), + 'strict' => $this->stringToBool($config['strict'] ?? 'true'), + ] + ) + ); } protected function getValidatorProperty(): string diff --git a/src/Preparation/Processor/Property/AttributeValidationProcessor.php b/src/Preparation/Processor/Property/AttributeValidationProcessor.php index dd2279d..9bb41e9 100644 --- a/src/Preparation/Processor/Property/AttributeValidationProcessor.php +++ b/src/Preparation/Processor/Property/AttributeValidationProcessor.php @@ -22,7 +22,7 @@ class AttributeValidationProcessor implements PropertyProcessorInterface * @param iterable $validatorProcessor */ public function __construct( - private readonly iterable $validatorProcessor + private iterable $validatorProcessor ) { } diff --git a/src/Preparation/Processor/Property/DtoPropertyProcessor.php b/src/Preparation/Processor/Property/DtoPropertyProcessor.php index 4d4136b..cb277d8 100644 --- a/src/Preparation/Processor/Property/DtoPropertyProcessor.php +++ b/src/Preparation/Processor/Property/DtoPropertyProcessor.php @@ -19,7 +19,7 @@ class DtoPropertyProcessor implements PropertyProcessorInterface { - public function __construct(private readonly ClassMetadataHelperInterface $classMetadataHelper) + public function __construct(private ClassMetadataHelperInterface $classMetadataHelper) { } diff --git a/src/Reader/XmlReader.php b/src/Reader/XmlReader.php index acab652..f901b27 100755 --- a/src/Reader/XmlReader.php +++ b/src/Reader/XmlReader.php @@ -25,8 +25,8 @@ class XmlReader implements ReaderInterface * @param iterable $classDefinitionFilesCollection */ public function __construct( - private readonly iterable $classDefinitionFilesCollection, - private readonly MergerFactoryInterface $mergerFactory + private iterable $classDefinitionFilesCollection, + private MergerFactoryInterface $mergerFactory ) { } diff --git a/src/Resource/schema/dto-1.6.json b/src/Resource/schema/dto-1.6.json new file mode 100644 index 0000000..6b40de7 --- /dev/null +++ b/src/Resource/schema/dto-1.6.json @@ -0,0 +1,736 @@ +{ + "$schema": "https://json-schema.org/draft-07/schema#", + "$id": "micro:dto-1.6#", + "definitions": { + "ConstraintAbstractGroups": { + "type": "object", + "properties": { + "groups": { + "type": "string", + "default": "Default" + } + } + }, + "ConstraintAbstract": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstractGroups"}, + { + "type": "object", + "properties": { + "message": {"type": "string"} + } + } + ] + }, + "ConstraintPositive": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintAbstractComparison": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "propertyPath": {"type": "string"}, + "value": {"type": "string"} + } + } + ] + }, + "ConstraintIsNull": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintNegativeOrZero": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintSize": { + "required": [ + "min", + "max" + ], + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstractGroups"}, + { + "type": "object", + "properties": { + "min": {"type": "integer"}, + "max": {"type": "integer"}, + "messageMin": {"type": "string"}, + "messageMax": {"type": "string"} + } + } + ] + }, + "ConstraintRange": { + "allOf": [ + {"$ref": "#/definitions/ConstraintSize"}, + { + "type": "object", + "properties": { + "propertyPathMin": {"type": "string"}, + "propertyPathMax": {"type": "string"}, + "messageNotInRange": {"type": "string"} + } + } + ] + }, + "ConstraintBlank": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintDateTime": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "format": { + "type": [ + "string", + "number", + "integer", + "boolean", + "null" + ], + "default": "Y-m-d H:i:s" + } + } + } + ] + }, + "ConstraintTimeZone": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "intlCompatible": { + "type": "boolean", + "default": "false" + }, + "countryCode": { + "type": "string", + "default": "" + }, + "zone": { + "type": "integer", + "default": "2047" + } + } + } + ] + }, + "ConstraintPositiveOrZero": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintIssn": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "caseSensitive": { + "type": "boolean", + "default": "false" + }, + "requireHyphen": { + "type": "boolean", + "default": "false" + } + } + } + ] + }, + "ConstraintNegative": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintUuid": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "strict": { + "type": [ + "string", + "number", + "integer", + "boolean", + "null" + ], + "default": "true" + }, + "versions": { + "type": [ + "string", + "number", + "integer", + "boolean", + "null" + ], + "default": "1,2,3,4,5,6,7" + } + } + } + ] + }, + "ConstraintDate": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintCardScheme": { + "required": ["schemes"], + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "schemes": { + "type": [ + "string", + "number", + "integer", + "boolean", + "null" + ] + } + } + } + ] + }, + "ConstraintUrl": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "isRelative": { + "type": "boolean", + "default": "false" + } + } + } + ] + }, + "ConstraintBic": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "iban": {"type": "string"}, + "messageIban": {"type": "string"}, + "ibanPropertyPath": {"type": "string"} + } + } + ] + }, + "ConstraintIsbn": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "messageIsbn10": {"type": "string"}, + "messageIsbn13": {"type": "string"}, + "messageIsbnBoth": {"type": "string"}, + "type": { + "type": "string", + "default": "", + "enum": [ + "", + "isbn10", + "isbn13" + ] + } + } + } + ] + }, + "ConstraintIp": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "version": { + "type": "string", + "default": "4", + "enum": [ + "4", + "6", + "all", + "4_no_priv", + "6_no_priv", + "all_no_priv", + "4_no_res", + "6_no_res", + "all_no_res", + "4_public", + "6_public", + "all_public" + ] + } + } + } + ] + }, + "ConstraintTime": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintRegex": { + "required": ["pattern"], + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "pattern": {"type": "string"}, + "match": { + "type": "boolean", + "default": "true" + } + } + } + ] + }, + "ConstraintJson": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": {} + } + ] + }, + "ConstraintNotBlank": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "allowNull": { + "type": [ + "string", + "number", + "integer", + "boolean", + "null" + ], + "default": "false" + } + } + } + ] + }, + "ConstraintHostname": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "ltdRequired": { + "type": "boolean", + "default": "false" + } + } + } + ] + }, + "ConstraintEmail": { + "allOf": [ + {"$ref": "#/definitions/ConstraintAbstract"}, + { + "type": "object", + "properties": { + "mode": { + "type": "string", + "default": "html5", + "enum": [ + "html5", + "html5-allow-no-tld", + "strict" + ] + } + } + } + ] + }, + "ValidationType": { + "type": "object", + "required": ["dateOrDatetimeOrTime"], + "properties": { + "dateOrDatetimeOrTime": { + "type": "array", + "items": { + "anyOf": [ + { + "type": "object", + "properties": { + "positive": {"$ref": "#/definitions/ConstraintPositive"} + } + }, + { + "type": "object", + "properties": { + "identical_to": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "is_null": {"$ref": "#/definitions/ConstraintIsNull"} + } + }, + { + "type": "object", + "properties": { + "negative_or_zero": {"$ref": "#/definitions/ConstraintNegativeOrZero"} + } + }, + { + "type": "object", + "properties": { + "greater_than": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "range": {"$ref": "#/definitions/ConstraintRange"} + } + }, + { + "type": "object", + "properties": { + "blank": {"$ref": "#/definitions/ConstraintBlank"} + } + }, + { + "type": "object", + "properties": { + "datetime": {"$ref": "#/definitions/ConstraintDateTime"} + } + }, + { + "type": "object", + "properties": { + "time_zone": {"$ref": "#/definitions/ConstraintTimeZone"} + } + }, + { + "type": "object", + "properties": { + "positive_or_zero": {"$ref": "#/definitions/ConstraintPositiveOrZero"} + } + }, + { + "type": "object", + "properties": { + "currency": {"$ref": "#/definitions/ConstraintAbstract"} + } + }, + { + "type": "object", + "properties": { + "issn": {"$ref": "#/definitions/ConstraintIssn"} + } + }, + { + "type": "object", + "properties": { + "greater_than_or_equal": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "negative": {"$ref": "#/definitions/ConstraintNegative"} + } + }, + { + "type": "object", + "properties": { + "uuid": {"$ref": "#/definitions/ConstraintUuid"} + } + }, + { + "type": "object", + "properties": { + "date": {"$ref": "#/definitions/ConstraintDate"} + } + }, + { + "type": "object", + "properties": { + "not_equal_to": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "luhn": {"$ref": "#/definitions/ConstraintAbstract"} + } + }, + { + "type": "object", + "properties": { + "card_scheme": {"$ref": "#/definitions/ConstraintCardScheme"} + } + }, + { + "type": "object", + "properties": { + "url": {"$ref": "#/definitions/ConstraintUrl"} + } + }, + { + "type": "object", + "properties": { + "bic": {"$ref": "#/definitions/ConstraintBic"} + } + }, + { + "type": "object", + "properties": { + "less_than": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "less_than_or_equal": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "isbn": {"$ref": "#/definitions/ConstraintIsbn"} + } + }, + { + "type": "object", + "properties": { + "iban": {"$ref": "#/definitions/ConstraintAbstract"} + } + }, + { + "type": "object", + "properties": { + "isin": {"$ref": "#/definitions/ConstraintAbstract"} + } + }, + { + "type": "object", + "properties": { + "ip": {"$ref": "#/definitions/ConstraintIp"} + } + }, + { + "type": "object", + "properties": { + "equal_to": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "time": {"$ref": "#/definitions/ConstraintTime"} + } + }, + { + "type": "object", + "properties": { + "regex": {"$ref": "#/definitions/ConstraintRegex"} + } + }, + { + "type": "object", + "properties": { + "not_identical_to": {"$ref": "#/definitions/ConstraintAbstractComparison"} + } + }, + { + "type": "object", + "properties": { + "json": {"$ref": "#/definitions/ConstraintJson"} + } + }, + { + "type": "object", + "properties": { + "not_blank": {"$ref": "#/definitions/ConstraintNotBlank"} + } + }, + { + "type": "object", + "properties": { + "length": {"$ref": "#/definitions/ConstraintSize"} + } + }, + { + "type": "object", + "properties": { + "hostname": {"$ref": "#/definitions/ConstraintHostname"} + } + }, + { + "type": "object", + "properties": { + "email": {"$ref": "#/definitions/ConstraintEmail"} + } + } + ] + }, + "minItems": 1 + } + } + }, + "PropertyType": { + "type": "object", + "required": [ + "name", + "type" + ], + "properties": { + "content": { + "type": "array", + "items": { + "anyOf": [ + {"type": "string"}, + { + "type": "object", + "properties": { + "validation": {"$ref": "#/definitions/ValidationType"} + } + } + ] + } + }, + "name": {"type": "string"}, + "type": {"type": "string"}, + "description": {"type": "string"}, + "deprecated": {"type": "string"}, + "isCollection": { + "type": "boolean", + "default": "false" + }, + "required": { + "type": "boolean", + "default": "false" + } + } + }, + "ClassType": { + "type": "object", + "required": ["property"], + "properties": { + "property": { + "type": "array", + "items": {"$ref": "#/definitions/PropertyType"}, + "minItems": 1 + }, + "name": {"type": "string"}, + "description": {"type": "string"}, + "deprecated": {"type": "string"} + } + }, + "DtoType": { + "type": "object", + "required": ["clazz"], + "properties": { + "clazz": { + "type": "array", + "items": {"$ref": "#/definitions/ClassType"}, + "minItems": 1 + } + } + } + }, + "properties": { + "dto": {"$ref": "#/definitions/DtoType"}, + "validation": {"$ref": "#/definitions/ValidationType"}, + "date": {"$ref": "#/definitions/ConstraintDate"}, + "datetime": {"$ref": "#/definitions/ConstraintDateTime"}, + "time": {"$ref": "#/definitions/ConstraintTime"}, + "time_zone": {"$ref": "#/definitions/ConstraintTimeZone"}, + "is_null": {"$ref": "#/definitions/ConstraintIsNull"}, + "blank": {"$ref": "#/definitions/ConstraintBlank"}, + "not_blank": {"$ref": "#/definitions/ConstraintNotBlank"}, + "email": {"$ref": "#/definitions/ConstraintEmail"}, + "ip": {"$ref": "#/definitions/ConstraintIp"}, + "hostname": {"$ref": "#/definitions/ConstraintHostname"}, + "url": {"$ref": "#/definitions/ConstraintUrl"}, + "regex": {"$ref": "#/definitions/ConstraintRegex"}, + "length": {"$ref": "#/definitions/ConstraintSize"}, + "json": {"$ref": "#/definitions/ConstraintJson"}, + "uuid": {"$ref": "#/definitions/ConstraintUuid"}, + "positive": {"$ref": "#/definitions/ConstraintPositive"}, + "negative": {"$ref": "#/definitions/ConstraintNegative"}, + "negative_or_zero": {"$ref": "#/definitions/ConstraintNegativeOrZero"}, + "positive_or_zero": {"$ref": "#/definitions/ConstraintPositiveOrZero"}, + "equal_to": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "not_equal_to": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "greater_than": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "greater_than_or_equal": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "less_than": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "less_than_or_equal": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "identical_to": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "not_identical_to": {"$ref": "#/definitions/ConstraintAbstractComparison"}, + "range": {"$ref": "#/definitions/ConstraintRange"}, + "card_scheme": {"$ref": "#/definitions/ConstraintCardScheme"}, + "bic": {"$ref": "#/definitions/ConstraintBic"}, + "currency": {"$ref": "#/definitions/ConstraintAbstract"}, + "luhn": {"$ref": "#/definitions/ConstraintAbstract"}, + "iban": {"$ref": "#/definitions/ConstraintAbstract"}, + "isbn": {"$ref": "#/definitions/ConstraintIsbn"}, + "issn": {"$ref": "#/definitions/ConstraintIssn"}, + "isin": {"$ref": "#/definitions/ConstraintAbstract"} + } +} \ No newline at end of file diff --git a/src/Serializer/Serializer.php b/src/Serializer/Serializer.php index 9de1dc3..6bf4767 100644 --- a/src/Serializer/Serializer.php +++ b/src/Serializer/Serializer.php @@ -110,7 +110,9 @@ public function toArray(AbstractDto $abstractDto, bool $serializeEmptyValues = t { $reflectionDto = new \ReflectionClass($abstractDto); $attributesMetadataReflection = $reflectionDto->getMethod(PreparationProcessorInterface::CLASS_PROPS_META_METHOD); - $metadata = $attributesMetadataReflection->invoke($abstractDto); + $attributesMetadataReflection->setAccessible(true); + $metadata = $attributesMetadataReflection->invoke($reflectionDto); + $attributesMetadataReflection->setAccessible(false); $resultArray = []; foreach ($metadata as $propertyName => $propertyMeta) { $value = $abstractDto->offsetGet($propertyName); @@ -158,14 +160,17 @@ public function toArrayTransfer(AbstractDto $abstractDto): array { $reflectionDto = new \ReflectionClass($abstractDto); $attributesMetadataReflection = $reflectionDto->getMethod(PreparationProcessorInterface::CLASS_PROPS_META_METHOD); - + $attributesMetadataReflection->setAccessible(true); $result = $attributesMetadataReflection->invoke($abstractDto); + $attributesMetadataReflection->setAccessible(false); $resultProperties = []; foreach ($result as $propName => $meta) { $propertyConfig = []; $reflectionProperty = $reflectionDto->getProperty($propName); + $reflectionProperty->setAccessible(true); $value = $reflectionProperty->getValue($abstractDto); + $reflectionProperty->setAccessible(false); $propertyConfig[self::SECTION_TYPE] = $this->getPropertyType($value); if ($value instanceof AbstractDto) { diff --git a/src/SerializerFacade.php b/src/SerializerFacade.php index 845a86c..a5c5683 100644 --- a/src/SerializerFacade.php +++ b/src/SerializerFacade.php @@ -21,7 +21,7 @@ class SerializerFacade implements SerializerFacadeInterface /** * @param SerializerFactoryInterface $serializerFactory */ - public function __construct(private readonly SerializerFactoryInterface $serializerFactory) + public function __construct(private SerializerFactoryInterface $serializerFactory) { } diff --git a/src/Validator/Validator.php b/src/Validator/Validator.php index 25893b2..c310865 100644 --- a/src/Validator/Validator.php +++ b/src/Validator/Validator.php @@ -19,7 +19,7 @@ class Validator implements ValidatorInterface { - public function __construct(private readonly SymfonyValidator $validator) + public function __construct(private SymfonyValidator $validator) { } diff --git a/src/Validator/ValidatorFactory.php b/src/Validator/ValidatorFactory.php index dcf4791..c61c248 100644 --- a/src/Validator/ValidatorFactory.php +++ b/src/Validator/ValidatorFactory.php @@ -21,8 +21,8 @@ class ValidatorFactory implements ValidatorFactoryInterface { public function __construct( - private readonly CacheItemPoolInterface|null $cacheItemPool = null, - private readonly string|null $translationDomain = null + private CacheItemPoolInterface|null $cacheItemPool = null, + private string|null $translationDomain = null ) { } diff --git a/src/ValidatorFacade.php b/src/ValidatorFacade.php index 14f6fdd..a51d9fe 100644 --- a/src/ValidatorFacade.php +++ b/src/ValidatorFacade.php @@ -20,7 +20,7 @@ class ValidatorFacade implements ValidatorFacadeInterface { public function __construct( - private readonly ValidatorFactoryInterface $validatorFactory + private ValidatorFactoryInterface $validatorFactory ) { } diff --git a/src/Writer/WriterFilesystem.php b/src/Writer/WriterFilesystem.php index 34ce934..91f0fb7 100755 --- a/src/Writer/WriterFilesystem.php +++ b/src/Writer/WriterFilesystem.php @@ -20,8 +20,8 @@ class WriterFilesystem implements WriterInterface * @param string $namespaceGeneral */ public function __construct( - private readonly string $classFilePath, - private readonly string $namespaceGeneral, + private string $classFilePath, + private string $namespaceGeneral, ) { } diff --git a/tests/Unit/Out/Simple/SimpleUserTransfer.php b/tests/Unit/Out/Simple/SimpleUserTransfer.php index 3864604..5510e28 100644 --- a/tests/Unit/Out/Simple/SimpleUserTransfer.php +++ b/tests/Unit/Out/Simple/SimpleUserTransfer.php @@ -53,6 +53,10 @@ final class SimpleUserTransfer extends \Micro\Library\DTO\Object\AbstractDto #[\Symfony\Component\Validator\Constraints\Date(groups: ['Default'])] protected string|null $updated_at = null; + #[\Symfony\Component\Validator\Constraints\NotBlank(groups: ['Default'], allowNull: false)] + #[\Symfony\Component\Validator\Constraints\Time(groups: ['Default'])] + protected string|null $time = null; + #[\Symfony\Component\Validator\Constraints\Timezone(groups: ['Default'], countryCode: 'BY', intlCompatible: true, zone: 4096)] protected string|null $timezone = null; @@ -78,6 +82,7 @@ final class SimpleUserTransfer extends \Micro\Library\DTO\Object\AbstractDto protected string|null $isbn = null; #[\Symfony\Component\Validator\Constraints\NotBlank(groups: ['Default'], allowNull: false)] + #[\Symfony\Component\Validator\Constraints\Issn(groups: ['Default'])] protected string|null $issn = null; #[\Symfony\Component\Validator\Constraints\NotBlank(groups: ['Default'], allowNull: false)] @@ -144,6 +149,11 @@ public function getUpdatedAt(): string|null return $this->updated_at; } + public function getTime(): string|null + { + return $this->time; + } + public function getTimezone(): string|null { return $this->timezone; @@ -268,6 +278,13 @@ public function setUpdatedAt(string|null $updated_at): self return $this; } + public function setTime(string|null $time): self + { + $this->time = $time; + + return $this; + } + public function setTimezone(string|null $timezone): self { $this->timezone = $timezone; @@ -447,6 +464,16 @@ protected static function attributesMetadata(): array 'required' => false, 'actionName' => 'updatedAt', ), + 'time' => + array ( + 'type' => + array ( + 0 => 'string', + 1 => 'null', + ), + 'required' => false, + 'actionName' => 'time', + ), 'timezone' => array ( 'type' => diff --git a/tests/Unit/example.xml b/tests/Unit/example.xml index 1656a9b..38c6d9c 100755 --- a/tests/Unit/example.xml +++ b/tests/Unit/example.xml @@ -6,7 +6,7 @@ - + @@ -86,6 +86,12 @@ + + + + + diff --git a/tests/Unit/libraryTest.php b/tests/Unit/libraryTest.php index 9af1bf6..5190cf2 100644 --- a/tests/Unit/libraryTest.php +++ b/tests/Unit/libraryTest.php @@ -73,20 +73,20 @@ public function testValidateEmptyDto(): void { $validatorFacade = new ValidatorFacadeDefault(); - $this->assertEquals(11, \count($validatorFacade->validate($this->createEmptyDto()))); + $this->assertEquals(12, \count($validatorFacade->validate($this->createEmptyDto()))); } public function testSerializeEmpty(): void { $empty = $this->createEmptyDto(); - $json = '{"parent":null,"username":null,"age":null,"email":null,"ip":null,"hostname":null,"sometext":null,"url":null,"json":null,"uuid":null,"created_at":null,"updated_at":null,"timezone":null,"card_scheme":null,"bic":null,"currency":null,"iban":null,"isbn":null,"issn":null,"isin":null}'; + $json = '{"parent":null,"username":null,"age":null,"email":null,"ip":null,"hostname":null,"sometext":null,"url":null,"json":null,"uuid":null,"created_at":null,"updated_at":null,"time":null,"timezone":null,"card_scheme":null,"bic":null,"currency":null,"iban":null,"isbn":null,"issn":null,"isin":null}'; $this->testSerialize($empty, $json); } public function testSerializeValid(): void { - $json = '{"parent":{"weight":9,"height":8,"parent":null},"username":"Asisyas","age":19,"email":"test@example.com","ip":"192.168.0.1","hostname":"localhost","sometext":"azds","url":"\/\/abc","json":"{\"test\": 123}","uuid":"ffd4ff99-33ed-4a13-88cf-47e22de29dcc","created_at":"2002-08-11 20:08:01","updated_at":"2002-08-11","timezone":"Europe\/Minsk","card_scheme":"5555555555554444","bic":"MIDLGB22","currency":"USD","iban":"BY 13 NBRB 3600900000002Z00AB00","isbn":"978-0-545-01022-1","issn":"0378-5955","isin":"US0378331005"}'; + $json = '{"parent":{"weight":9,"height":8,"parent":null},"username":"Asisyas","age":19,"email":"test@example.com","ip":"192.168.0.1","hostname":"localhost","sometext":"azds","url":"\/\/abc","json":"{\"test\": 123}","uuid":"ffd4ff99-33ed-4a13-88cf-47e22de29dcc","created_at":"2002-08-11 20:08:01","updated_at":"2002-08-11","time":"14:04:01","timezone":"Europe\/Minsk","card_scheme":"5555555555554444","bic":"MIDLGB22","currency":"USD","iban":"BY 13 NBRB 3600900000002Z00AB00","isbn":"978-0-545-01022-1","issn":"0378-5955","isin":"US0378331005"}'; $this->testSerialize($this->createValidDto(), $json); } @@ -98,7 +98,7 @@ public function testIterableDto(): void $keys[] = $key; } - $this->assertEquals(20, \count($keys)); + $this->assertEquals(21, \count($keys)); $simpleUser['username'] = 'test'; $this->assertEquals('test', $simpleUser['username']); @@ -150,6 +150,7 @@ protected function createValidDto(): SimpleUserTransfer ->setHostname('localhost') ->setUsername('Asisyas') ->setSometext('azds') + ->setTime('14:04:01') ->setUrl('//abc') ->setJson('{"test": 123}') ->setUuid('ffd4ff99-33ed-4a13-88cf-47e22de29dcc')