|null> */ class NutritionalValuesCast implements CastsAttributes { /** @param array $attributes */ public function get(Model $model, string $key, mixed $value, array $attributes): ?NutritionalValues { if ($value === null) { return null; } $data = is_string($value) ? json_decode($value, true) : $value; if (! is_array($data)) { return null; } return $this->fromArray($data); } /** * @param array $attributes * @return array */ public function set(Model $model, string $key, mixed $value, array $attributes): array { if ($value === null) { return [$key => null]; } if (is_string($value)) { $value = json_decode($value, true); } if (is_array($value)) { $value = $this->fromArray($value); } if (! $value instanceof NutritionalValues) { throw new InvalidArgumentException('The given value is not a NutritionalValues instance.'); } return [$key => json_encode($value->toArray())]; } /** * @param array $data */ private function fromArray(array $data): ?NutritionalValues { $refWeightData = Arr::array($data, 'refWeightG'); $rawVal = Arr::get($refWeightData, 'value'); $rawUnit = Arr::get($refWeightData, 'unit'); if ((! is_string($rawVal) && ! is_numeric($rawVal)) || ! is_string($rawUnit)) { return null; } $refWeightUnit = NutritionnalUnit::tryFrom($rawUnit); if ($refWeightUnit === null) { return null; } /** @param array $data */ $getProperty = function (array $data, string $key): ?NutritionalValue { return when( is_array(Arr::get($data, $key)), fn () => $this->toNutritionalValues(Arr::array($data, $key)), null ); }; return new NutritionalValues( refWeightG: new NutritionalValue((string) $rawVal, $refWeightUnit), kj: $getProperty($data, 'kj'), kcal: $getProperty($data, 'kcal'), fatG: $getProperty($data, 'fatG'), satFatG: $getProperty($data, 'satFatG'), carbG: $getProperty($data, 'carbG'), sugarG: $getProperty($data, 'sugarG'), fiberG: $getProperty($data, 'fiberG'), proteinG: $getProperty($data, 'proteinG'), saltG: $getProperty($data, 'saltG'), ); } /** * @param array $data */ private function toNutritionalValues(array $data): ?NutritionalValue { $rawItemVal = Arr::get($data, 'value'); $rawItemUnit = Arr::get($data, 'unit'); if ((! is_string($rawItemVal) && ! is_numeric($rawItemVal)) || ! is_string($rawItemUnit)) { return null; } $value = mb_trim((string) $rawItemVal); $unit = NutritionnalUnit::tryFrom($rawItemUnit); if ($value === '' || $unit === null) { return null; } return new NutritionalValue($value, $unit); } }