Passed
Branch master (699e14)
by refat
03:14
created

Route   A

Complexity

Total Complexity 23

Size/Duplication

Total Lines 169
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 0

Importance

Changes 0
Metric Value
dl 0
loc 169
rs 10
c 0
b 0
f 0
wmc 23
lcom 1
cbo 0

14 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A add() 0 17 1
A setPrefix() 0 9 3
A setAction() 0 7 2
A setMiddleware() 0 10 2
A getAction() 0 8 2
A generatePattern() 0 8 1
A group() 0 22 1
A package() 0 11 1
A getProperRoute() 0 20 4
A fullMatch() 0 4 2
A isMatchingPattern() 0 7 1
A getArgumentsFor() 0 10 1
A getCurrent() 0 4 1
1
<?php
2
3
namespace System;
4
5
class Route
6
{
7
    private $app;
8
9
    private $routes = [];
10
11
    public $current = [];
12
13
    private $prefix;
14
15
    private $basController;
16
17
    private $groupMiddleware = [];
18
19
    public function __construct(Application $app)
20
    {
21
        $this->app = $app;
22
    }
23
24
    public function add($url, $action, $requestMethods = ['GET'], $middleware = [])
25
    {
26
        $url = $this->setPrefix($url);
27
        $action = $this->setAction($action);
28
        $middleware = $this->setMiddleware($middleware);
29
        $routes = [
30
            'url' => $url,
31
            'pattern' => $this->generatePattern($url),
32
            'action' => $this->getAction($action),
33
            'method' => $requestMethods,
34
            'middleware' => $middleware
35
        ];
36
37
        $this->routes[] = $routes;
38
39
        return $this;
40
    }
41
42
    private function setPrefix($url)
43
    {
44
        if ($this->prefix && $this->prefix !== '/') {
45
            $url = $this->prefix . $url;
46
            $url = rtrim($url, '/');
47
        }
48
49
        return $url;
50
    }
51
52
    private function setAction($action)
53
    {
54
        if ($this->basController) {
55
            $action = $this->basController . '/' . $action;
56
        }
57
        return $action;
58
    }
59
60
    private function setMiddleware($middleware)
61
    {
62
        if (!is_array($middleware)) {
63
            $middleware = [$middleware];
64
        }
65
66
        $middleware = array_merge($this->groupMiddleware, $middleware);
67
68
        return $middleware;
69
    }
70
71
    private function getAction($action)
72
    {
73
        $action = str_replace('/', '\\', $action);
74
        $action = (strpos($action, '@') != 0) ? $action : $action . '@index';
75
        $action = explode('@', $action);
76
77
        return $action;
78
    }
79
80
    private function generatePattern($url)
81
    {
82
        $pattern = '#^';
83
        $pattern .= str_replace([':text', ':id'], ['([a-zA-Z0-9-]+)', '(\d+)'], strtolower($url));
84
        $pattern .= '$#';
85
86
        return $pattern;
87
    }
88
89
    public function group($groupOptions, callable $callback)
90
    {
91
        $prefix = $groupOptions['prefix'];
92
        $controller = $groupOptions['controller'];
93
        $middleware = $groupOptions['middleware'];
94
95
        $this->prefix = $prefix;
96
97
        $this->basController = $controller;
98
99
        $this->groupMiddleware = $middleware;
100
101
        $callback($this);
102
103
        $this->prefix = '';
104
105
        $this->basController = '';
106
107
        $this->groupMiddleware = [];
108
109
        return $this;
110
    }
111
112
    public function package($url, $controller, $middlewares = [])
113
    {
114
        $this->add($url, $controller);
115
        $this->add("$url/:id", "$controller@row", ['GET'], $middlewares['row'] ?? []);
116
        $this->add("$url/new", "$controller@new", ['GET'], $middlewares['new'] ?? []);
117
        $this->add("$url/add", "$controller@add", ['POST'], $middlewares['add'] ?? []);
118
        $this->add("$url/update/:id", "$controller@update", ['POST'], $middlewares['update'] ?? []);
119
        $this->add("$url/delete/:id", "$controller@delete", ['POST'], $middlewares['delete'] ?? []);
120
121
        return $this;
122
    }
123
124
    public function getProperRoute()
125
    {
126
        foreach ($this->routes as $route) {
127
            if ($this->fullMatch($route['pattern'], $route['method'])) {
128
                $this->current = $route;
129
130
                $continue = $this->app->request->canRequestContinue($route['middleware']);
0 ignored issues
show
Documentation introduced by
The property request does not exist on object<System\Application>. Since you implemented __get, maybe consider adding a @property annotation.

Since your code implements the magic getter _get, this function will be called for any read access on an undefined variable. You can add the @property annotation to your class or interface to document the existence of this variable.

<?php

/**
 * @property int $x
 * @property int $y
 * @property string $text
 */
class MyLabel
{
    private $properties;

    private $allowedProperties = array('x', 'y', 'text');

    public function __get($name)
    {
        if (isset($properties[$name]) && in_array($name, $this->allowedProperties)) {
            return $properties[$name];
        } else {
            return null;
        }
    }

    public function __set($name, $value)
    {
        if (in_array($name, $this->allowedProperties)) {
            $properties[$name] = $value;
        } else {
            throw new \LogicException("Property $name is not defined.");
        }
    }

}

If the property has read access only, you can use the @property-read annotation instead.

Of course, you may also just have mistyped another name, in which case you should fix the error.

See also the PhpDoc documentation for @property.

Loading history...
131
132
                if ($continue) {
133
                    list($controller, $method) = $route['action'];
134
135
                    $arguments = $this->getArgumentsFor($route['pattern']);
136
137
                    return (string) $this->app->load->action($controller, $method, $arguments);
0 ignored issues
show
Documentation introduced by
The property load does not exist on object<System\Application>. Since you implemented __get, maybe consider adding a @property annotation.

Since your code implements the magic getter _get, this function will be called for any read access on an undefined variable. You can add the @property annotation to your class or interface to document the existence of this variable.

<?php

/**
 * @property int $x
 * @property int $y
 * @property string $text
 */
class MyLabel
{
    private $properties;

    private $allowedProperties = array('x', 'y', 'text');

    public function __get($name)
    {
        if (isset($properties[$name]) && in_array($name, $this->allowedProperties)) {
            return $properties[$name];
        } else {
            return null;
        }
    }

    public function __set($name, $value)
    {
        if (in_array($name, $this->allowedProperties)) {
            $properties[$name] = $value;
        } else {
            throw new \LogicException("Property $name is not defined.");
        }
    }

}

If the property has read access only, you can use the @property-read annotation instead.

Of course, you may also just have mistyped another name, in which case you should fix the error.

See also the PhpDoc documentation for @property.

Loading history...
138
                }
139
                break;
140
            }
141
        }
142
        return notFoundPage();
143
    }
144
145
    private function fullMatch($pattern, $methods)
146
    {
147
        return $this->isMatchingPattern($pattern) && $this->app->request->isMatchingRequestMethod($methods);
0 ignored issues
show
Documentation introduced by
The property request does not exist on object<System\Application>. Since you implemented __get, maybe consider adding a @property annotation.

Since your code implements the magic getter _get, this function will be called for any read access on an undefined variable. You can add the @property annotation to your class or interface to document the existence of this variable.

<?php

/**
 * @property int $x
 * @property int $y
 * @property string $text
 */
class MyLabel
{
    private $properties;

    private $allowedProperties = array('x', 'y', 'text');

    public function __get($name)
    {
        if (isset($properties[$name]) && in_array($name, $this->allowedProperties)) {
            return $properties[$name];
        } else {
            return null;
        }
    }

    public function __set($name, $value)
    {
        if (in_array($name, $this->allowedProperties)) {
            $properties[$name] = $value;
        } else {
            throw new \LogicException("Property $name is not defined.");
        }
    }

}

If the property has read access only, you can use the @property-read annotation instead.

Of course, you may also just have mistyped another name, in which case you should fix the error.

See also the PhpDoc documentation for @property.

Loading history...
148
    }
149
150
    private function isMatchingPattern($pattern)
151
    {
152
        $url = $this->app->request->url();
0 ignored issues
show
Documentation introduced by
The property request does not exist on object<System\Application>. Since you implemented __get, maybe consider adding a @property annotation.

Since your code implements the magic getter _get, this function will be called for any read access on an undefined variable. You can add the @property annotation to your class or interface to document the existence of this variable.

<?php

/**
 * @property int $x
 * @property int $y
 * @property string $text
 */
class MyLabel
{
    private $properties;

    private $allowedProperties = array('x', 'y', 'text');

    public function __get($name)
    {
        if (isset($properties[$name]) && in_array($name, $this->allowedProperties)) {
            return $properties[$name];
        } else {
            return null;
        }
    }

    public function __set($name, $value)
    {
        if (in_array($name, $this->allowedProperties)) {
            $properties[$name] = $value;
        } else {
            throw new \LogicException("Property $name is not defined.");
        }
    }

}

If the property has read access only, you can use the @property-read annotation instead.

Of course, you may also just have mistyped another name, in which case you should fix the error.

See also the PhpDoc documentation for @property.

Loading history...
153
        $url = strtolower($url);
154
155
        return preg_match($pattern, $url);
156
    }
157
158
    private function getArgumentsFor($pattern)
159
    {
160
        $url = $this->app->request->url();
0 ignored issues
show
Documentation introduced by
The property request does not exist on object<System\Application>. Since you implemented __get, maybe consider adding a @property annotation.

Since your code implements the magic getter _get, this function will be called for any read access on an undefined variable. You can add the @property annotation to your class or interface to document the existence of this variable.

<?php

/**
 * @property int $x
 * @property int $y
 * @property string $text
 */
class MyLabel
{
    private $properties;

    private $allowedProperties = array('x', 'y', 'text');

    public function __get($name)
    {
        if (isset($properties[$name]) && in_array($name, $this->allowedProperties)) {
            return $properties[$name];
        } else {
            return null;
        }
    }

    public function __set($name, $value)
    {
        if (in_array($name, $this->allowedProperties)) {
            $properties[$name] = $value;
        } else {
            throw new \LogicException("Property $name is not defined.");
        }
    }

}

If the property has read access only, you can use the @property-read annotation instead.

Of course, you may also just have mistyped another name, in which case you should fix the error.

See also the PhpDoc documentation for @property.

Loading history...
161
162
        preg_match($pattern, $url, $matches);
163
164
        array_shift($matches);
165
166
        return $matches;
167
    }
168
169
    public function getCurrent($key)
170
    {
171
        return $this->current[$key];
172
    }
173
}
174