Passed
Push — master ( 904eb0...5301fa )
by Atanas
02:22
created

Route::getHandler()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 2
nc 1
nop 0
dl 0
loc 3
ccs 2
cts 2
cp 1
crap 1
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace WPEmerge\Routing;
4
5
use Exception;
6
use WPEmerge\Middleware\HasMiddlewareTrait;
7
use WPEmerge\Request;
8
use WPEmerge\Routing\Conditions\ConditionInterface;
9
use WPEmerge\Routing\Conditions\Factory;
10
use WPEmerge\Routing\Conditions\InvalidRouteConditionException;
11
use WPEmerge\Routing\Conditions\Url as UrlCondition;
12
13
/**
14
 * Represent a route
15
 */
16
class Route implements RouteInterface {
17
	use HasMiddlewareTrait;
18
19
	/**
20
	 * Allowed methods
21
	 *
22
	 * @var string[]
23
	 */
24
	protected $methods = [];
25
26
	/**
27
	 * Route target
28
	 *
29
	 * @var ConditionInterface
30
	 */
31
	protected $target = null;
32
33
	/**
34
	 * Route handler
35
	 *
36
	 * @var Handler
37
	 */
38
	protected $handler = null;
39
40
	/**
41
	 * Constructor
42
	 *
43
	 * @throws Exception
44
	 * @param  string[]        $methods
45
	 * @param  mixed           $target
46
	 * @param  string|\Closure $handler
47
	 */
48 3
	public function __construct( $methods, $target, $handler ) {
49 3
		if ( ! is_a( $target, ConditionInterface::class ) ) {
50
			try {
51 2
				$target = Factory::make( $target );
52 2
			} catch ( InvalidRouteConditionException $e ) {
53 1
				throw new Exception( 'Route target is not a valid route string or condition.' );
54
			}
55 1
		}
56
57 2
		$this->methods = $methods;
58 2
		$this->target = $target;
59 2
		$this->handler = new Handler( $handler );
60 2
	}
61
62
	/**
63
	 * Get allowed methods
64
	 *
65
	 * @return string[]
66
	 */
67 1
	public function getMethods() {
68 1
		return $this->methods;
69
	}
70
71
	/**
72
	 * Get target
73
	 *
74
	 * @return ConditionInterface
75
	 */
76 1
	public function getTarget() {
77 1
		return $this->target;
78
	}
79
80
	/**
81
	 * Get handler
82
	 *
83
	 * @return Handler
84
	 */
85 1
	public function getHandler() {
86 1
		return $this->handler;
87
	}
88
89
	/**
90
	 * {@inheritDoc}
91
	 */
92 2
	public function isSatisfied( Request $request ) {
93 2
		if ( ! in_array( $request->getMethod(), $this->methods) ) {
94 1
			return false;
95
		}
96 2
		return $this->target->isSatisfied( $request );
97
	}
98
99
	/**
100
	 * {@inheritDoc}
101
	 */
102
	public function handle( Request $request, $view ) {
103
		$arguments = array_merge( [$request, $view], $this->target->getArguments( $request ) );
104
		return $this->executeMiddleware( $this->getMiddleware(), $request, function() use ( $arguments ) {
105
			return call_user_func_array( [$this->handler, 'execute'], $arguments );
106
		} );
107
	}
108
109
	/**
110
	 * Add a rewrite rule to WordPress for url-based routes
111
	 *
112
	 * @throws Exception
113
	 * @param  string    $rewrite_to
114
	 * @return static    $this
115
	 */
116
	public function rewrite( $rewrite_to ) {
117
		if ( ! is_a( $this->target, UrlCondition::class ) ) {
118
			throw new Exception( 'Only routes with url targets can add rewrite rules.' );
119
		}
120
121
		$regex = $this->target->getValidationRegex( $this->target->getUrl(), false );
122
		$regex = preg_replace( '~^\^/~', '^', $regex ); // rewrite rules require NO leading slash
123
124
		add_filter( 'wpemerge.routing.rewrite_rules', function( $rules ) use ( $regex, $rewrite_to ) {
125
			$rules[ $regex ] = $rewrite_to;
126
			return $rules;
127
		} );
128
129
		return $this;
130
	}
131
}
132