assertNotFalse($root, 'Project root not found.'); return $root; } private function readProjectFile(string $path): string { $root = $this->projectRootPath(); $fullPath = $root . '/' . $path; $this->assertFileExists($fullPath, 'File not found: ' . $path); $content = file_get_contents($fullPath); $this->assertNotFalse($content, 'Could not read file: ' . $path); return $content; } /** * @return list */ private function findPatternMatchesInPhpFiles(string $relativeDirectory, string $pattern): array { return $this->findPatternMatchesInFiles($relativeDirectory, $pattern, ['php']); } /** * @param list $extensions * @return list */ private function findPatternMatchesInFiles(string $relativeDirectory, string $pattern, array $extensions): array { $root = $this->projectRootPath(); $basePath = $root . '/' . $relativeDirectory; $this->assertDirectoryExists($basePath, 'Directory not found: ' . $relativeDirectory); $iterator = new \RecursiveIteratorIterator(new \RecursiveDirectoryIterator($basePath)); $violations = []; /** @var \SplFileInfo $file */ foreach ($iterator as $file) { if (!$file->isFile() || !in_array($file->getExtension(), $extensions, true)) { continue; } $content = file_get_contents($file->getPathname()); $this->assertNotFalse($content, 'Could not read file: ' . $file->getPathname()); if (!preg_match($pattern, $content)) { continue; } $relativePath = str_replace($root . '/', '', $file->getPathname()); $violations[] = $relativePath; } sort($violations); return $violations; } }