Total Complexity | 58 |
Total Lines | 301 |
Duplicated Lines | 0 % |
Changes | 0 |
Complex classes like Laravel often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes.
Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.
While breaking up the class, it is a good idea to analyze how other classes use Laravel, and based on these observations, apply Extract Interface, too.
1 | <?php |
||
12 | class Laravel |
||
13 | { |
||
14 | protected $app; |
||
15 | |||
16 | /** |
||
17 | * @var HttpKernel $kernel |
||
18 | */ |
||
19 | protected $kernel; |
||
20 | |||
21 | protected static $snapshotKeys = ['config', 'cookie', 'auth', /*'auth.password'*/]; |
||
22 | |||
23 | /** |
||
24 | * @var array $snapshots |
||
25 | */ |
||
26 | protected $snapshots = []; |
||
27 | |||
28 | protected $conf = []; |
||
29 | |||
30 | protected static $staticBlackList = [ |
||
31 | '/index.php' => 1, |
||
32 | '/.htaccess' => 1, |
||
33 | '/web.config' => 1, |
||
34 | ]; |
||
35 | |||
36 | private $rawGlobals = []; |
||
37 | |||
38 | public function __construct(array $conf = []) |
||
41 | } |
||
42 | |||
43 | public function prepareLaravel() |
||
44 | { |
||
45 | static::autoload($this->conf['root_path']); |
||
46 | $this->createApp(); |
||
47 | $this->createKernel(); |
||
48 | $this->setLaravel(); |
||
49 | $this->loadAllConfigurations(); |
||
50 | $this->bootstrap(); |
||
51 | $this->saveSnapshots(); |
||
52 | } |
||
53 | |||
54 | public static function autoload($rootPath) |
||
55 | { |
||
56 | $autoload = $rootPath . '/bootstrap/autoload.php'; |
||
57 | if (file_exists($autoload)) { |
||
58 | require_once $autoload; |
||
59 | } else { |
||
60 | require_once $rootPath . '/vendor/autoload.php'; |
||
61 | } |
||
62 | } |
||
63 | |||
64 | protected function createApp() |
||
67 | } |
||
68 | |||
69 | protected function createKernel() |
||
73 | } |
||
74 | } |
||
75 | |||
76 | protected function setLaravel() |
||
87 | } |
||
88 | |||
89 | protected function bootstrap() |
||
90 | { |
||
91 | if ($this->conf['is_lumen']) { |
||
92 | if (method_exists($this->app, 'boot')) { |
||
93 | $this->app->boot(); |
||
94 | } |
||
95 | } else { |
||
96 | $this->app->make(ConsoleKernel::class)->bootstrap(); |
||
97 | } |
||
98 | } |
||
99 | |||
100 | public function loadAllConfigurations() |
||
101 | { |
||
102 | if (!$this->conf['is_lumen']) { |
||
103 | return; |
||
104 | } |
||
105 | |||
106 | $cfgPaths = [ |
||
107 | // Framework default configuration |
||
108 | $this->conf['root_path'] . '/vendor/laravel/lumen-framework/config/', |
||
109 | // App configuration |
||
110 | $this->conf['root_path'] . '/config/', |
||
111 | ]; |
||
112 | $keys = []; |
||
113 | foreach ($cfgPaths as $cfgPath) { |
||
114 | $configs = (array)glob($cfgPath . '*.php'); |
||
115 | foreach ($configs as $config) { |
||
116 | $config = substr(basename($config), 0, -4); |
||
117 | $keys[$config] = $config; |
||
118 | } |
||
119 | } |
||
120 | foreach ($keys as $key) { |
||
121 | $this->app->configure($key); |
||
122 | } |
||
123 | } |
||
124 | |||
125 | protected function saveSnapshots() |
||
126 | { |
||
127 | $this->snapshots['config'] = $this->app['config']->all(); |
||
128 | } |
||
129 | |||
130 | protected function applySnapshots() |
||
131 | { |
||
132 | $this->app['config']->set($this->snapshots['config']); |
||
133 | if (isset($this->app['cookie'])) { |
||
134 | foreach ($this->app['cookie']->getQueuedCookies() as $name => $cookie) { |
||
135 | $this->app['cookie']->unqueue($name); |
||
136 | } |
||
137 | } |
||
138 | } |
||
139 | |||
140 | public function getRawGlobals() |
||
143 | } |
||
144 | |||
145 | public function handleDynamic(IlluminateRequest $request) |
||
146 | { |
||
147 | $this->applySnapshots(); |
||
148 | |||
149 | ob_start(); |
||
150 | |||
151 | if ($this->conf['is_lumen']) { |
||
152 | $response = $this->app->dispatch($request); |
||
153 | if ($response instanceof SymfonyResponse) { |
||
154 | $content = $response->getContent(); |
||
155 | } else { |
||
156 | $content = (string)$response; |
||
157 | } |
||
158 | |||
159 | $laravelReflect = new \ReflectionObject($this->app); |
||
160 | $middleware = $laravelReflect->getProperty('middleware'); |
||
161 | $middleware->setAccessible(true); |
||
162 | if (!empty($middleware->getValue($this->app))) { |
||
163 | $callTerminableMiddleware = $laravelReflect->getMethod('callTerminableMiddleware'); |
||
164 | $callTerminableMiddleware->setAccessible(true); |
||
165 | $callTerminableMiddleware->invoke($this->app, $response); |
||
166 | } |
||
167 | } else { |
||
168 | $response = $this->kernel->handle($request); |
||
169 | $content = $response->getContent(); |
||
170 | $this->kernel->terminate($request, $response); |
||
171 | } |
||
172 | |||
173 | // prefer content in response, secondly ob |
||
174 | if (strlen($content) === 0 && ob_get_length() > 0) { |
||
175 | $response->setContent(ob_get_contents()); |
||
176 | } |
||
177 | |||
178 | ob_end_clean(); |
||
179 | |||
180 | return $response; |
||
181 | } |
||
182 | |||
183 | public function handleStatic(IlluminateRequest $request) |
||
184 | { |
||
185 | $uri = $request->getRequestUri(); |
||
186 | if (isset(self::$staticBlackList[$uri])) { |
||
187 | return false; |
||
188 | } |
||
189 | |||
190 | $publicPath = $this->conf['static_path']; |
||
191 | $requestFile = $publicPath . $uri; |
||
192 | if (is_file($requestFile)) { |
||
193 | return $this->createStaticResponse($requestFile, $request); |
||
194 | } elseif (is_dir($requestFile)) { |
||
195 | $indexFile = $this->lookupIndex($requestFile); |
||
196 | if ($indexFile === false) { |
||
197 | return false; |
||
198 | } else { |
||
199 | return $this->createStaticResponse($indexFile, $request); |
||
200 | } |
||
201 | } else { |
||
202 | return false; |
||
203 | } |
||
204 | } |
||
205 | |||
206 | protected function lookupIndex($folder) |
||
207 | { |
||
208 | $folder = rtrim($folder, '/') . '/'; |
||
209 | foreach (['index.html', 'index.htm'] as $index) { |
||
210 | $tmpFile = $folder . $index; |
||
211 | if (is_file($tmpFile)) { |
||
212 | return $tmpFile; |
||
213 | } |
||
214 | } |
||
215 | return false; |
||
216 | } |
||
217 | |||
218 | public function createStaticResponse($requestFile, IlluminateRequest $request) |
||
219 | { |
||
220 | $response = new BinaryFileResponse($requestFile); |
||
221 | $response->prepare($request); |
||
222 | $response->isNotModified($request); |
||
223 | return $response; |
||
224 | } |
||
225 | |||
226 | public function reRegisterServiceProvider($providerCls, array $clearFacades = [], $force = false) |
||
227 | { |
||
228 | if (class_exists($providerCls, false) || $force) { |
||
229 | if ($this->conf['is_lumen']) { |
||
230 | $laravelReflect = new \ReflectionObject($this->app); |
||
231 | $loadedProviders = $laravelReflect->getProperty('loadedProviders'); |
||
232 | $loadedProviders->setAccessible(true); |
||
233 | $oldLoadedProviders = $loadedProviders->getValue($this->app); |
||
234 | unset($oldLoadedProviders[get_class(new $providerCls($this->app))]); |
||
235 | $loadedProviders->setValue($this->app, $oldLoadedProviders); |
||
236 | } |
||
237 | foreach ($clearFacades as $facade) { |
||
238 | Facade::clearResolvedInstance($facade); |
||
239 | } |
||
240 | $this->app->register($providerCls, [], true); |
||
241 | } |
||
242 | } |
||
243 | |||
244 | public function cleanRequest(IlluminateRequest $request) |
||
245 | { |
||
246 | // Clean laravel session |
||
247 | if ($request->hasSession()) { |
||
248 | $session = $request->getSession(); |
||
249 | if (method_exists($session, 'clear')) { |
||
250 | $session->clear(); |
||
251 | } elseif (method_exists($session, 'flush')) { |
||
252 | $session->flush(); |
||
253 | } |
||
254 | // TODO: clear session for other versions |
||
255 | } |
||
256 | |||
257 | // Re-register auth |
||
258 | //$this->reRegisterServiceProvider('\Illuminate\Auth\AuthServiceProvider', ['auth', 'auth.driver']); |
||
259 | //$this->reRegisterServiceProvider('\Illuminate\Auth\Passwords\PasswordResetServiceProvider', ['auth.password']); |
||
260 | |||
261 | // Re-register passport |
||
262 | $this->reRegisterServiceProvider('\Laravel\Passport\PassportServiceProvider'); |
||
263 | |||
264 | // Re-register some singleton providers |
||
265 | foreach ($this->conf['register_providers'] as $provider) { |
||
266 | $this->reRegisterServiceProvider($provider); |
||
267 | } |
||
268 | |||
269 | // Clear request |
||
270 | $this->app->forgetInstance('request'); |
||
271 | Facade::clearResolvedInstance('request'); |
||
272 | |||
273 | //... |
||
274 | } |
||
275 | |||
276 | public function fireEvent($name, array $params = []) |
||
277 | { |
||
278 | $params[] = $this->app; |
||
279 | return $this->app->events->fire($name, $params); |
||
280 | } |
||
281 | |||
282 | public function bindRequest(IlluminateRequest $request) |
||
283 | { |
||
284 | $this->app->instance('request', $request); |
||
285 | } |
||
286 | |||
287 | public function bindSwoole($swoole) |
||
288 | { |
||
289 | $this->app->singleton('swoole', function () use ($swoole) { |
||
290 | return $swoole; |
||
291 | }); |
||
292 | } |
||
293 | |||
294 | public function make($abstract, array $parameters = []) |
||
297 | } |
||
298 | |||
299 | public function resetSession() |
||
300 | { |
||
301 | if (!empty($this->app['session'])) { |
||
302 | $reflection = new \ReflectionObject($this->app['session']); |
||
303 | $drivers = $reflection->getProperty('drivers'); |
||
304 | $drivers->setAccessible(true); |
||
305 | $drivers->setValue($this->app['session'], []); |
||
306 | } |
||
307 | } |
||
308 | |||
309 | public function saveSession() |
||
313 | } |
||
314 | } |
||
315 | } |
||
316 |