Skip to content

Commit 33d1258

Browse files
zonuexecursoragent
andcommitted
Do not match ignored error messages repeatedly for multiple paths
Co-authored-by: Cursor <cursoragent@cursor.com>
1 parent d6adcb4 commit 33d1258

2 files changed

Lines changed: 49 additions & 13 deletions

File tree

‎src/Analyser/Ignore/IgnoredErrorHelperResult.php‎

Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -116,22 +116,27 @@ public function process(
116116
}
117117
}
118118
} elseif (isset($ignore['paths'])) {
119-
foreach ($ignore['paths'] as $j => $ignorePath) {
120-
$shouldBeIgnored = IgnoredError::shouldIgnore($this->fileHelper, $error, ignoredErrorPattern: $ignore['message'] ?? null, ignoredErrorMessage: $ignore['rawMessage'] ?? null, identifier: $ignore['identifier'] ?? null, path: $ignorePath);
121-
if (!$shouldBeIgnored) {
122-
continue;
123-
}
124-
125-
if (isset($unmatchedIgnoredErrors[$i])) {
126-
if (!is_array($unmatchedIgnoredErrors[$i])) {
127-
throw new ShouldNotHappenException();
119+
// Message and identifier do not depend on the path. Match them once
120+
// instead of repeating the potentially expensive regex for every path.
121+
$matchesMessageAndIdentifier = IgnoredError::shouldIgnore($this->fileHelper, $error, ignoredErrorPattern: $ignore['message'] ?? null, ignoredErrorMessage: $ignore['rawMessage'] ?? null, identifier: $ignore['identifier'] ?? null, path: null);
122+
if ($matchesMessageAndIdentifier) {
123+
foreach ($ignore['paths'] as $j => $ignorePath) {
124+
$shouldBeIgnored = IgnoredError::shouldIgnore($this->fileHelper, $error, ignoredErrorPattern: null, ignoredErrorMessage: null, identifier: null, path: $ignorePath);
125+
if (!$shouldBeIgnored) {
126+
continue;
128127
}
129-
unset($unmatchedIgnoredErrors[$i]['paths'][$j]);
130-
if (isset($unmatchedIgnoredErrors[$i]['paths']) && count($unmatchedIgnoredErrors[$i]['paths']) === 0) {
131-
unset($unmatchedIgnoredErrors[$i]);
128+
129+
if (isset($unmatchedIgnoredErrors[$i])) {
130+
if (!is_array($unmatchedIgnoredErrors[$i])) {
131+
throw new ShouldNotHappenException();
132+
}
133+
unset($unmatchedIgnoredErrors[$i]['paths'][$j]);
134+
if (isset($unmatchedIgnoredErrors[$i]['paths']) && count($unmatchedIgnoredErrors[$i]['paths']) === 0) {
135+
unset($unmatchedIgnoredErrors[$i]);
136+
}
132137
}
138+
break;
133139
}
134-
break;
135140
}
136141
} else {
137142
$shouldBeIgnored = IgnoredError::shouldIgnore($this->fileHelper, $error, ignoredErrorPattern: $ignore['message'] ?? null, ignoredErrorMessage: $ignore['rawMessage'] ?? null, identifier: $ignore['identifier'] ?? null, path: null);

‎tests/PHPStan/Analyser/AnalyserTest.php‎

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -406,6 +406,37 @@ public function testIgnoreErrorRawByPaths(): void
406406
$this->assertNoErrors($result);
407407
}
408408

409+
public function testIgnoreErrorByMessageIdentifierAndSecondPath(): void
410+
{
411+
$ignoreErrors = [
412+
[
413+
'message' => '#Fail\.#',
414+
'identifier' => 'tests.alwaysFail',
415+
'paths' => [
416+
__DIR__ . '/data/another-path.php',
417+
__DIR__ . '/data/bootstrap-error.php',
418+
],
419+
],
420+
];
421+
$result = $this->runAnalyser($ignoreErrors, false, __DIR__ . '/data/bootstrap-error.php', false);
422+
$this->assertNoErrors($result);
423+
}
424+
425+
public function testIgnoreErrorByPathsRequiresMatchingIdentifier(): void
426+
{
427+
$ignoreErrors = [
428+
[
429+
'message' => '#Fail\.#',
430+
'identifier' => 'wrong.identifier',
431+
'paths' => [__DIR__ . '/data/bootstrap-error.php'],
432+
],
433+
];
434+
$result = $this->runAnalyser($ignoreErrors, false, __DIR__ . '/data/bootstrap-error.php', false);
435+
$this->assertCount(1, $result);
436+
$this->assertInstanceOf(Error::class, $result[0]);
437+
$this->assertSame('Fail.', $result[0]->getMessage());
438+
}
439+
409440
public function testIgnoreErrorMultiByPaths(): void
410441
{
411442
$ignoreErrors = [

0 commit comments

Comments
 (0)