diff --git a/.github/workflows/run-tests.yml b/.github/workflows/run-tests.yml index e3de85f..5a21aaf 100644 --- a/.github/workflows/run-tests.yml +++ b/.github/workflows/run-tests.yml @@ -13,12 +13,14 @@ jobs: fail-fast: true matrix: os: [ubuntu-latest, windows-latest] - php: [8.1] - laravel: [9.*] + php: [8.1, 8.2] + laravel: [9.*, 10.*] stability: [prefer-lowest, prefer-stable] include: + - laravel: 10.* + testbench: 8.* - laravel: 9.* - testbench: ^7.0 + testbench: 7.* name: P${{ matrix.php }} - L${{ matrix.laravel }} - ${{ matrix.stability }} - ${{ matrix.os }} diff --git a/composer.json b/composer.json index d825691..4a33070 100644 --- a/composer.json +++ b/composer.json @@ -19,15 +19,15 @@ "php": "^8.1", "symfony/console": "^6.0", "spatie/laravel-package-tools": "^1.9.2", - "illuminate/contracts": "^9.0" + "illuminate/contracts": "^9.0|^10.0" }, "require-dev": { "laravel/sail": "^1.13", "nunomaduro/collision": "^v6.1.0", - "nunomaduro/larastan": "^1.0", - "orchestra/testbench": "^7.0", + "nunomaduro/larastan": "^2.0", + "orchestra/testbench": "^7.0|^8.0", "pestphp/pest": "^1.21", - "pestphp/pest-plugin-laravel": "^1.1", + "pestphp/pest-plugin-laravel": "^1.4", "phpstan/extension-installer": "^1.1", "phpstan/phpstan-deprecation-rules": "^1.0", "phpstan/phpstan-phpunit": "^1.0", diff --git a/src/Concerns/UsesInputValidation.php b/src/Concerns/UsesInputValidation.php index 72a95a2..72e60f9 100644 --- a/src/Concerns/UsesInputValidation.php +++ b/src/Concerns/UsesInputValidation.php @@ -35,11 +35,11 @@ protected function validate(Collection $collection): Collection $messages ); - if (!$validator->fails()) { + if (! $validator->fails()) { return $collection; } - $inputErrors = $collection->mapWithKeys(fn(InputReflection $reflection) => [ + $inputErrors = $collection->mapWithKeys(fn (InputReflection $reflection) => [ $reflection->getName() => new InputErrorData( key: $reflection->getName(), choices: $choices[$reflection->getName()] ?? [], @@ -56,7 +56,7 @@ protected function validate(Collection $collection): Collection */ protected function extractValidationData(Collection $collection): array { - return $collection->reduce(fn(array $carry, InputReflection $reflection) => [ + return $collection->reduce(fn (array $carry, InputReflection $reflection) => [ 'values' => [...$carry['values'], ...$this->extractInputValues($reflection)], 'rules' => [...$carry['rules'], ...$this->extractInputRules($reflection)], 'messages' => [...$carry['messages'], ...$this->extractValidationMessages($reflection)], @@ -71,12 +71,12 @@ protected function extractValidationData(Collection $collection): array protected function extractValidationMessages(InputReflection $reflection): array { - if (!$reflection->getValidationMessage()) { + if (! $reflection->getValidationMessage()) { return []; } return collect($reflection->getValidationMessage()) - ->mapWithKeys(fn(string $value, string $key) => ["{$reflection->getName()}.{$key}" => $value]) + ->mapWithKeys(fn (string $value, string $key) => ["{$reflection->getName()}.{$key}" => $value]) ->all(); } @@ -98,7 +98,7 @@ protected function extractInputRules( ): array { $rules = []; - if ($this->hasAutoAskEnabled($reflection) && !$reflection->isArray()) { + if ($this->hasAutoAskEnabled($reflection) && ! $reflection->isArray()) { $rules[] = 'required'; } diff --git a/src/Reflections/ArgumentReflection.php b/src/Reflections/ArgumentReflection.php index 990b8b9..c135033 100644 --- a/src/Reflections/ArgumentReflection.php +++ b/src/Reflections/ArgumentReflection.php @@ -5,6 +5,9 @@ use Thettler\LaravelConsoleToolkit\Attributes\Argument; use Thettler\LaravelConsoleToolkit\Enums\ConsoleInputType; +/** + * @extends InputReflection + */ class ArgumentReflection extends InputReflection { public static function isArgument(\ReflectionProperty $property): bool diff --git a/src/Reflections/CommandReflection.php b/src/Reflections/CommandReflection.php index fbff703..06a9947 100644 --- a/src/Reflections/CommandReflection.php +++ b/src/Reflections/CommandReflection.php @@ -36,6 +36,9 @@ public function usesInputAttributes(): bool return $this->getArguments()->isNotEmpty() || $this->getOptions()->isNotEmpty(); } + /** + * @return Collection + */ public function getArguments(): Collection { return collect($this->reflection->getProperties()) @@ -49,6 +52,9 @@ public function getArguments(): Collection ); } + /** + * @return Collection + */ public function getOptions(): Collection { return collect($this->reflection->getProperties()) diff --git a/src/Transfers/InputErrorData.php b/src/Transfers/InputErrorData.php index 67ce631..4461847 100644 --- a/src/Transfers/InputErrorData.php +++ b/src/Transfers/InputErrorData.php @@ -2,10 +2,17 @@ namespace Thettler\LaravelConsoleToolkit\Transfers; +use Thettler\LaravelConsoleToolkit\Contracts\ConsoleInput; use Thettler\LaravelConsoleToolkit\Reflections\InputReflection; class InputErrorData { + /** + * @param string $key + * @param array $choices + * @param InputReflection $reflection + * @param bool $hasAutoAsk + */ public function __construct( public readonly string $key, public readonly array $choices, diff --git a/tests/ConsoleInputAutoAskTest.php b/tests/ConsoleInputAutoAskTest.php index 0301920..b5f706c 100644 --- a/tests/ConsoleInputAutoAskTest.php +++ b/tests/ConsoleInputAutoAskTest.php @@ -2,6 +2,8 @@ use Illuminate\Console\Application as Artisan; use Illuminate\Console\Command; +use Illuminate\Support\Facades\App; +use Illuminate\Translation\Translator; use Thettler\LaravelConsoleToolkit\Attributes\Argument; use Thettler\LaravelConsoleToolkit\Attributes\Option; use Thettler\LaravelConsoleToolkit\Concerns\UsesConsoleToolkit; @@ -143,11 +145,12 @@ public function handle() }; Artisan::starting(fn (Artisan $artisan) => $artisan->add($command)); + $translator = App::make(Translator::class); \Pest\Laravel\artisan('validate LongerThan5 --shortOption=alsoLonger') - ->expectsOutput('The short argument must not be greater than 5 characters.') + ->expectsOutput($translator->get('validation.max.string', ['attribute' => 'short argument', 'max' => 5])) ->expectsQuestion('Please enter "shortArgument"', 'short') - ->expectsOutput('The short option must not be greater than 5 characters.') + ->expectsOutput($translator->get('validation.max.string', ['attribute' => 'short option', 'max' => 5])) ->expectsQuestion('Please enter "shortOption"', 'small') ->expectsOutput('short small') ->assertSuccessful(); diff --git a/tests/ConsoleInputValidationTest.php b/tests/ConsoleInputValidationTest.php index f9d8f98..9a223e5 100644 --- a/tests/ConsoleInputValidationTest.php +++ b/tests/ConsoleInputValidationTest.php @@ -2,6 +2,8 @@ use Illuminate\Console\Application as Artisan; use Illuminate\Console\Command; +use Illuminate\Support\Facades\App; +use Illuminate\Translation\Translator; use Thettler\LaravelConsoleToolkit\Attributes\Argument; use Thettler\LaravelConsoleToolkit\Attributes\Option; use Thettler\LaravelConsoleToolkit\Concerns\UsesConsoleToolkit; @@ -30,15 +32,17 @@ public function handle() { - $this->line($this->shortArgument . ' ' . $this->shortOption); + $this->line($this->shortArgument.' '.$this->shortOption); } }; Artisan::starting(fn (Artisan $artisan) => $artisan->add($command)); + $translator = App::make(Translator::class); + \Pest\Laravel\artisan('validate LongerThan5 --shortOption=alsoLonger') - ->expectsOutput('The short argument must not be greater than 5 characters.') - ->expectsOutput('The short option must not be greater than 5 characters.') + ->expectsOutput($translator->get('validation.max.string', ['attribute' => 'short argument', 'max' => 5])) + ->expectsOutput($translator->get('validation.max.string', ['attribute' => 'short option', 'max' => 5])) ->doesntExpectOutput('LongerThan5 alsoLonger') ->assertFailed(); }); @@ -59,7 +63,7 @@ public function handle() public function handle() { - $this->line($this->A->name . ' ' . $this->O->value); + $this->line($this->A->name.' '.$this->O->value); } }; @@ -68,14 +72,14 @@ public function handle() \Pest\Laravel\artisan('validate notValid --O=notValid') ->expectsOutput('The selected a is invalid.') ->expectsOutput('Possible values for: A.') - ->expectsOutput(' - ' . Enum::A->name) - ->expectsOutput(' - ' . Enum::B->name) - ->expectsOutput(' - ' . Enum::C->name) + ->expectsOutput(' - '.Enum::A->name) + ->expectsOutput(' - '.Enum::B->name) + ->expectsOutput(' - '.Enum::C->name) ->expectsOutput('The selected o is invalid.') ->expectsOutput('Possible values for: O.') - ->expectsOutput(' - ' . StringEnum::A->value) - ->expectsOutput(' - ' . StringEnum::B->value) - ->expectsOutput(' - ' . StringEnum::C->value) + ->expectsOutput(' - '.StringEnum::A->value) + ->expectsOutput(' - '.StringEnum::B->value) + ->expectsOutput(' - '.StringEnum::C->value) ->assertFailed(); }); @@ -105,7 +109,7 @@ public function handle() public function handle() { - $this->line($this->shortArgument . ' ' . $this->shortOption); + $this->line($this->shortArgument.' '.$this->shortOption); } };