Skip to content

Commit 620a9fe

Browse files
committed
Make unmatched inline ignores fixable
ignore.unmatchedIdentifier removes the identifier from the @PHPStan-Ignore comment, or the whole ignore when it is the only one. ignore.unmatchedLine removes the @phpstan-ignore-line / -next-line ignore. Plain comments are edited as text and left alone when they have other contents. PHPDocs are edited with PhpDocEditor, so their other tags are kept. Amp-Thread-ID: https://ampcode.com/threads/T-01a198ef-d81e-7532-81f4-438bae7a4db3
1 parent 5520ce9 commit 620a9fe

8 files changed

Lines changed: 580 additions & 4 deletions

File tree

‎src/Analyser/AnalyserResultFinalizer.php‎

Lines changed: 29 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
use Closure;
66
use PHPStan\AnalysedCodeException;
7+
use PHPStan\Analyser\Ignore\UnmatchedIgnoreFixer;
78
use PHPStan\Analyser\ResultCache\LazyCollectedData;
89
use PHPStan\BetterReflection\NodeCompiler\Exception\UnableToCompileNode;
910
use PHPStan\BetterReflection\Reflection\Exception\CircularReference;
@@ -12,6 +13,7 @@
1213
use PHPStan\DependencyInjection\AutowiredParameter;
1314
use PHPStan\DependencyInjection\AutowiredService;
1415
use PHPStan\DependencyInjection\ExtensionsCollection;
16+
use PHPStan\File\FileReader;
1517
use PHPStan\Node\CollectedDataNode;
1618
use PHPStan\Node\CollectedDataNodeReads;
1719
use PHPStan\Rules\Registry as RuleRegistry;
@@ -44,6 +46,7 @@ public function __construct(
4446
private RuleErrorTransformer $ruleErrorTransformer,
4547
private ScopeFactory $scopeFactory,
4648
private LocalIgnoresProcessor $localIgnoresProcessor,
49+
private UnmatchedIgnoreFixer $unmatchedIgnoreFixer,
4750
#[AutowiredParameter]
4851
private bool $reportUnmatchedIgnoredErrors,
4952
private ValueDependencyCollector $valueDependencyCollector,
@@ -399,6 +402,23 @@ private function mergeFilteredPhpErrors(AnalyserResult $analyserResult): Analyse
399402
);
400403
}
401404

405+
/**
406+
* @return list<FixedErrorDiff>
407+
*/
408+
private function fixUnmatchedIgnore(string $file, ?string $code, int $line, ?string $identifier): array
409+
{
410+
if ($code === null) {
411+
return [];
412+
}
413+
414+
$newCode = $this->unmatchedIgnoreFixer->fix($code, $line, $identifier);
415+
if ($newCode === null) {
416+
return [];
417+
}
418+
419+
return [$this->ruleErrorTransformer->createFixedErrorDiff($file, $code, $newCode)];
420+
}
421+
402422
/**
403423
* @param list<Error> $collectorErrors
404424
* @param list<Error> $locallyIgnoredCollectorErrors
@@ -423,26 +443,31 @@ private function addUnmatchedIgnoredErrors(
423443
continue;
424444
}
425445

446+
$code = is_file($file) ? FileReader::read($file) : null;
426447
foreach ($lines as $line => $identifiers) {
427448
if ($identifiers === null) {
428-
$errors[] = (new Error(
449+
$errors[] = new Error(
429450
sprintf('No error to ignore is reported on line %d.', $line),
430451
$file,
431452
$line,
432453
false,
433454
$file,
434-
))->withIdentifier('ignore.unmatchedLine');
455+
identifier: 'ignore.unmatchedLine',
456+
fixedErrorDiffs: $this->fixUnmatchedIgnore($file, $code, $line, null),
457+
);
435458
continue;
436459
}
437460

438461
foreach ($identifiers as $identifier) {
439-
$errors[] = (new Error(
462+
$errors[] = new Error(
440463
sprintf('No error with identifier %s is reported on line %d.', $identifier['name'], $line),
441464
$file,
442465
$line,
443466
false,
444467
$file,
445-
))->withIdentifier('ignore.unmatchedIdentifier');
468+
identifier: 'ignore.unmatchedIdentifier',
469+
fixedErrorDiffs: $this->fixUnmatchedIgnore($file, $code, $line, $identifier['name']),
470+
);
446471
}
447472
}
448473
}

0 commit comments

Comments
 (0)