diff --git a/resources/functionMap_php80delta_bleedingEdge.php b/resources/functionMap_php80delta_bleedingEdge.php index 92f41e9db0..701777c4d1 100644 --- a/resources/functionMap_php80delta_bleedingEdge.php +++ b/resources/functionMap_php80delta_bleedingEdge.php @@ -2,7 +2,11 @@ return [ 'new' => [ + 'array_rand' => ['int|string|array|array', 'input'=>'non-empty-array', 'num_req'=>'positive-int'], + 'array_rand\'1' => ['int|string', 'input'=>'non-empty-array'], ], 'old' => [ + 'array_rand' => ['int|string|array|array', 'input'=>'array', 'num_req'=>'int'], + 'array_rand\'1' => ['int|string', 'input'=>'array'], ], ]; diff --git a/resources/functionMap_php82delta.php b/resources/functionMap_php82delta.php index 6054b7a9ce..033e6e716b 100644 --- a/resources/functionMap_php82delta.php +++ b/resources/functionMap_php82delta.php @@ -24,6 +24,7 @@ 'iterator_count' => ['0|positive-int', 'iterator'=>'iterable'], 'iterator_to_array' => ['array', 'iterator'=>'iterable', 'use_keys='=>'bool'], 'str_split' => ['list', 'str'=>'string', 'split_length='=>'positive-int'], + 'Random\Randomizer::pickArrayKeys' => ['non-empty-array', 'array'=>'non-empty-array', 'num'=>'positive-int'], ], 'old' => [ diff --git a/tests/PHPStan/Rules/Functions/CallToFunctionParametersRuleTest.php b/tests/PHPStan/Rules/Functions/CallToFunctionParametersRuleTest.php index 1753a05e0e..c8deff26b8 100644 --- a/tests/PHPStan/Rules/Functions/CallToFunctionParametersRuleTest.php +++ b/tests/PHPStan/Rules/Functions/CallToFunctionParametersRuleTest.php @@ -2368,4 +2368,39 @@ public function testBug13556(): void $this->analyse([__DIR__ . '/data/bug-13556.php'], []); } + #[RequiresPhp('>= 8.0')] + public function testArrayRand(): void + { + $this->analyse([__DIR__ . '/data/array_rand.php'], [ + [ + 'Parameter #1 $input of function array_rand expects non-empty-array, array{} given.', + 7, + 'array{} is empty.', + ], + [ + 'Parameter #1 $input of function array_rand expects non-empty-array, array{} given.', + 8, + 'array{} is empty.', + ], + [ + 'Parameter #2 $num_req of function array_rand expects int<1, max>, int given.', + 8, + ], + [ + 'Parameter #2 $num_req of function array_rand expects int<1, max>, -5 given.', + 13, + ], + [ + 'Parameter #2 $num_req of function array_rand expects int<1, max>, 0 given.', + 14, + ], + ]); + } + + #[RequiresPhp('< 8.0')] + public function testArrayRandPhp7(): void + { + $this->analyse([__DIR__ . '/data/array_rand.php'], []); + } + } diff --git a/tests/PHPStan/Rules/Functions/data/array_rand.php b/tests/PHPStan/Rules/Functions/data/array_rand.php new file mode 100644 index 0000000000..92fa5a808c --- /dev/null +++ b/tests/PHPStan/Rules/Functions/data/array_rand.php @@ -0,0 +1,17 @@ +analyse([__DIR__ . '/data/bug-13511.php'], []); } + #[RequiresPhp('>= 8.2')] + public function testRandomizer(): void + { + $this->checkThisOnly = false; + $this->checkNullables = true; + $this->checkUnionTypes = true; + $this->checkExplicitMixed = true; + + $this->analyse([__DIR__ . '/data/randomizer.php'], [ + [ + 'Parameter #2 $num of method Random\Randomizer::pickArrayKeys() expects int<1, max>, 0 given.', + 7, + ], + [ + 'Parameter #1 $array of method Random\Randomizer::pickArrayKeys() expects non-empty-array, array{} given.', + 8, + 'array{} is empty.', + ], + ]); + } + } diff --git a/tests/PHPStan/Rules/Methods/data/randomizer.php b/tests/PHPStan/Rules/Methods/data/randomizer.php new file mode 100644 index 0000000000..d124dd8785 --- /dev/null +++ b/tests/PHPStan/Rules/Methods/data/randomizer.php @@ -0,0 +1,8 @@ +pickArrayKeys(['a', 'b'], 10)); +var_dump($r->pickArrayKeys(['a'], 0)); +var_dump($r->pickArrayKeys([], 1));