Passed
Push — master ( 83996b...17a193 )
by Jean-Christophe
09:22
created

ControllerParser::parseMethods()   B

Complexity

Conditions 11
Paths 15

Size

Total Lines 17
Code Lines 13

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 12
CRAP Score 11

Importance

Changes 0
Metric Value
eloc 13
dl 0
loc 17
ccs 12
cts 12
cp 1
rs 7.3166
c 0
b 0
f 0
cc 11
nc 15
nop 4
crap 11

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
namespace Ubiquity\cache\parser;
4
5
use Ubiquity\orm\parser\Reflexion;
6
use Ubiquity\utils\base\UString;
7
use Ubiquity\annotations\router\RouteAnnotation;
8
use Ubiquity\cache\ClassUtils;
9
use Ubiquity\utils\base\UArray;
10
11
/**
12
 * Scans a controller to detect routes defined by annotations.
13
 * Ubiquity\cache\parser$ControllerParser
14
 * This class is part of Ubiquity
15
 *
16
 * @author jcheron <[email protected]>
17
 * @version 1.0.6
18
 *
19
 */
20
class ControllerParser {
21
	use ControllerParserPathTrait;
22
	private $controllerClass;
23
	private $mainRouteClass;
24
	private $routesMethods = [ ];
25
	private $rest = false;
26
	private static $excludeds = [ "__construct","isValid","initialize","finalize","onInvalidControl","loadView","forward","redirectToRoute" ];
27
28 16
	public function parse($controllerClass) {
29 16
		$automated = false;
30 16
		$inherited = false;
31 16
		$this->controllerClass = $controllerClass;
32 16
		$restAnnotsClass = [ ];
33 16
		$reflect = new \ReflectionClass ( $controllerClass );
34 16
		if (! $reflect->isAbstract () && $reflect->isSubclassOf ( "Ubiquity\controllers\Controller" )) {
35
			try {
36 16
				$annotsClass = Reflexion::getAnnotationClass ( $controllerClass, "@route" );
37 16
				$restAnnotsClass = Reflexion::getAnnotationClass ( $controllerClass, "@rest" );
38
			} catch ( \Exception $e ) {
39
				// When controllerClass generates an exception
40
			}
41 16
			$this->rest = \sizeof ( $restAnnotsClass ) > 0;
42 16
			if (isset ( $annotsClass ) && \sizeof ( $annotsClass ) > 0) {
43 16
				$this->mainRouteClass = $annotsClass [0];
44 16
				$inherited = $this->mainRouteClass->inherited;
45 16
				$automated = $this->mainRouteClass->automated;
46
			}
47 16
			$methods = Reflexion::getMethods ( $controllerClass, \ReflectionMethod::IS_PUBLIC );
48 16
			$this->parseMethods ( $methods, $controllerClass, $inherited, $automated );
49
		}
50 16
	}
51
52 16
	private function parseMethods($methods, $controllerClass, $inherited, $automated) {
53 16
		foreach ( $methods as $method ) {
54 16
			if ($method->getDeclaringClass ()->getName () === $controllerClass || $inherited) {
55
				try {
56 16
					$annots = Reflexion::getAnnotationsMethod ( $controllerClass, $method->name, [ "@route","@get","@post" ] );
57 16
					if (sizeof ( $annots ) > 0) {
58 16
						foreach ( $annots as $annot ) {
59 16
							$this->parseAnnot ( $annot, $method );
60
						}
61 16
						$this->routesMethods [$method->name] = [ "annotations" => $annots,"method" => $method ];
62
					} else {
63 16
						if ($automated) {
64 16
							if ($method->class !== 'Ubiquity\\controllers\\Controller' && \array_search ( $method->name, self::$excludeds ) === false && ! UString::startswith ( $method->name, "_" ))
65 16
								$this->routesMethods [$method->name] = [ "annotations" => $this->generateRouteAnnotationFromMethod ( $method ),"method" => $method ];
66
						}
67
					}
68 1
				} catch ( \Exception $e ) {
69
					// When controllerClass generates an exception
70
				}
71
			}
72
		}
73 16
	}
74
75 16
	private function parseAnnot(&$annot, $method) {
76 16
		if (UString::isNull ( $annot->path )) {
77 16
			$newAnnot = $this->generateRouteAnnotationFromMethod ( $method );
78 16
			$annot->path = $newAnnot [0]->path;
79
		} else {
80 16
			$annot->path = $this->parseMethodPath ( $method, $annot->path );
81
		}
82 16
	}
83
84 16
	private function generateRouteAnnotationFromMethod(\ReflectionMethod $method) {
85 16
		$annot = new RouteAnnotation ();
86 16
		$annot->path = self::getPathFromMethod ( $method );
87 16
		return [ $annot ];
88
	}
89
90 16
	public function asArray() {
91 16
		$result = [ ];
92 16
		$prefix = "";
93 16
		$httpMethods = false;
94 16
		if ($this->mainRouteClass) {
95 16
			if (isset ( $this->mainRouteClass->path ))
96 16
				$prefix = $this->mainRouteClass->path;
97 16
			if (isset ( $this->mainRouteClass->methods )) {
98
				$httpMethods = $this->mainRouteClass->methods;
99
				if ($httpMethods !== null) {
100
					if (\is_string ( $httpMethods ))
101
						$httpMethods = [ $httpMethods ];
102
				}
103
			}
104
		}
105 16
		foreach ( $this->routesMethods as $method => $arrayAnnotsMethod ) {
106 16
			$routeAnnotations = $arrayAnnotsMethod ["annotations"];
107
108 16
			foreach ( $routeAnnotations as $routeAnnotation ) {
109 16
				$params = [ "path" => $routeAnnotation->path,"methods" => $routeAnnotation->methods,"name" => $routeAnnotation->name,"cache" => $routeAnnotation->cache,"duration" => $routeAnnotation->duration,"requirements" => $routeAnnotation->requirements,"priority" => $routeAnnotation->priority ];
110 16
				self::parseRouteArray ( $result, $this->controllerClass, $params, $arrayAnnotsMethod ["method"], $method, $prefix, $httpMethods );
111
			}
112
		}
113
		uasort ( $result, function ($item1, $item2) {
114 16
			return UArray::getRecursive ( $item2, "priority", 0 ) <=> UArray::getRecursive ( $item1, "priority", 0 );
115 16
		} );
116 16
		UArray::removeRecursive ( $result, "priority" );
117 16
		return $result;
118
	}
119
120 36
	public static function parseRouteArray(&$result, $controllerClass, $routeArray, \ReflectionMethod $method, $methodName, $prefix = "", $httpMethods = NULL) {
121 36
		if (! isset ( $routeArray ["path"] )) {
122
			$routeArray ["path"] = self::getPathFromMethod ( $method );
123
		}
124 36
		$pathParameters = self::addParamsPath ( $routeArray ["path"], $method, $routeArray ["requirements"] );
125 36
		$name = $routeArray ["name"];
126 36
		if (! isset ( $name )) {
127 16
			$name = UString::cleanAttribute ( ClassUtils::getClassSimpleName ( $controllerClass ) . "_" . $methodName );
128
		}
129 36
		$cache = $routeArray ["cache"];
130 36
		$duration = $routeArray ["duration"];
131 36
		$path = $pathParameters ["path"];
132 36
		$parameters = $pathParameters ["parameters"];
133 36
		$priority = $routeArray ["priority"];
134 36
		$callback = $routeArray ["callback"] ?? null;
135 36
		$path = self::cleanpath ( $prefix, $path );
136 36
		if (isset ( $routeArray ["methods"] ) && \is_array ( $routeArray ["methods"] )) {
137 16
			self::createRouteMethod ( $result, $controllerClass, $path, $routeArray ["methods"], $methodName, $parameters, $name, $cache, $duration, $priority, $callback );
138 36
		} elseif (\is_array ( $httpMethods )) {
139
			self::createRouteMethod ( $result, $controllerClass, $path, $httpMethods, $methodName, $parameters, $name, $cache, $duration, $priority, $callback );
140
		} else {
141 36
			$v = [ "controller" => $controllerClass,"action" => $methodName,"parameters" => $parameters,"name" => $name,"cache" => $cache,"duration" => $duration,"priority" => $priority ];
142 36
			if (isset ( $callback )) {
143
				$v ['callback'] = $callback;
144
			}
145 36
			$result [$path] = $v;
146
		}
147 36
	}
148
149 16
	private static function createRouteMethod(&$result, $controllerClass, $path, $httpMethods, $method, $parameters, $name, $cache, $duration, $priority, $callback = null) {
150 16
		foreach ( $httpMethods as $httpMethod ) {
151 16
			$v = [ "controller" => $controllerClass,"action" => $method,"parameters" => $parameters,"name" => $name,"cache" => $cache,"duration" => $duration,"priority" => $priority ];
152 16
			if (isset ( $callback )) {
153
				$v ['callback'] = $callback;
154
			}
155 16
			$result [$path] [$httpMethod] = $v;
156
		}
157 16
	}
158
159 16
	public function isRest() {
160 16
		return $this->rest;
161
	}
162
}
163