-
Notifications
You must be signed in to change notification settings - Fork 0
/
Application.php
188 lines (168 loc) · 4.44 KB
/
Application.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
<?php
namespace alvin\phpmvc;
/**
* Core Application class.
*/
class Application {
/**
* Application instance.
* @var alvin\phpmvc\Application
*/
public static Application $app;
/**
* Root directory of application.
* @var string
*/
public ? string $rootDir = null;
/**
* Router instance.
* @var alvin\phpmvc\Router
*/
public Router $router;
/**
* Session instance.
* @var alvin\phpmvc\Session
*/
public Session $session;
/**
* Request instance.
* @var alvin\phpmvc\Request
*/
public Request $request;
/**
* Response instance.
* @var alvin\phpmvc\Response
*/
public Response $response;
/**
* View instance
* @var alvin\phpmvc\View
*/
public View $view;
/**
* FileStorage instance.
* @var alvin\phpmvc\FileStorage
*/
public FileStorage $fileStorage;
/**
* Middleware instance.
* @var alvin\phpmvc\Middleware
*/
public Middleware $middleware;
/**
* Creates a new Application instance.
*
* @param string $rootDir Root directory of the application
*/
public function __construct(string $rootDir) {
$this->setErrorHandlers();
$this->rootDir = $rootDir;
$this->router = new Router();
$this->request = new Request();
$this->response = new Response();
$this->session = new Session();
$this->view = new View();
$this->middleware = new Middleware();
$this->fileStorage = new FileStorage();
self::$app = $this;
}
/**
* Set global error handler and exception handler.
*
* Used for displaying the error on browser while in development mode
*
* @return void
*/
public function setErrorHandlers() {
if (getenv("ENV") == "development" || !getenv("ENV")) {
set_exception_handler([ExceptionHandler::class, 'handle']);
set_error_handler([ErrorHandler::class, 'handle']);
}
}
/**
* Set global middlewares.
*
* Used for registering middlewares that runs on every request
*
* @param object $middleware
* @return void
*/
public function use ($middleware) {
$this->middleware->add($middleware);
}
/**
* Set route level middlewares.
*
* Used for registering middlewares that runs only on specified routes
*
* @param object $middleware
* @return void
*/
public function middleware($middleware) {
$this->router->setRouteMiddleware($middleware);
}
/**
* Set controllers for get request.
*
* Used for specifying controllers for get requests on a particular route
*
* @param string $route The route to be handled
* @param string[]|string $resolvable An array with first element as class name and second element as the method to invoke or string as name of html view to render
* @return alvin\phpmvc\Application
*/
public function get(string $route, $resolvable) {
$this->checkInput($route, $resolvable);
$this->router->get($route, $resolvable);
return self::$app;
}
/**
* Set controllers for post request.
*
* Used for specifying controllers for post requests on a particular route
*
* @param string $route The route to be handled
* @param string[]|string $resolvable An array with first element as class name and second element as the method to invoke or string as name of html view to render
* @return alvin\phpmvc\Application
*/
public function post(string $route, $resolvable) {
$this->checkInput($route, $resolvable);
$this->router->post($route, $resolvable);
return self::$app;
}
/**
* Run application.
*
* Invokes all registered middlewares and then runs controller specified for current route
* @return void
*/
public function run() {
$this->middleware->resolve();
$this->router->resolve();
}
/**
* Checks input.
*
* check for any errors in args for get and post
*
* @param string $route
* @param string[]|string $resolvable
* @return void
*/
private function checkInput($route, $resolvable) {
if (strpos($route, '/') !== 0) {
throw new \InvalidArgumentException("The route should begin with a '/', $route given");
} else if (is_string($resolvable)) {
return;
} else if (is_array($resolvable)) {
if (sizeof($resolvable) !== 2) {
throw new \InvalidArgumentException("The array should contain exactly 2 elements");
}
if (!is_string($resolvable[1])) {
throw new \InvalidArgumentException("second element in the array should be a string, " . gettype($resolvable[1]) . " given");
}
return;
} else {
throw new \InvalidArgumentException("second argument should be an array containing a classname and method name,name of a view or a anonymous function");
}
}
}