<?php
/*
* This file is part of Chevere.
*
* (c) Rodolfo Berrios <[email protected]>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
declare(strict_types=1);
namespace Chevere\Parameter;
use Chevere\Parameter\Interfaces\IterableParameterInterface;
use Chevere\Parameter\Interfaces\ParameterInterface;
use Chevere\Parameter\Interfaces\TypeInterface;
use Chevere\Parameter\Traits\ArrayParameterTrait;
use Chevere\Parameter\Traits\ExceptionErrorMessageTrait;
use Chevere\Parameter\Traits\ParameterTrait;
use InvalidArgumentException;
use Throwable;
use function Chevere\Message\message;
final class IterableParameter implements IterableParameterInterface
{
use ParameterTrait;
use ArrayParameterTrait;
use ExceptionErrorMessageTrait;
/**
* @var iterable<mixed, mixed>
*/
private ?iterable $default = null;
public function __construct(
private ParameterInterface $value,
private ParameterInterface $key,
private string $description = ''
) {
$this->setUp(); // @codeCoverageIgnore
$this->type = $this->type();
$this->parameters = new Parameters(
K: $this->key,
V: $this->value
);
}
/**
* @phpstan-ignore-next-line
*/
public function __invoke(iterable $value): iterable
{
if (empty($value)) {
throw new InvalidArgumentException(
(string) message('Argument value provided is empty')
);
}
$iterable = ' *iterable';
$iterableKey = 'K' . $iterable;
$iterableValue = 'V' . $iterable;
try {
foreach ($value as $k => $v) {
assertNamedArgument($iterableKey, $this->key, $k);
assertNamedArgument($iterableValue, $this->value, $v);
}
} catch (Throwable $e) {
$message = $this->getExceptionMessage($e, ': ');
throw new InvalidArgumentException($message);
}
return $value;
}
public function default(): ?iterable
{
return $this->default;
}
public function withDefault(iterable $default): IterableParameterInterface
{
$this($default);
$new = clone $this;
$new->default = $default;
return $new;
}
public function key(): ParameterInterface
{
return $this->key;
}
public function value(): ParameterInterface
{
return $this->value;
}
public function assertCompatible(IterableParameterInterface $parameter): void
{
$this->key->assertCompatible($parameter->key());
$this->value->assertCompatible($parameter->value());
}
public function typeSchema(): string
{
return $this->type->primitive();
}
private function typeName(): string
{
return TypeInterface::ITERABLE;
}
}
|