1: <?php
2:
3: declare(strict_types=1);
4:
5: namespace PHPStan\BetterReflection\SourceLocator\Type;
6:
7: use RecursiveDirectoryIterator;
8: use RecursiveIteratorIterator;
9: use PHPStan\BetterReflection\Identifier\Identifier;
10: use PHPStan\BetterReflection\Identifier\IdentifierType;
11: use PHPStan\BetterReflection\Reflection\Reflection;
12: use PHPStan\BetterReflection\Reflector\Reflector;
13: use PHPStan\BetterReflection\SourceLocator\Ast\Locator;
14: use PHPStan\BetterReflection\SourceLocator\Exception\InvalidDirectory;
15: use PHPStan\BetterReflection\SourceLocator\Exception\InvalidFileInfo;
16:
17: use function array_map;
18: use function is_dir;
19:
20: /**
21: * This source locator recursively loads all php files in an entire directory or multiple directories.
22: */
23: class DirectoriesSourceLocator implements SourceLocator
24: {
25: private AggregateSourceLocator $aggregateSourceLocator;
26:
27: /**
28: * @param list<string> $directories directories to scan
29: *
30: * @throws InvalidDirectory
31: * @throws InvalidFileInfo
32: */
33: public function __construct(array $directories, Locator $astLocator)
34: {
35: $this->aggregateSourceLocator = new AggregateSourceLocator(array_map(
36: static function (string $directory) use ($astLocator): FileIteratorSourceLocator {
37: if (! is_dir($directory)) {
38: throw InvalidDirectory::fromNonDirectory($directory);
39: }
40:
41: return new FileIteratorSourceLocator(
42: new RecursiveIteratorIterator(new RecursiveDirectoryIterator(
43: $directory,
44: RecursiveDirectoryIterator::SKIP_DOTS,
45: )),
46: $astLocator,
47: );
48: },
49: $directories,
50: ));
51: }
52:
53: public function locateIdentifier(Reflector $reflector, Identifier $identifier): ?\PHPStan\BetterReflection\Reflection\Reflection
54: {
55: return $this->aggregateSourceLocator->locateIdentifier($reflector, $identifier);
56: }
57:
58: /**
59: * {@inheritDoc}
60: */
61: public function locateIdentifiersByType(Reflector $reflector, IdentifierType $identifierType): array
62: {
63: return $this->aggregateSourceLocator->locateIdentifiersByType($reflector, $identifierType);
64: }
65: }
66: