From e30413dc02261b52d02fc84150de5afcf01a3db2 Mon Sep 17 00:00:00 2001 From: Maximilian Haye Date: Tue, 22 Oct 2024 19:50:38 +0200 Subject: [PATCH] refactor: remove array_converter::configure and related methods --- classes/array_converter/array_converter.php | 60 +++---------- classes/array_converter/converter_config.php | 94 +------------------- 2 files changed, 15 insertions(+), 139 deletions(-) diff --git a/classes/array_converter/array_converter.php b/classes/array_converter/array_converter.php index 5607f89c..c2dcfbe6 100644 --- a/classes/array_converter/array_converter.php +++ b/classes/array_converter/array_converter.php @@ -36,25 +36,6 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ class array_converter { - /** @var callable[] associative array of class names to configuration hook functions for those classes */ - private static array $hooks = []; - - /** - * Customizes the way in which classes and their subclasses are converted from and to arrays. - * - * In the case of traits, the configuration will be applied to any classes using them. - * Configuration is done in hook functions. When converting to or from a class instance, all hook function of it and - * its superclasses and used traits are applied to a single {@see converter_config} instance. - * - * @param string $class class or trait for whom array conversion should be customized - * @param callable $hook configuration function which takes a {@see converter_config} instance as its argument, - * adds its own configuration to it, and returning nothing - * @see converter_config for the available options - */ - public static function configure(string $class, callable $hook): void { - self::$hooks[$class] = $hook; - } - /** * Recursively converts an array to an instance of the given class. * @@ -323,46 +304,27 @@ private static function convert_to_required_type(?ReflectionNamedType $type, con } /** - * Calls all configuration hooks for the given class. + * Inspects the attributes on the given class, superclasses and traits and updates the given config. * - * @param ReflectionClass $class + * @param ReflectionClass $reflect * @param converter_config|null $config an existing config to add to or null, in which case a new one will be * created * @return converter_config - * @see self::configure() */ - private static function get_config_for(ReflectionClass $class, ?converter_config $config = null): converter_config { + private static function get_config_for(ReflectionClass $reflect, ?converter_config $config = null): converter_config { if (!$config) { $config = new converter_config(); } - $parent = $class->getParentClass(); + $parent = $reflect->getParentClass(); if ($parent) { $config = self::get_config_for($parent, $config); } - foreach ($class->getTraits() as $trait) { + foreach ($reflect->getTraits() as $trait) { $config = self::get_config_for($trait, $config); } - self::configure_from_attributes($class, $config); - - $hook = self::$hooks[$class->getName()] ?? null; - if ($hook) { - $hook($config); - } - - return $config; - } - - /** - * Inspects the attributes on the given class and updates the given config. - * - * @param ReflectionClass $reflect - * @param converter_config $config - * @return void - */ - private static function configure_from_attributes(ReflectionClass $reflect, converter_config $config): void { $polyattrs = $reflect->getAttributes(array_polymorphic::class); foreach ($polyattrs as $attr) { /** @var array_polymorphic $instance */ @@ -378,14 +340,20 @@ private static function configure_from_attributes(ReflectionClass $reflect, conv } foreach ($property->getAttributes(array_key::class) as $attr) { - $config->rename($property->getName(), $attr->newInstance()->key); + $config->renames[$property->getName()] = $attr->newInstance()->key; } foreach ($property->getAttributes(array_alias::class) as $attr) { - $config->alias($property->getName(), $attr->newInstance()->alias); + if (isset($config->aliases[$property->getName()])) { + $config->aliases[$property->getName()][] = $attr->newInstance()->alias; + } else { + $config->aliases[$property->getName()] = [$attr->newInstance()->alias]; + } } foreach ($property->getAttributes(array_element_class::class) as $attr) { - $config->array_elements($property->getName(), $attr->newInstance()->class); + $config->elementclasses[$property->getName()] = $attr->newInstance()->class; } } + + return $config; } } diff --git a/classes/array_converter/converter_config.php b/classes/array_converter/converter_config.php index 9bf585e2..fb795b5c 100644 --- a/classes/array_converter/converter_config.php +++ b/classes/array_converter/converter_config.php @@ -17,9 +17,7 @@ namespace qtype_questionpy\array_converter; /** - * Allows customization of conversions by {@see array_converter}. - * - * @see array_converter::configure() + * Holds customization of {@see array_converter}. * * @package qtype_questionpy * @author Maximilian Haye @@ -41,94 +39,4 @@ class converter_config { /** @var string[] mapping from property names to the classes of their array elements */ public array $elementclasses = []; - - /** - * Changes the name under which the value of a property appears in arrays. - * - * Renames differ from {@see self::alias() aliases} in that they apply to both serialization and deserialization, - * and replace the original property name. - * - * @param string $propname property whose array key to rename - * @param string $arraykey new array key - * @return $this for chaining - */ - public function rename(string $propname, string $arraykey): self { - $this->renames[$propname] = $arraykey; - return $this; - } - - /** - * Adds an alias for the given property. - * - * Aliases differ from {@see self::rename() renames} in that they only apply to deserialization, and are tried in - * addition to the original property name (or rename, if any). - * - * @param string $propname property name for which the alias should be tried - * @param string $alias new alias - * @return $this for chaining - */ - public function alias(string $propname, string $alias): self { - if (isset($this->aliases[$propname])) { - $this->aliases[$propname][] = $alias; - } else { - $this->aliases[$propname] = [$alias]; - } - return $this; - } - - /** - * Enables polymorphic deserialization for this class, using the given key as a discriminator. - * - * The value of the given array key will determine the actual class ('variant') used for deserialization. Variants - * are registered using {@see self::variant()}. - * - * @param string $discriminator key of the array entry determining the concrete class to deserialize to. - * @return $this for chaining - */ - public function discriminate_by(string $discriminator): self { - $this->discriminator = $discriminator; - return $this; - } - - /** - * Adds a variant for polymorphic deserialization. - * - * @param string $discriminator the discriminator value associated with the concrete class - * @param string $classname the concrete class to convert to when the discriminator is encountered - * @return $this for chaining - * @see self::discriminate_by() - * @see self::fallback_variant() - */ - public function variant(string $discriminator, string $classname): self { - $this->variants[$discriminator] = $classname; - return $this; - } - - /** - * Sets the fallback variant for polymorphic deserialization. - * - * When a discriminator is encountered which isn't {@see variant registered}, the default behaviour is to throw an - * exception. Instead, you can register a fallback class to be used. A debugging message will still be emitted. - * - * @param string $classname the concrete class to convert to when an unknown discriminator is encountered - * @return $this for chaining - * @see self::discriminate_by() - * @see self::variant() - */ - public function fallback_variant(string $classname): self { - $this->fallbackvariant = $classname; - return $this; - } - - /** - * For an array-typed property with the given name, sets the class to use for the deserialization of its elements. - * - * @param string $propname property name - * @param string $class class to deserialize to - * @return $this for chaining - */ - public function array_elements(string $propname, string $class): self { - $this->elementclasses[$propname] = $class; - return $this; - } }