decouple FilesystemTweaker

This commit is contained in:
Tomas Votruba 2018-08-30 22:45:06 +02:00
parent 1c51f5d9bf
commit 010a55a261
4 changed files with 106 additions and 106 deletions

View File

@ -0,0 +1,70 @@
<?php declare(strict_types=1);
namespace Rector\Utils;
use Nette\Utils\Strings;
use Rector\Exception\FileSystem\DirectoryNotFoundException;
use Rector\Exception\FileSystem\FileNotFoundException;
final class FilesystemTweaker
{
/**
* @param string[] $source
* @return string[][]
*/
public function splitSourceToDirectoriesAndFiles(array $source): array
{
$files = [];
$directories = [];
foreach ($source as $singleSource) {
if (is_file($singleSource)) {
$this->ensureFileExists($singleSource);
$files[] = $singleSource;
} else {
$directories[] = $singleSource;
}
}
return [$files, $directories];
}
/**
* This will turn paths like "src/Symfony/Component/*\/Tests" to existing directory paths
*
* @param string[] $directories
* @return string[]
*/
public function resolveDirectoriesWithFnmatch(array $directories): array
{
$absoluteDirectories = [];
foreach ($directories as $directory) {
if (Strings::contains($directory, '*')) { // is fnmatch for directories
$absoluteDirectories = array_merge($absoluteDirectories, glob($directory, GLOB_ONLYDIR));
} else { // is classic directory
$this->ensureDirectoryExists($directory);
$absoluteDirectories[] = $directory;
}
}
return $absoluteDirectories;
}
private function ensureFileExists(string $file): void
{
if (file_exists($file)) {
return;
}
throw new FileNotFoundException(sprintf('File "%s" was not found.', $file));
}
private function ensureDirectoryExists(string $directory): void
{
if (file_exists($directory)) {
return;
}
throw new DirectoryNotFoundException(sprintf('Directory "%s" was not found.', $directory));
}
}

View File

@ -17,9 +17,6 @@ parameters:
- '#Cannot cast PhpParser\\Node\\Expr\|PhpParser\\Node\\Name to string#'
- '#Array \(array<array<PhpParser\\Node\\Stmt>>\) does not accept array<PhpParser\\Node\\Stmt|null>#'
# array miss types
- '#Method Rector\\FileSystem\\FilesFinder::splitSourceToDirectoriesAndFiles\(\) should return array<array<string>\|Symfony\\Component\\Finder\\SplFileInfo> but returns array<int, array<int, string\|Symfony\\Component\\Finder\\SplFileInfo>>#'
# already fixed, invalidated cache?
- '#Access to an undefined property PhpParser\\Node\\Expr::\$args#'

View File

@ -3,9 +3,9 @@
namespace Rector\Autoloading;
use Nette\Loaders\RobotLoader;
use Nette\Utils\Strings;
use Rector\Configuration\Option;
use Rector\FileSystem\FileGuard;
use Rector\Utils\FilesystemTweaker;
use Symfony\Component\Console\Input\InputInterface;
/**
@ -28,15 +28,25 @@ final class AdditionalAutoloader
*/
private $autoloadDirectories = [];
/**
* @var FilesystemTweaker
*/
private $filesystemTweaker;
/**
* @param string[] $autoloadFiles
* @param string[] $autoloadDirectories
*/
public function __construct(array $autoloadFiles, array $autoloadDirectories, FileGuard $fileGuard)
{
public function __construct(
array $autoloadFiles,
array $autoloadDirectories,
FileGuard $fileGuard,
FilesystemTweaker $filesystemTweaker
) {
$this->autoloadFiles = $autoloadFiles;
$this->autoloadDirectories = $autoloadDirectories;
$this->fileGuard = $fileGuard;
$this->filesystemTweaker = $filesystemTweaker;
}
public function autoloadWithInput(InputInterface $input): void
@ -53,20 +63,10 @@ final class AdditionalAutoloader
{
$this->autoloadWithInput($input);
[$files, $directories] = $this->splitSourceToDirectoriesAndFiles($source);
// @todo include the files so people don't have to do it manually?
$absoluteDirectories = [];
foreach ($directories as $directory) {
if (Strings::contains($directory, '*')) { // is fnmatch for directories
$absoluteDirectories = array_merge($absoluteDirectories, glob($directory, GLOB_ONLYDIR));
} else { // is classic directory
$absoluteDirectories[] = $directory;
}
}
[$files, $directories] = $this->filesystemTweaker->splitSourceToDirectoriesAndFiles($source);
$this->autoloadFiles($files);
$absoluteDirectories = $this->filesystemTweaker->resolveDirectoriesWithFnmatch($directories);
if (count($absoluteDirectories)) {
$this->autoloadDirectories($absoluteDirectories);
}
@ -83,27 +83,6 @@ final class AdditionalAutoloader
$this->autoloadFiles([$autoloadFile]);
}
/**
* @todo decouple to standalone Finder/File something
* @param string[] $source
* @return string[][]|string[]
*/
private function splitSourceToDirectoriesAndFiles(array $source): array
{
$files = [];
$directories = [];
foreach ($source as $singleSource) {
if (is_file($singleSource)) {
$files[] = $singleSource;
} else {
$directories[] = $singleSource;
}
}
return [$files, $directories];
}
/**
* @param string[] $directories
*/

View File

@ -3,7 +3,7 @@
namespace Rector\FileSystem;
use Nette\Utils\Strings;
use Rector\Exception\FileSystem\DirectoryNotFoundException;
use Rector\Utils\FilesystemTweaker;
use SplFileInfo as NativeSplFileInfo;
use Symfony\Component\Finder\Finder;
use Symfony\Component\Finder\SplFileInfo;
@ -20,12 +20,18 @@ final class FilesFinder
*/
private $excludePaths = [];
/**
* @var FilesystemTweaker
*/
private $filesystemTweaker;
/**
* @param string[] $excludePaths
*/
public function __construct(array $excludePaths)
public function __construct(array $excludePaths, FilesystemTweaker $filesystemTweaker)
{
$this->excludePaths = $excludePaths;
$this->filesystemTweaker = $filesystemTweaker;
}
/**
@ -40,11 +46,15 @@ final class FilesFinder
return $this->fileInfosBySourceAndSuffixes[$cacheKey];
}
[$splFileInfos, $directories] = $this->splitSourceToDirectoriesAndFiles($source);
if (count($directories)) {
$splFileInfos = array_merge($splFileInfos, $this->findInDirectories($directories, $suffixes));
[$files, $directories] = $this->filesystemTweaker->splitSourceToDirectoriesAndFiles($source);
$splFileInfos = [];
foreach ($files as $file) {
$splFileInfos[] = new SplFileInfo($file, '', '');
}
$splFileInfos = array_merge($splFileInfos, $this->findInDirectories($directories, $suffixes));
return $this->fileInfosBySourceAndSuffixes[$cacheKey] = $splFileInfos;
}
@ -55,7 +65,11 @@ final class FilesFinder
*/
private function findInDirectories(array $directories, array $suffixes): array
{
$absoluteDirectories = $this->resolveAbsoluteDirectories($directories);
if (! count($directories)) {
return [];
}
$absoluteDirectories = $this->filesystemTweaker->resolveDirectoriesWithFnmatch($directories);
if (! $absoluteDirectories) {
return [];
}
@ -74,24 +88,6 @@ final class FilesFinder
return iterator_to_array($finder->getIterator());
}
private function ensureFileExists(string $file): void
{
if (file_exists($file)) {
return;
}
throw new DirectoryNotFoundException(sprintf('File "%s" was not found.', $file));
}
private function ensureDirectoryExists(string $directory): void
{
if (file_exists($directory)) {
return;
}
throw new DirectoryNotFoundException(sprintf('Directory "%s" was not found.', $directory));
}
/**
* @param string[] $suffixes
*/
@ -102,48 +98,6 @@ final class FilesFinder
return '#\.(' . $suffixesPattern . ')$#';
}
/**
* @todo decouple
* @param string[] $source
* @return string[][]|SplFileInfo[]
*/
private function splitSourceToDirectoriesAndFiles(array $source): array
{
$files = [];
$directories = [];
foreach ($source as $singleSource) {
if (is_file($singleSource)) {
$this->ensureFileExists($singleSource);
$files[] = new SplFileInfo($singleSource, '', '');
} else {
$directories[] = $singleSource;
}
}
return [$files, $directories];
}
/**
* @param string[] $directories
* @return string[]
*/
private function resolveAbsoluteDirectories(array $directories): array
{
$absoluteDirectories = [];
foreach ($directories as $directory) {
if (Strings::contains($directory, '*')) { // is fnmatch for directories
$absoluteDirectories = array_merge($absoluteDirectories, glob($directory, GLOB_ONLYDIR));
} else { // is classic directory
$this->ensureDirectoryExists($directory);
$absoluteDirectories[] = $directory;
}
}
return $absoluteDirectories;
}
private function addFilterWithExcludedPaths(Finder $finder): void
{
if (! $this->excludePaths) {