diff --git a/src/Analyser/NodeScopeResolver.php b/src/Analyser/NodeScopeResolver.php index c952da2e95..d5f87e3f15 100644 --- a/src/Analyser/NodeScopeResolver.php +++ b/src/Analyser/NodeScopeResolver.php @@ -6521,6 +6521,23 @@ private function enterForeach(MutatingScope $scope, MutatingScope $originalScope } } + if ( + $stmt->expr instanceof FuncCall + && $stmt->expr->name instanceof Name + && $stmt->expr->name->toLowerString() === 'array_keys' + && $stmt->valueVar instanceof Variable + ) { + $args = $stmt->expr->getArgs(); + if (count($args) >= 1) { + $arrayArg = $args[0]->value; + $scope = $scope->assignExpression( + new ArrayDimFetch($arrayArg, $stmt->valueVar), + $scope->getType($arrayArg)->getIterableValueType(), + $scope->getNativeType($arrayArg)->getIterableValueType(), + ); + } + } + return $this->processVarAnnotation($scope, $vars, $stmt); } diff --git a/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php b/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php index 48e9f1012d..6c79bcc795 100644 --- a/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php +++ b/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php @@ -1000,4 +1000,11 @@ public function testBug10492(): void ]); } + public function testBug12926(): void + { + $this->reportPossiblyNonexistentGeneralArrayOffset = true; + + $this->analyse([__DIR__ . '/data/bug-12926.php'], []); + } + } diff --git a/tests/PHPStan/Rules/Arrays/data/bug-12926.php b/tests/PHPStan/Rules/Arrays/data/bug-12926.php new file mode 100644 index 0000000000..d83bd21b36 --- /dev/null +++ b/tests/PHPStan/Rules/Arrays/data/bug-12926.php @@ -0,0 +1,13 @@ +