From a7cc9f079f51d15af7607aef4329666af6f5d080 Mon Sep 17 00:00:00 2001 From: Mark Scherer Date: Thu, 21 Sep 2023 11:06:16 +0200 Subject: [PATCH] Allow global key type config. (#55) --- config/app.default.php | 1 + src/Dto/AbstractDto.php | 11 +++-- src/Dto/AbstractImmutableDto.php | 5 +- src/Dto/Dto.php | 81 ++++++++++++++++++++++---------- 4 files changed, 65 insertions(+), 33 deletions(-) diff --git a/config/app.default.php b/config/app.default.php index a3a4c54..11884fc 100644 --- a/config/app.default.php +++ b/config/app.default.php @@ -9,6 +9,7 @@ 'immutable' => false, // This can have a negative performance impact 'defaultCollectionType' => null, // Defaults to `\ArrayObject` 'debug' => false, // Add all meta data into DTOs for debugging + 'keyType' => null, // Dto::TYPE_DEFAULT by default which uses Dto::TYPE_CAMEL ], ]; diff --git a/src/Dto/AbstractDto.php b/src/Dto/AbstractDto.php index d1db68e..76b07e6 100644 --- a/src/Dto/AbstractDto.php +++ b/src/Dto/AbstractDto.php @@ -10,10 +10,10 @@ abstract class AbstractDto extends Dto { /** * @param array $data * @param bool $ignoreMissing - * @param string $type + * @param string|null $type * @return $this */ - public function fromArray(array $data, bool $ignoreMissing = false, $type = self::TYPE_DEFAULT) { + public function fromArray(array $data, bool $ignoreMissing = false, ?string $type = null) { return $this->setFromArray($data, $ignoreMissing, $type); } @@ -27,7 +27,7 @@ public function fromArray(array $data, bool $ignoreMissing = false, $type = self */ public function unserialize($serialized, $ignoreMissing = false) { $jsonUtil = new Json(); - $this->fromArray($jsonUtil->decode($serialized, true) ?: [], $ignoreMissing, static::TYPE_DEFAULT); + $this->fromArray($jsonUtil->decode($serialized, true) ?: [], $ignoreMissing); return $this; } @@ -46,11 +46,12 @@ public function __set(string $property, $value): void { /** * @param string $field * @param mixed $value - * @param string $type + * @param string|null $type * @throws \RuntimeException * @return $this */ - public function set(string $field, $value, string $type = self::TYPE_DEFAULT) { + public function set(string $field, $value, ?string $type = null) { + $type = $this->keyType($type); if ($type !== static::TYPE_DEFAULT) { $field = $this->field($field, $type); } diff --git a/src/Dto/AbstractImmutableDto.php b/src/Dto/AbstractImmutableDto.php index b098443..659d1f0 100644 --- a/src/Dto/AbstractImmutableDto.php +++ b/src/Dto/AbstractImmutableDto.php @@ -9,11 +9,12 @@ abstract class AbstractImmutableDto extends Dto { /** * @param string $field * @param mixed $value - * @param string $type + * @param string|null $type * @throws \RuntimeException * @return static */ - public function with(string $field, $value, string $type = self::TYPE_DEFAULT) { + public function with(string $field, $value, ?string $type = null) { + $type = $this->keyType($type); if ($type !== static::TYPE_DEFAULT) { $field = $this->field($field, $type); } diff --git a/src/Dto/Dto.php b/src/Dto/Dto.php index e31f121..80abb7c 100644 --- a/src/Dto/Dto.php +++ b/src/Dto/Dto.php @@ -6,6 +6,7 @@ use ArrayObject; use Cake\Collection\Collection; use Cake\Collection\CollectionInterface; +use Cake\Core\Configure; use CakeDto\View\Json; use Countable; use InvalidArgumentException; @@ -17,10 +18,10 @@ abstract class Dto implements Serializable { /** * @param array $data * @param bool $ignoreMissing - * @param string $type + * @param string|null $type * @return static */ - public static function createFromArray(array $data, bool $ignoreMissing = false, string $type = self::TYPE_DEFAULT) { + public static function createFromArray(array $data, bool $ignoreMissing = false, ?string $type = null) { return new static($data, $ignoreMissing, $type); } @@ -32,7 +33,7 @@ public static function createFromArray(array $data, bool $ignoreMissing = false, public static function fromUnserialized(string $data, bool $ignoreMissing = false) { $jsonUtil = new Json(); - return new static($jsonUtil->decode($data, true), $ignoreMissing, static::TYPE_DEFAULT); + return new static($jsonUtil->decode($data, true), $ignoreMissing); } /** @@ -61,15 +62,15 @@ public function unserialize($serialized, $ignoreMissing = false) { * * @param array|null $data * @param bool $ignoreMissing - * @param string $type + * @param string|null $type * @return static */ - public static function create(?array $data = null, bool $ignoreMissing = false, string $type = self::TYPE_DEFAULT) { + public static function create(?array $data = null, bool $ignoreMissing = false, ?string $type = null) { return new static($data, $ignoreMissing, $type); } /** - * Default camelCased type. + * Default type, defaults to camelBacked * * E.g. `myFieldName` * @@ -77,6 +78,15 @@ public static function create(?array $data = null, bool $ignoreMissing = false, */ public const TYPE_DEFAULT = 'default'; + /** + * For camelBacked input/output. + * + * E.g. `myFieldName` + * + * @var string + */ + public const TYPE_CAMEL = 'camel'; + /** * For DB and form input/output. * @@ -119,9 +129,9 @@ public static function create(?array $data = null, bool $ignoreMissing = false, /** * @param array|null $data * @param bool $ignoreMissing - * @param string $type + * @param string|null $type */ - public function __construct(?array $data = null, bool $ignoreMissing = false, string $type = self::TYPE_DEFAULT) { + public function __construct(?array $data = null, bool $ignoreMissing = false, ?string $type = null) { if ($data) { $this->setFromArray($data, $ignoreMissing, $type); } @@ -165,13 +175,11 @@ public function read(array $path, $default = null) { * @param bool $touched * @return array */ - public function toArray(?string $type = self::TYPE_DEFAULT, ?array $fields = null, bool $touched = false): array { + public function toArray(?string $type = null, ?array $fields = null, bool $touched = false): array { if ($fields === null) { $fields = $this->fields(); } - if ($type === null) { - $type = static::TYPE_DEFAULT; - } + $type = $this->keyType($type); $values = []; foreach ($fields as $field) { @@ -258,23 +266,24 @@ protected function transformArrayCollectionToArray(array $array, string $childCo } /** - * @param string $type + * @param string|null $type * @return array */ - public function touchedToArray(string $type = self::TYPE_DEFAULT): array { + public function touchedToArray(?string $type = null): array { return $this->toArray($type, $this->touchedFields(), true); } /** * @param array $data * @param bool $ignoreMissing - * @param string $type + * @param string|null $type * @throws \RuntimeException * @return $this */ - protected function setFromArray(array $data, bool $ignoreMissing, string $type = self::TYPE_DEFAULT) { + protected function setFromArray(array $data, bool $ignoreMissing, ?string $type = null) { $immutable = $this instanceof AbstractImmutableDto; + $type = $this->keyType($type); foreach ($data as $field => $value) { if (!$this->hasField($field, $ignoreMissing, $type)) { continue; @@ -332,11 +341,11 @@ protected function setFromArray(array $data, bool $ignoreMissing, string $type = * @param string $elementType * @param \ArrayObject|array $arrayObject * @param bool $ignoreMissing - * @param string $type + * @param string|null $type * * @return \Cake\Collection\CollectionInterface */ - protected function createCakeCollection(string $elementType, $arrayObject, bool $ignoreMissing, string $type = self::TYPE_DEFAULT): CollectionInterface { + protected function createCakeCollection(string $elementType, $arrayObject, bool $ignoreMissing, ?string $type = null): CollectionInterface { $collection = new Collection([]); foreach ($arrayObject as $arrayElement) { if (!is_array($arrayElement)) { @@ -436,11 +445,11 @@ protected function createWithConstructor(string $field, $value) { * @param string $elementType * @param \ArrayObject|array $arrayObject * @param bool $ignoreMissing - * @param string $type + * @param string|null $type * * @return \ArrayObject */ - protected function createCollection(string $collectionType, string $elementType, $arrayObject, bool $ignoreMissing, string $type = self::TYPE_DEFAULT): ArrayObject { + protected function createCollection(string $collectionType, string $elementType, $arrayObject, bool $ignoreMissing, ?string $type = null): ArrayObject { /** @var \ArrayObject $collection */ $collection = new $collectionType(); foreach ($arrayObject as $arrayElement) { @@ -472,12 +481,12 @@ protected function createCollection(string $collectionType, string $elementType, * @param string $elementType * @param \ArrayObject|array $arrayObject * @param bool $ignoreMissing - * @param string $type + * @param string|null $type * @param string|bool $key * * @return array */ - protected function createArrayCollection(string $elementType, $arrayObject, bool $ignoreMissing, string $type = self::TYPE_DEFAULT, $key = false): array { + protected function createArrayCollection(string $elementType, $arrayObject, bool $ignoreMissing, ?string $type = null, $key = false): array { $collection = []; foreach ($arrayObject as $index => $arrayElement) { if (!is_array($arrayElement)) { @@ -692,11 +701,12 @@ public function __isset(string $property): bool { /** * @param string $field - * @param string $type + * @param string|null $type * @throws \RuntimeException * @return bool */ - public function has(string $field, string $type = self::TYPE_DEFAULT): bool { + public function has(string $field, ?string $type = null): bool { + $type = $this->keyType($type); if ($type !== static::TYPE_DEFAULT) { $field = $this->field($field, $type); } @@ -712,11 +722,12 @@ public function has(string $field, string $type = self::TYPE_DEFAULT): bool { /** * @param string $field - * @param string $type + * @param string|null $type * @throws \RuntimeException * @return mixed */ - public function &get(string $field, string $type = self::TYPE_DEFAULT) { + public function &get(string $field, ?string $type = null) { + $type = $this->keyType($type); if ($type !== static::TYPE_DEFAULT) { $field = $this->field($field, $type); } @@ -781,6 +792,24 @@ protected function type($value): string { return $type; } + /** + * @param string|null $type + * + * @return string + */ + protected function keyType(?string $type): string { + if ($type === null) { + /** @var string|null $type */ + $type = Configure::read('CakeDto.keyType'); + } + + if ($type === null || $type === static::TYPE_CAMEL) { + return static::TYPE_DEFAULT; + } + + return $type; + } + /** * @param object $value * @param string $serialize