Skip to content

Commit 7538546

Browse files
Avoid false positive in_array() always true
1 parent 1164c64 commit 7538546

File tree

7 files changed

+139
-0
lines changed

7 files changed

+139
-0
lines changed

src/Rules/Comparison/ImpossibleCheckTypeHelper.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -157,6 +157,11 @@ public function findSpecifiedType(
157157
continue;
158158
}
159159

160+
$haystackArrayValueConstantScalarTypes = $haystackArrayValueType->getConstantScalarTypes();
161+
if (count($haystackArrayValueConstantScalarTypes) > 1) {
162+
continue;
163+
}
164+
160165
foreach ($haystackArrayValueType->getConstantScalarTypes() as $constantScalarType) {
161166
if ($constantScalarType->isSuperTypeOf($needleType)->yes()) {
162167
continue 3;

tests/PHPStan/Analyser/NodeScopeResolverTest.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,7 @@ private static function findTestFiles(): iterable
8888
yield __DIR__ . '/../Rules/Variables/data/bug-10577.php';
8989
yield __DIR__ . '/../Rules/Variables/data/bug-10610.php';
9090
yield __DIR__ . '/../Rules/Comparison/data/bug-2550.php';
91+
yield __DIR__ . '/../Rules/Comparison/data/bug-12412.php';
9192
yield __DIR__ . '/../Rules/Properties/data/bug-3777.php';
9293
yield __DIR__ . '/../Rules/Methods/data/bug-4552.php';
9394
yield __DIR__ . '/../Rules/Methods/data/infer-array-key.php';

tests/PHPStan/Rules/Comparison/ImpossibleCheckTypeFunctionCallRuleTest.php

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -981,4 +981,28 @@ public function testBugPR3404(): void
981981
]);
982982
}
983983

984+
public function testBug13151(): void
985+
{
986+
$this->treatPhpDocTypesAsCertain = true;
987+
$this->analyse([__DIR__ . '/data/bug-13151.php'], []);
988+
}
989+
990+
public function testBug8818(): void
991+
{
992+
$this->treatPhpDocTypesAsCertain = true;
993+
$this->analyse([__DIR__ . '/data/bug-8818.php'], []);
994+
}
995+
996+
public function testBug12755(): void
997+
{
998+
$this->treatPhpDocTypesAsCertain = true;
999+
$this->analyse([__DIR__ . '/data/bug-12755.php'], []);
1000+
}
1001+
1002+
public function testBug12412(): void
1003+
{
1004+
$this->treatPhpDocTypesAsCertain = true;
1005+
$this->analyse([__DIR__ . '/data/bug-12412.php'], []);
1006+
}
1007+
9841008
}
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
<?php declare(strict_types = 1);
2+
3+
namespace Bug12412;
4+
5+
use function PHPStan\Testing\assertType;
6+
7+
/**
8+
* @param 'A'|'B' $type
9+
* @return list<string>
10+
*/
11+
function f(string $type): array {
12+
$field_list = [ ];
13+
if ($type === 'A') {
14+
array_push($field_list, 'x1');
15+
}
16+
if ($type === 'B') {
17+
array_push($field_list, 'x2');
18+
}
19+
20+
assertType('bool', in_array('x1', $field_list, true));
21+
22+
array_push($field_list, 'x3');
23+
assertType('bool', in_array('x1', $field_list, true));
24+
25+
return $field_list;
26+
}
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
<?php declare(strict_types = 1);
2+
3+
namespace Bug12755;
4+
5+
class HelloWorld
6+
{
7+
/**
8+
* @param array{
9+
* key1: ?int,
10+
* key2: ?string,
11+
* } $myArray
12+
*/
13+
public function testOther(array $myArray): ?\stdClass
14+
{
15+
if (\in_array(null, $myArray, true)) {
16+
return null;
17+
}
18+
19+
return (object) $myArray;
20+
}
21+
22+
/**
23+
* @param array{
24+
* key1: ?bool,
25+
* } $myArray
26+
*/
27+
public function testBool(array $myArray): ?\stdClass
28+
{
29+
if (\in_array(null, $myArray, true)) {
30+
return null;
31+
}
32+
33+
return (object) $myArray;
34+
}
35+
}
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
<?php declare(strict_types = 1);
2+
3+
namespace Bug13151;
4+
5+
class HelloWorld
6+
{
7+
/**
8+
* @return array{a:0|1, b:0|1, c:0|1}
9+
*/
10+
public function extractAsArray(): array
11+
{
12+
return [
13+
'a' => 1,
14+
'b' => 1,
15+
'c' => 1
16+
];
17+
}
18+
19+
public function test(): void
20+
{
21+
echo in_array(0, $this->extractAsArray(), true) ? "True" : "False";
22+
}
23+
24+
public function test2(): void
25+
{
26+
echo in_array(0, $this->extractAsArray()) ? "True" : "False";
27+
}
28+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
<?php declare(strict_types = 1);
2+
3+
namespace Bug8818;
4+
5+
class MyEnum {
6+
public const ONE = 'one';
7+
public const TWO = 'two';
8+
public const THREE = 'three';
9+
}
10+
11+
class HelloWorld
12+
{
13+
/**
14+
* @param list<MyEnum::*> $stack
15+
*/
16+
public function sayHello(array $stack): bool
17+
{
18+
return count($stack) === 1 && in_array(MyEnum::ONE, $stack, true);
19+
}
20+
}

0 commit comments

Comments
 (0)