Passed
Pull Request — master (#196)
by Rustam
13:36
created

FileRoutesProvider::getRoutes()   B

Complexity

Conditions 10
Paths 6

Size

Total Lines 45
Code Lines 25

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 30
CRAP Score 10

Importance

Changes 2
Bugs 0 Features 0
Metric Value
cc 10
eloc 25
c 2
b 0
f 0
nc 6
nop 0
dl 0
loc 45
ccs 30
cts 30
cp 1
crap 10
rs 7.6666

How to fix   Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Router\Provider;
6
7
use Closure;
8
use Yiisoft\Router\Group;
9
use Yiisoft\Router\Route;
10
11
/**
12
 * A file provider provides routes from a file or directory of files.
13
 */
14
final class FileRoutesProvider implements RoutesProviderInterface
15
{
16 4
    public function __construct(private string $file, private array $scope = [])
17
    {
18 4
    }
19
20 4
    public function getRoutes(): array
21
    {
22
        /** @var Closure $scopeRequire */
23 4
        $scopeRequire = Closure::bind(static function (string $file, array $scope): mixed {
24 3
            extract($scope, EXTR_SKIP);
25
            /**
26
             * @psalm-suppress UnresolvableInclude
27
             */
28 3
            return require $file;
29 4
        }, null);
30 4
        if (!file_exists($this->file)) {
31 1
            throw new \RuntimeException(
32 1
                'Failed to provide routes from "' . $this->file . '". File or directory not found.'
33 1
            );
34
        }
35 3
        if (is_dir($this->file) && !is_file($this->file)) {
36 1
            $directoryRoutes = [];
37 1
            $files = new \CallbackFilterIterator(
38 1
                new \FilesystemIterator(
39 1
                    $this->file,
40 1
                    \FilesystemIterator::SKIP_DOTS | \FilesystemIterator::FOLLOW_SYMLINKS
41 1
                ),
42 1
                fn (\SplFileInfo $fileInfo) => $fileInfo->isFile() && $fileInfo->getExtension() === 'php'
43 1
            );
44
            /** @var \SplFileInfo[] $files */
45 1
            foreach ($files as $file) {
46
                /** @var mixed $fileRoutes */
47 1
                $fileRoutes = $scopeRequire($file->getRealPath(), $this->scope);
48 1
                if (is_array($fileRoutes) && $this->isRoutesAreValid($fileRoutes)) {
49 1
                    array_push(
50 1
                        $directoryRoutes,
51 1
                        ...$fileRoutes
52 1
                    );
53
                }
54
            }
55 1
            return $directoryRoutes;
56
        }
57
58
        /** @var mixed $routes */
59 2
        $routes = $scopeRequire($this->file, $this->scope);
60 2
        if (is_array($routes) && $this->isRoutesAreValid($routes)) {
61 1
            return $routes;
62
        }
63
64 1
        return [];
65
    }
66
67
    /**
68
     * @psalm-assert-if-true Route[]|Group[] $routes
69
     */
70 3
    private function isRoutesAreValid(array $routes): bool
71
    {
72 3
        foreach ($routes as $route) {
73
            if (
74 3
                !is_a($route, Route::class, true) && !is_a($route, Group::class, true)
75
            ) {
76 2
                return false;
77
            }
78
        }
79 2
        return true;
80
    }
81
}
82