8000 [JsonEncoder] Replace normalizers by value transformers · Spomky/symfony@ced7191 · GitHub
[go: up one dir, main page]

Skip to content

Commit ced7191

Browse files
committed
[JsonEncoder] Replace normalizers by value transformers
1 parent 04551ad commit ced7191

File tree

118 files changed

+837
-885
lines changed
  • Fixtures
  • Mapping
  • ValueTransformer
  • ValueTransformer
  • Some content is hidden

    Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

    118 files changed

    +837
    -885
    lines changed

    src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Compiler/UnusedTagsPass.php

    Lines changed: 1 addition & 2 deletions
    Original file line numberDiff line numberDiff line change
    @@ -53,8 +53,7 @@ class UnusedTagsPass implements CompilerPassInterface
    5353
    'form.type_guesser',
    5454
    'html_sanitizer',
    5555
    'http_client.client',
    56-
    'json_encoder.denormalizer',
    57-
    'json_encoder.normalizer',
    56+
    'json_encoder.value_transformer',
    5857
    'kernel.cache_clearer',
    5958
    'kernel.cache_warmer',
    6059
    'kernel.event_listener',

    src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php

    Lines changed: 3 additions & 6 deletions
    Original file line numberDiff line numberDiff line change
    @@ -101,11 +101,10 @@
    101101
    use Symfony\Component\HttpKernel\DependencyInjection\Extension;
    102102
    use Symfony\Component\HttpKernel\Log\DebugLoggerConfigurator;
    103103
    use Symfony\Component\JsonEncoder\Attribute\JsonEncodable;
    104-
    use Symfony\Component\JsonEncoder\Decode\Denormalizer\DenormalizerInterface as JsonEncoderDenormalizerInterface;
    105104
    use Symfony\Component\JsonEncoder\DecoderInterface as JsonEncoderDecoderInterface;
    106-
    use Symfony\Component\JsonEncoder\Encode\Normalizer\NormalizerInterface as JsonEncoderNormalizerInterface;
    107105
    use Symfony\Component\JsonEncoder\EncoderInterface as JsonEncoderEncoderInterface;
    108106
    use Symfony\Component\JsonEncoder\JsonEncoder;
    107+
    use Symfony\Component\JsonEncoder\ValueTransformer\ValueTransformerInterface;
    109108
    use Symfony\Component\Lock\LockFactory;
    110109
    use Symfony\Component\Lock\LockInterface;
    111110
    use Symfony\Component\Lock\PersistingStoreInterface;
    @@ -2027,10 +2026,8 @@ private function registerJsonEncoderConfiguration(array $config, ContainerBuilde
    20272026
    throw new LogicException('JsonEncoder support cannot be enabled as the JsonEncoder component is not installed. Try running "composer require symfony/json-encoder".');
    20282027
    }
    20292028

    2030-
    $container->registerForAutoconfiguration(JsonEncoderNormalizerInterface::class)
    2031-
    ->addTag('json_encoder.normalizer');
    2032-
    $container->registerForAutoconfiguration(JsonEncoderDenormalizerInterface::class)
    2033-
    ->addTag('json_encoder.denormalizer');
    2029+
    $container->registerForAutoconfiguration(ValueTransformerInterface::class)
    2030+
    ->addTag('json_encoder.value_transformer');
    20342031

    20352032
    $loader->load('json_encoder.php');
    20362033

    src/Symfony/Bundle/FrameworkBundle/Resources/config/json_encoder.php

    Lines changed: 12 additions & 19 deletions
    Original file line numberDiff line numberDiff line change
    @@ -13,8 +13,6 @@
    1313

    1414
    use Symfony\Component\JsonEncoder\CacheWarmer\EncoderDecoderCacheWarmer;
    1515
    use Symfony\Component\JsonEncoder\CacheWarmer\LazyGhostCacheWarmer;
    16-
    use Symfony\Component\JsonEncoder\Decode\Denormalizer\DateTimeDenormalizer;
    17-
    use Symfony\Component\JsonEncoder\Encode\Normalizer\DateTimeNormalizer;
    1816
    use Symfony\Component\JsonEncoder\JsonDecoder;
    1917
    use Symfony\Component\JsonEncoder\JsonEncoder;
    2018
    use Symfony\Component\JsonEncoder\Mapping\Decode\AttributePropertyMetadataLoader as DecodeAttributePropertyMetadataLoader;
    @@ -23,19 +21,21 @@
    2321
    use Symfony\Component\JsonEncoder\Mapping\Encode\DateTimeTypePropertyMetadataLoader as EncodeDateTimeTypePropertyMetadataLoader;
    2422
    use Symfony\Component\JsonEncoder\Mapping\GenericTypePropertyMetadataLoader;
    2523
    use Symfony\Component\JsonEncoder\Mapping\PropertyMetadataLoader;
    24+
    use Symfony\Component\JsonEncoder\ValueTransformer\DateTimeToStringValueTransformer;
    25+
    use Symfony\Component\JsonEncoder\ValueTransformer\StringToDateTimeValueTransformer;
    2626

    2727
    return static function (ContainerConfigurator $container) {
    2828
    $container->services()
    2929
    // encoder/decoder
    3030
    ->set('json_encoder.encoder', JsonEncoder::class)
    3131
    ->args([
    32-
    tagged_locator('json_encoder.normalizer'),
    32+
    tagged_locator('json_encoder.value_transformer'),
    3333
    service('json_encoder.encode.property_metadata_loader'),
    3434
    param('.json_encoder.encoders_dir'),
    3535
    ])
    3636
    ->set('json_encoder.decoder', JsonDecoder::class)
    3737
    ->args([
    38-
    tagged_locator('json_encoder.denormalizer'),
    38+
    tagged_locator('json_encoder.value_transformer'),
    3939
    service('json_encoder.decode.property_metadata_loader'),
    4040
    param('.json_encoder.decoders_dir'),
    4141
    param('.json_encoder.lazy_ghosts_dir'),
    @@ -63,7 +63,7 @@
    6363
    ->decorate('json_encoder.encode.property_metadata_loader')
    6464
    ->args([
    6565
    service('.inner'),
    66-
    tagged_locator('json_encoder.normalizer'),
    66+
    tagged_locator('json_encoder.value_transformer'),
    6767
    service('type_info.resolver'),
    6868
    ])
    6969

    @@ -86,23 +86,16 @@
    8686
    ->decorate('json_encoder.decode.property_metadata_loader')
    8787
    ->args([
    8888
    service('.inner'),
    89-
    tagged_locator('json_encoder.normalizer'),
    89+
    tagged_locator('json_encoder.value_transformer'),
    9090
    service('type_info.resolver'),
    9191
    ])
    9292

    93-
    // normalizers/denormalizers
    94-
    ->set('json_encoder.normalizer.date_time', DateTimeNormalizer::class)
    95-
    ->tag('json_encoder.normalizer')
    96-
    ->set('json_encoder.denormalizer.date_time', DateTimeDenormalizer::class)
    97-
    ->args([
    98-
    false,
    99-
    ])
    100-
    ->tag('json_encoder.denormalizer')
    101-
    ->set('json_encoder.denormalizer.date_time_immutable', DateTimeDenormalizer::class)
    102-
    ->args([
    103-
    true,
    104-
    ])
    105-
    ->tag('json_encoder.denormalizer')
    93+
    // value transformers
    94+
    ->set('json_encoder.value_transformer.date_time_to_string', DateTimeToStringValueTransformer::class)
    95+
    ->tag('json_encoder.value_transformer')
    96+
    97+
    ->set('json_encoder.value_transformer.string_to_date_time', StringToDateTimeValueTransformer::class)
    98+
    ->tag('json_encoder.value_transformer')
    10699

    107100
    // cache
    108101
    ->set('.json_encoder.cache_warmer.encoder_decoder', EncoderDecoderCacheWarmer::class)

    src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/JsonEncoder/Dto/Dummy.php

    Lines changed: 5 additions & 7 deletions
    Original file line numberDiff line numberDiff line change
    @@ -11,11 +11,11 @@
    1111

    1212
    namespace Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\Dto;
    1313

    14-
    use Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\RangeNormalizer;
    15-
    use Symfony\Component\JsonEncoder\Attribute\Denormalizer;
    14+
    use Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\RangeToStringValueTransformer;
    15+
    use Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\StringToRangeValueTransformer;
    1616
    use Symfony\Component\JsonEncoder\Attribute\EncodedName;
    1717
    use Symfony\Component\JsonEncoder\Attribute\JsonEncodable;
    18-
    use Symfony\Component\JsonEncoder\Attribute\Normalizer;
    18+
    use Symfony\Component\JsonEncoder\Attribute\ValueTransformer;
    1919

    2020
    /**
    2121
    * @author Mathias Arlaud <mathias.arlaud@gmail.com>
    @@ -24,11 +24,9 @@
    2424
    class Dummy
    2525
    {
    2626
    #[EncodedName('@name')]
    27-
    #[Normalizer('strtoupper')]
    28-
    #[Denormalizer('strtolower')]
    27+
    #[ValueTransformer(toJsonValue: 'strtoupper', toNativeValue: 'strtolower')]
    2928
    public string $name = 'dummy';
    3029

    31-
    #[Normalizer(RangeNormalizer::class)]
    32-
    #[Denormalizer(RangeNormalizer::class)]
    30+
    #[ValueTransformer(toJsonValue: RangeToStringValueTransformer::class, toNativeValue: StringToRangeValueTransformer::class)]
    3331
    public array $range = [10, 20];
    3432
    }
    Lines changed: 32 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,32 @@
    1+
    <?php
    2+
    3+
    /*
    4+
    * This file is part of the Symfony package.
    5+
    *
    6+
    * (c) Fabien Potencier <fabien@symfony.com>
    7+
    *
    8+
    * For the full copyright and license information, please view the LICENSE
    9+
    * file that was distributed with this source code.
    10+
    */
    11+
    12+
    namespace Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder;
    13+
    14+
    use Symfony\Component\JsonEncoder\ValueTransformer\ValueTransformerInterface;
    15+
    use Symfony\Component\TypeInfo\Type;
    16+
    use Symfony\Component\TypeInfo\Type\BuiltinType;
    17+
    18+
    /**
    19+
    * @author Mathias Arlaud <mathias.arlaud@gmail.com>
    20+
    */
    21+
    class RangeToStringValueTransformer implements ValueTransformerInterface
    22+
    {
    23+
    public function transform(mixed $value, array $options = []): string
    24+
    {
    25+
    return $value[0].'..'.$value[1];
    26+
    }
    27+
    28+
    public static function getJsonValueType(): BuiltinType
    29+
    {
    30+
    return Type::string();
    31+
    }
    32+
    }

    src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/JsonEncoder/RangeNormalizer.php renamed to src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/JsonEncoder/StringToRangeValueTransformer.php

    Lines changed: 5 additions & 11 deletions
    Original file line numberDiff line numberDiff line change
    @@ -11,27 +11,21 @@
    1111

    1212
    namespace Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder;
    1313

    14-
    use Symfony\Component\JsonEncoder\Decode\Denormalizer\DenormalizerInterface;
    15-
    use Symfony\Component\JsonEncoder\Encode\Normalizer\NormalizerInterface;
    14+
    use Symfony\Component\JsonEncoder\ValueTransformer\ValueTransformerInterface;
    1615
    use Symfony\Component\TypeInfo\Type;
    1716
    use Symfony\Component\TypeInfo\Type\BuiltinType;
    1817

    1918
    /**
    2019
    * @author Mathias Arlaud <mathias.arlaud@gmail.com>
    2120
    */
    22-
    class RangeNormalizer implements NormalizerInterface, DenormalizerInterface
    21+
    class StringToRangeValueTransformer implements ValueTransformerInterface
    2322
    {
    24-
    public function normalize(mixed $denormalized, array $options = []): string
    23+
    public function transform(mixed $value, array $options = []): array
    2524
    {
    26-
    return $denormalized[0].'..'.$denormalized[1];
    25+
    return array_map(static fn (string $v): int => (int) $v, explode('..', $value));
    2726
    }
    2827

    29-
    public function denormalize(mixed $normalized, array $options = []): array
    30-
    {
    31-
    return array_map(static fn (string $v): int => (int) $v, explode('..', $normalized));
    32-
    }
    33-
    34-
    public static function getNormalizedType(): BuiltinType
    28+
    public static function getJsonValueType(): BuiltinType
    3529
    {
    3630
    return Type::string();
    3731
    }

    src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/JsonEncoder/config.yml

    Lines changed: 2 additions & 1 deletion
    Original file line numberDiff line numberDiff line change
    @@ -23,4 +23,5 @@ services:
    2323
    public: true
    2424

    2525
    Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\Dto\Dummy: ~
    26-
    Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\RangeNormalizer: ~
    26+
    Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\StringToRangeValueTransformer: ~
    27+
    Symfony\Bundle\FrameworkBundle\Tests\Functional\app\JsonEncoder\RangeToStringValueTransformer: ~

    src/Symfony/Component/JsonEncoder/Attribute/Denormalizer.php

    Lines changed: 0 additions & 43 deletions
    This file was deleted.

    src/Symfony/Component/JsonEncoder/Attribute/Normalizer.php

    Lines changed: 0 additions & 43 deletions
    This file was deleted.
    Lines changed: 63 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,63 @@
    1+
    <?php
    2+
    3+
    /*
    4+
    * This file is part of the Symfony package.
    5+
    *
    6+
    * (c) Fabien Potencier <fabien@symfony.com>
    7+
    *
    8+
    * For the full copyright and license information, please view the LICENSE
    9+
    * file that was distributed with this source code.
    10+
    */
    11+
    12+
    namespace Symfony\Component\JsonEncoder\Attribute;
    13+
    14+
    use Symfony\Component\JsonEncoder\Exception\LogicException;
    15+
    16+
    /**
    17+
    * Defines a callable or a {@see \Symfony\Component\JsonEncoder\ValueTransformer\ValueTransformerInterface} service id
    18+
    * that will be used to transform the property data during encoding and decoding.
    19+
    *
    20+
    * @author Mathias Arlaud <mathias.arlaud@gmail.com>
    21+
    *
    22+
    * @experimental
    23+
    */
    24+
    #[\Attribute(\Attribute::TARGET_PROPERTY)]
    25+
    class ValueTransformer
    26+
    {
    27+
    private \Closure|string|null $toNativeValue;
    28+
    private \Closure|string|null $toJsonValue;
    29+
    30+
    /**
    31+
    * @param (callable(mixed, array<string, mixed>=): mixed)|string|null $toNativeValue
    32+
    * @param (callable(mixed, array<string, mixed>=): mixed)|string|null $toJsonValue
    33+
    */
    34+
    public function __construct(
    35+
    callable|string|null $toNativeValue = null,
    36+
    callable|string|null $toJsonValue = null,
    37+
    ) {
    38+
    if (!$toNativeValue && !$toJsonValue) {
    39+
    throw new LogicException('#[ValueTransformer] attribute must declare either $toNativeValue or $toJsonValue.');
    40+
    }
    41+
    42+
    if (\is_callable($toNativeValue)) {
    43+
    $toNativeValue = $toNativeValue(...);
    44+
    }
    45+
    46+
    if (\is_callable($toJsonValue)) {
    47+
    $toJsonValue = $toJsonValue(...);
    48+
    }
    49+
    50+
    $this->toNativeValue = $toNativeValue;
    51+
    $this->toJsonValue = $toJsonValue;
    52+
    }
    53+
    54+
    public function getToNativeValueTransformer(): string|\Closure|null
    55+
    {
    56+
    return $this->toNativeValue;
    57+
    }
    58+
    59+
    public function getToJsonValueTransformer(): string|\Closure|null
    60+
    {
    61+
    return $this->toJsonValue;
    62+
    }
    63+
    }

    0 commit comments

    Comments
     (0)
    0