From bb5b30480ed6254e809d08935d1a9e019b3b64f6 Mon Sep 17 00:00:00 2001 From: Jephte Clain Date: Fri, 7 Mar 2025 19:59:23 +0400 Subject: [PATCH] modifs.mineures sans commentaires --- src/schema/TODO.md | 33 ------------ src/schema/_scalar/ScalarSchema.php | 1 + src/schema/types.php | 12 ++++- src/schema/types/IType.php | 9 ++++ src/schema/types/Registry.php | 5 +- src/schema/types/_tsimple.php | 20 ++++++-- src/schema/types/tarray.php | 2 + src/schema/types/tbool.php | 4 ++ src/schema/types/tcallable.php | 4 ++ src/schema/types/tcontent.php | 2 + src/schema/types/tfloat.php | 4 ++ src/schema/types/tint.php | 4 ++ src/schema/types/tkey.php | 2 + src/schema/types/tmixed.php | 46 +++++++++++++++++ src/schema/types/tpkey.php | 2 + src/schema/types/traw.php | 16 ++++++ src/schema/types/trawstring.php | 2 + src/schema/types/tstring.php | 2 + src/schema/types/ttext.php | 2 + tests/wip/schema/_scalar/ScalarValueTest.php | 53 ++++++++++++++++++++ 20 files changed, 186 insertions(+), 39 deletions(-) create mode 100644 src/schema/types/tmixed.php create mode 100644 src/schema/types/traw.php diff --git a/src/schema/TODO.md b/src/schema/TODO.md index 62def1a..ca79d50 100644 --- a/src/schema/TODO.md +++ b/src/schema/TODO.md @@ -1,6 +1,5 @@ # nulib\schema -* tester type===null --> implémenter traw et tmixed * ScalarSchema::from_property() * dans AssocSchema, support `[key_prefix]` qui permet de spécifier un préfixe @@ -32,38 +31,6 @@ $wrapper->reset($value); # $value vaut ["x_a" => "5", "x_b" => 10]; ~~~ -* implémenter l'instanciation de types avec des paramètres particuliers. *si* - des paramètres sont fournis, le type est instancié avec la signature - `IType($typeDefinition, $schemaDefinition)` e.g - ~~~php - const SCHEMA = ["type", default, "required" => true]; - # le type est instancié comme suit: - $type = new ttype(); - - const SCHEMA = [[["type", ...]], default, "required" => true]; - // ou - const SCHEMA = [["type" => [...]], default, "required" => true]; - # le type est instancié comme suit: - # le tableau peut être une liste ou associatif, c'est au type de décider ce - # qu'il en fait - $type = new ttype(["type", ...], SCHEMA); - ~~~ -* ajouter à IType les méthodes getName() pour le nom officiel du type, - getAliases() pour les alias supportés, et getClass() pour la définition de la - classe dans les méthodes et propriétés - getName() et getAliases() sont juste pour information, ils ne sont pas utilisés - lors de la résolution du type effectif. -* si cela a du sens, dans AssocSchema, n'instancier les schémas de chaque clé qu'à la demande. - l'idée est de ne pas perdre du temps à instancier un schéma qui ne serait pas utilisé - - on pourrait avoir d'une manière générale quelque chose comme: - ~~~ - Schema::ensure(&$schema, ?array $def=null, $defKey=null): Schema; - ~~~ - * si $schema est une instance de Schema, la retourner - * si c'est un array, c'est une définition et il faut la remplacer par l'instance de Schema correspondant - * sinon, prendre $def comme définition - $key est la clé si $schema est dans un autre schema * actuellement, pour un schéma associatif, si on normalise un tableau séquentiel, chaque valeur correspond à la clé de même rang, eg. pour un schéma ~~~php diff --git a/src/schema/_scalar/ScalarSchema.php b/src/schema/_scalar/ScalarSchema.php index 947a5e7..3d6594d 100644 --- a/src/schema/_scalar/ScalarSchema.php +++ b/src/schema/_scalar/ScalarSchema.php @@ -115,6 +115,7 @@ class ScalarSchema extends Schema { $deftype = explode("|", $deftype); } foreach ($deftype as $type) { + if ($type !== null) $type = trim($type); if ($type === null || $type === "null") { $nullable = true; continue; diff --git a/src/schema/types.php b/src/schema/types.php index c69ccba..e3489c5 100644 --- a/src/schema/types.php +++ b/src/schema/types.php @@ -6,8 +6,13 @@ use nur\sery\wip\schema\types\Registry; use nur\sery\wip\schema\types\tarray; use nur\sery\wip\schema\types\tbool; use nur\sery\wip\schema\types\tcallable; +use nur\sery\wip\schema\types\tcontent; use nur\sery\wip\schema\types\tfloat; use nur\sery\wip\schema\types\tint; +use nur\sery\wip\schema\types\tkey; +use nur\sery\wip\schema\types\tmixed; +use nur\sery\wip\schema\types\tpkey; +use nur\sery\wip\schema\types\traw; use nur\sery\wip\schema\types\trawstring; use nur\sery\wip\schema\types\tstring; use nur\sery\wip\schema\types\ttext; @@ -26,7 +31,7 @@ class types { return self::$registry; } - static function get(bool $nullable, string $name, ?array $params=null, ?array $definition=null): IType { + static function get(bool $nullable, ?string $name, ?array $params=null, ?array $definition=null): IType { return self::registry()->get($nullable, $name, $params, $definition); } @@ -38,4 +43,9 @@ class types { static function float(bool $nullable=true): tfloat { return self::get($nullable, "float"); } static function array(bool $nullable=true): tarray { return self::get($nullable, "array"); } static function callable(bool $nullable=true): tcallable { return self::get($nullable, "callable"); } + static function raw(bool $nullable=true): traw { return self::get($nullable, "raw"); } + static function mixed(bool $nullable=true): tmixed { return self::get($nullable, "mixed"); } + static function key(bool $nullable=true): tkey { return self::get($nullable, "key"); } + static function pkey(bool $nullable=true): tpkey { return self::get($nullable, "pkey"); } + static function content(bool $nullable=true): tcontent { return self::get($nullable, "content"); } } diff --git a/src/schema/types/IType.php b/src/schema/types/IType.php index f7fd5cc..a245fd7 100644 --- a/src/schema/types/IType.php +++ b/src/schema/types/IType.php @@ -10,6 +10,15 @@ use nur\sery\wip\schema\Schema; * Interface IType: un type de données */ interface IType { + /** + * obtenir, pour information, le nom officiel de ce type, utilisable dans une + * définition de schéma + */ + function getName(): string; + + /** obtenir la liste des aliases valides pour ce type */ + function getAliases(): array; + /** * @return string la classe des objets gérés par ce format: le type attendu * par {@link format()} et le type retourné par {@link verifix()} diff --git a/src/schema/types/Registry.php b/src/schema/types/Registry.php index ac64560..5c08c92 100644 --- a/src/schema/types/Registry.php +++ b/src/schema/types/Registry.php @@ -16,6 +16,8 @@ class Registry { "array" => tarray::class, "callable" => tcallable::class, # types spéciaux + "raw" => tmixed::class, + "mixed" => tmixed::class, "key" => tkey::class, "pkey" => tpkey::class, "content" => tcontent::class, @@ -28,7 +30,8 @@ class Registry { /** @var IType[] */ protected $types; - function get(bool $nullable, string $name, ?array $params=null, ?array $definition=null): IType { + function get(bool $nullable, ?string $name, ?array $params=null, ?array $definition=null): IType { + $name ??= "raw"; $class = self::TYPES[$name]; $params = cl::merge($class::get_params_from_definition($definition), $params); if ($params !== null) { diff --git a/src/schema/types/_tsimple.php b/src/schema/types/_tsimple.php index 5f9ce7e..ac0aa36 100644 --- a/src/schema/types/_tsimple.php +++ b/src/schema/types/_tsimple.php @@ -7,6 +7,10 @@ use nur\sery\wip\schema\input\Input; use nur\str; abstract class _tsimple implements IType { + const NAME = null; + + const ALIASES = []; + static function get_params_from_definition(?array $definition): ?array { return null; } @@ -20,6 +24,14 @@ abstract class _tsimple implements IType { protected ?array $params; + function getName(): string { + return static::NAME; + } + + function getAliases(): array { + return static::ALIASES; + } + function getPhpType(bool $allowNullable=true): ?string { $phpType = $this->getClass(); if ($phpType === "mixed") return null; @@ -27,6 +39,10 @@ abstract class _tsimple implements IType { return $phpType; } + function is2States(): bool { + return false; + } + function get2States(): array { throw StateException::not_implemented(); } @@ -51,10 +67,6 @@ abstract class _tsimple implements IType { return $value; } - function is2States(): bool { - return false; - } - ############################################################################# function getGetterName(string $name): string { diff --git a/src/schema/types/tarray.php b/src/schema/types/tarray.php index abf7092..aba2aab 100644 --- a/src/schema/types/tarray.php +++ b/src/schema/types/tarray.php @@ -9,6 +9,8 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; class tarray extends _tstring { + const NAME = "array"; + const SPLIT_PATTERN = '/\s+/'; const FORMAT = " "; diff --git a/src/schema/types/tbool.php b/src/schema/types/tbool.php index 39c17e1..50fa206 100644 --- a/src/schema/types/tbool.php +++ b/src/schema/types/tbool.php @@ -11,6 +11,10 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; class tbool extends _tformatable { + const NAME = "bool"; + + const ALIASES = ["boolean"]; + /** liste de valeurs chaines à considérer comme 'OUI' */ const YES_VALUES = [ "true", "vrai", "yes", "oui", diff --git a/src/schema/types/tcallable.php b/src/schema/types/tcallable.php index a36032c..f9e95d6 100644 --- a/src/schema/types/tcallable.php +++ b/src/schema/types/tcallable.php @@ -10,6 +10,10 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; class tcallable extends _tsimple { + const NAME = "callable"; + + const ALIASES = ["func", "function"]; + static function ensure_callable(&$callable): void { $callable = func::ensure($callable); } diff --git a/src/schema/types/tcontent.php b/src/schema/types/tcontent.php index aff7d17..1dfe455 100644 --- a/src/schema/types/tcontent.php +++ b/src/schema/types/tcontent.php @@ -8,6 +8,8 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; abstract class tcontent extends _tunion { + const NAME = "content"; + static function ensure_content(&$content): void { if ($content === null || $content === false) $content = []; elseif (!is_string($content) && !is_array($content)) $content = strval($content); diff --git a/src/schema/types/tfloat.php b/src/schema/types/tfloat.php index 486187e..db67257 100644 --- a/src/schema/types/tfloat.php +++ b/src/schema/types/tfloat.php @@ -8,6 +8,10 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; class tfloat extends _tformatable { + const NAME = "float"; + + const ALIASES = ["flt", "double", "dbl"]; + static function ensure_float(&$float): void { if (!is_float($float)) $float = floatval($float); } diff --git a/src/schema/types/tint.php b/src/schema/types/tint.php index 33ae3ac..5673ab5 100644 --- a/src/schema/types/tint.php +++ b/src/schema/types/tint.php @@ -8,6 +8,10 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; class tint extends _tformatable { + const NAME = "int"; + + const ALIASES = ["integer"]; + static function ensure_int(&$int): void { if (!is_int($int)) $int = intval($int); } diff --git a/src/schema/types/tkey.php b/src/schema/types/tkey.php index 102beee..0e00cb3 100644 --- a/src/schema/types/tkey.php +++ b/src/schema/types/tkey.php @@ -7,6 +7,8 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; class tkey extends _tunion { + const NAME = "key"; + static function ensure_key(&$key): void { if ($key === null) $key = ""; elseif ($key === false) $key = 0; diff --git a/src/schema/types/tmixed.php b/src/schema/types/tmixed.php new file mode 100644 index 0000000..5f387c6 --- /dev/null +++ b/src/schema/types/tmixed.php @@ -0,0 +1,46 @@ +isAvailable($valueKey); + } + + public function isNull($value): bool { + return $value === null; + } + + function isValid($value, ?bool &$normalized=null): bool { + $normalized = true; + return true; + } + + function parse(string $value) { + return $value; + } + + /** + * @var ScalarResult $result + * @var ScalarSchema $schema + */ + function verifix(&$value, Result $result, Schema $schema): bool { + $result->setNormalized(); + return false; + } + + function format($value, $format=null): string { + return var_export($value, true); + } +} diff --git a/src/schema/types/tpkey.php b/src/schema/types/tpkey.php index 1606087..14f2e01 100644 --- a/src/schema/types/tpkey.php +++ b/src/schema/types/tpkey.php @@ -7,6 +7,8 @@ use nur\sery\wip\schema\Result; use nur\sery\wip\schema\Schema; class tpkey extends _tunion { + const NAME = "pkey"; + static function ensure_pkey(&$pkey): void { if ($pkey === null) $pkey = ""; elseif ($pkey === false) $pkey = 0; diff --git a/src/schema/types/traw.php b/src/schema/types/traw.php new file mode 100644 index 0000000..b187b3f --- /dev/null +++ b/src/schema/types/traw.php @@ -0,0 +1,16 @@ +checkVerifix($schema, false, false, false, true, true, true, true); + $this->checkVerifix($schema, false, true, false, true, true, true, true); + + $this->checkVerifix($schema, null, false, null, true, true, true, true); + $this->checkVerifix($schema, null, true, null, true, true, true, true); + + $obj = new stdClass(); + $this->checkVerifix($schema, $obj, false, $obj, true, true, true, true); + $this->checkVerifix($schema, $obj, true, $obj, true, true, true, true); + + $schema = new ScalarSchema("raw"); + + $this->checkVerifix($schema, false, false, false, true, true, true, true); + $this->checkVerifix($schema, false, true, false, true, true, true, true); + + $this->checkVerifix($schema, null, false, null, true, true, true, true); + $this->checkVerifix($schema, null, true, null, true, true, true, true); + + $obj = new stdClass(); + $this->checkVerifix($schema, $obj, false, $obj, true, true, true, true); + $this->checkVerifix($schema, $obj, true, $obj, true, true, true, true); + } + + function testMixed() { + $schema = new ScalarSchema("mixed"); + + $this->checkVerifix($schema, false, false, false, true, true, true, true); + $this->checkVerifix($schema, false, true, false, true, true, true, true); + + $this->checkVerifix($schema, null, false, null, true, true, false, false); + $this->checkException($schema, null, true, ValueException::class); + + $obj = new stdClass(); + $this->checkVerifix($schema, $obj, false, $obj, true, true, true, true); + $this->checkVerifix($schema, $obj, true, $obj, true, true, true, true); + + $schema = new ScalarSchema("?mixed"); + + $this->checkVerifix($schema, false, false, false, true, true, true, true); + $this->checkVerifix($schema, false, true, false, true, true, true, true); + + $this->checkVerifix($schema, null, false, null, true, true, true, true); + $this->checkVerifix($schema, null, true, null, true, true, true, true); + + $obj = new stdClass(); + $this->checkVerifix($schema, $obj, false, $obj, true, true, true, true); + $this->checkVerifix($schema, $obj, true, $obj, true, true, true, true); + } + function testRawstring() { $schema = new ScalarSchema("rawstring");