mirror of
https://github.com/danog/psalm.git
synced 2025-01-21 21:31:13 +01:00
Fix array_key_exists() with all int literal keys (#5197)
When checking code like the following: ``` <?php function checkNegated(string $key): void { $arr = [ 0 => "foo", 1 => "bar", ]; if (!array_key_exists($key, $arr)) { printf("not found\n"); } } function check(string $key): void { $arr = [ 0 => "foo", 1 => "bar", ]; if (array_key_exists($key, $arr)) { printf("found\n"); } } ``` the `if` in `checkNegated` would cause: ``` ERROR: RedundantCondition - 9:10 - Type string for $key is never =int(0) ``` This happens when the array keys are all int literals, but the "needle" is a string. `array_key_exists()` uses a loose equality comparison, but the generated assertions for this specific case (`AssertionFinder::getArrayKeyExistsAssertions`) was generating strict equality clauses. This commit fixes it by changing the generated clause from `=` to `~`.
This commit is contained in:
parent
4077de2c93
commit
144bb37f76
@ -3770,7 +3770,7 @@ class AssertionFinder
|
||||
}
|
||||
} elseif ($key_type->allIntLiterals() && !$key_type->possibly_undefined) {
|
||||
foreach ($key_type->getLiteralInts() as $array_literal_type) {
|
||||
$literal_assertions[] = '=' . $array_literal_type->getAssertionString();
|
||||
$literal_assertions[] = '~' . $array_literal_type->getAssertionString();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -327,6 +327,34 @@ class ArrayKeyExistsTest extends \Psalm\Tests\TestCase
|
||||
return 1;
|
||||
}'
|
||||
],
|
||||
'comparesStringAndAllIntKeysCorrectly' => [
|
||||
'<?php
|
||||
/**
|
||||
* @param array<1|2|3, string> $arr
|
||||
* @return bool
|
||||
*/
|
||||
function checkArrayKeyExistsComparison(array $arr, string $key): bool
|
||||
{
|
||||
if (array_key_exists($key, $arr)) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}'
|
||||
],
|
||||
'comparesStringAndAllIntKeysCorrectlyNegated' => [
|
||||
'<?php
|
||||
/**
|
||||
* @param array<1|2|3, string> $arr
|
||||
* @return bool
|
||||
*/
|
||||
function checkArrayKeyExistsComparisonNegated(array $arr, string $key): bool
|
||||
{
|
||||
if (!array_key_exists($key, $arr)) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}'
|
||||
],
|
||||
];
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user