GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Completed
Push — master ( 6e3bfc...c4e853 )
by やかみ
01:42
created

Request::isDelete()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
cc 1
eloc 2
nc 1
nop 0
dl 0
loc 4
ccs 0
cts 2
cp 0
crap 2
rs 10
c 0
b 0
f 0
1
<?php
2
/**
3
 * Kotori.php
4
 *
5
 * A Tiny Model-View-Controller PHP Framework
6
 *
7
 * This content is released under the Apache 2 License
8
 *
9
 * Copyright (c) 2015-2017 Kotori Technology. All rights reserved.
10
 *
11
 * Licensed under the Apache License, Version 2.0 (the "License");
12
 * you may not use this file except in compliance with the License.
13
 * You may obtain a copy of the License at
14
 *
15
 *     http://www.apache.org/licenses/LICENSE-2.0
16
 *
17
 * Unless required by applicable law or agreed to in writing, software
18
 * distributed under the License is distributed on an "AS IS" BASIS,
19
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
20
 * See the License for the specific language governing permissions and
21
 * limitations under the License.
22
 */
23
24
/**
25
 * Request Class
26
 *
27
 * @package     Kotori
28
 * @subpackage  Http
29
 * @author      Kokororin
30
 * @link        https://kotori.love
31
 */
32
namespace Kotori\Http;
33
34
use Kotori\Core\Container;
35
use Kotori\Debug\Hook;
36
use Kotori\Exception\NotFoundException;
37
38
class Request
39
{
40
    /**
41
     * Ip address
42
     *
43
     * @var mixed
44
     */
45
    protected $ip = null;
46
47
    /**
48
     * Http headers
49
     *
50
     * @var array
51
     */
52
    protected $headers = [];
53
54
    /**
55
     * Class constructor
56
     *
57
     * Initialize Request.
58
     *
59
     * @return void
0 ignored issues
show
Comprehensibility Best Practice introduced by
Adding a @return annotation to constructors is generally not recommended as a constructor does not have a meaningful return value.

Adding a @return annotation to a constructor is not recommended, since a constructor does not have a meaningful return value.

Please refer to the PHP core documentation on constructors.

Loading history...
60
     */
61
    public function __construct()
62
    {
63
        Hook::listen(__CLASS__);
64
    }
65
66
    /**
67
     * Internal method used to retrieve values from given arrays.
68
     *
69
     * @param  array $source
70
     * @param  mixed $key
71
     * @param  mixed $default
72
     * @return mixed
73
     */
74
    protected function getRequestParams(&$source, $key = null, $default = null)
75
    {
76
        // If $key is NULL, it means that the whole $source is requested
77
        if (!isset($key) || $key == null) {
78
            $key = array_keys($source);
79
        }
80
81
        if (is_array($key)) {
82
            $output = [];
83
            foreach ($key as $k) {
84
                $output[$k] = $this->getRequestParams($source, $k);
85
            }
86
87
            return $output;
88
        }
89
90
        if (isset($source[$key])) {
91
            $value = $source[$key];
92
        } else {
93
            return $default;
94
        }
95
96
        return $value;
97
98
    }
99
100
    /**
101
     * Fetch an item from the GET array
102
     *
103
     * @param  mixed $key
104
     * @return mixed
105
     */
106
    public function get($key = null, $default = null)
0 ignored issues
show
Coding Style introduced by
get uses the super-global variable $_GET which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
107
    {
108
        return $this->getRequestParams($_GET, $key, $default);
109
    }
110
111
    /**
112
     * Fetch an item from the POST array
113
     *
114
     * @param  mixed $key
115
     * @param  mixed $default
116
     * @return mixed
117
     */
118
    public function post($key = null, $default = null)
0 ignored issues
show
Coding Style introduced by
post uses the super-global variable $_POST which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
119
    {
120
        $rawPostData = file_get_contents('php://input');
121
        $source = json_decode($rawPostData, true);
122
        if (json_last_error() != JSON_ERROR_NONE) {
123
            $source = $_POST;
124
        }
125
126
        return $this->getRequestParams($source, $key, $default);
127
    }
128
129
    /**
130
     * Fetch an item from the SERVER array
131
     *
132
     * @param  mixed $key
133
     * @param  mixed $default
134
     * @return mixed
135
     */
136
    public function server($key = null, $default = null)
0 ignored issues
show
Coding Style introduced by
server uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
137
    {
138
        return $this->getRequestParams($_SERVER, $key, $default);
139
    }
140
141
    /**
142
     * Set or Get cookie
143
     *
144
     * @param  mixed  $key
145
     * @param  string $value
146
     * @param  mixed  $options
147
     * @return mixed
148
     */
149 2
    public function cookie($key = '', $value = '', $options = null)
0 ignored issues
show
Coding Style introduced by
cookie uses the super-global variable $_COOKIE which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
150
    {
151
        $defaultOptions = [
152 2
            'prefix' => '',
153
            'expire' => 86400,
154
            'path' => '/',
155
            'secure' => false,
156
            'httponly' => false,
157
        ];
158
159 2
        if (!is_null($options)) {
160
            if (is_numeric($options)) {
161
                $options = ['expire' => $options];
162
            } elseif (is_string($options)) {
163
                parse_str($options, $options);
164
            }
165
166
            $options = array_merge($defaultOptions, array_change_key_case($options));
167
        }
168
169 2
        if (!empty($options['httponly'])) {
170
            ini_set('session.cookie_httponly', 1);
171
        }
172
173 2
        if (is_null($key)) {
174
            if (empty($_COOKIE)) {
175
                return null;
176
            }
177
178
            $prefix = empty($value) ? $options['prefix'] : $value;
179
            if (!empty($prefix)) {
180
                foreach ($_COOKIE as $key => $val) {
181
                    if (0 === stripos($key, $prefix)) {
182
                        setcookie($key, '', time() - 3600, $options['path'], $options['domain'], $options['secure'], $options['httponly']);
183
                        unset($_COOKIE[$key]);
184
                    }
185
                }
186
            }
187
188
            return null;
189 2
        } elseif ('' === $key) {
190
            // Get All Cookie
191
            return $_COOKIE;
192
        }
193
194 2
        $key = $options['prefix'] . str_replace('.', '_', $key);
195 2
        if ('' === $value) {
196 2
            if (isset($_COOKIE[$key])) {
197 1
                $value = $_COOKIE[$key];
198 1
                if (0 === strpos($value, 'kotori:')) {
199
                    $value = substr($value, 6);
200
                    return array_map('urldecode', json_decode(MAGIC_QUOTES_GPC ? stripslashes($value) : $value, true));
201
                } else {
202 1
                    return $value;
203
                }
204
            } else {
205 1
                return null;
206
            }
207
        } else {
208 2
            if (is_null($value)) {
209 1
                setcookie($key, '', time() - 3600, $options['path'], $options['domain'], $options['secure'], $options['httponly']);
210 1
                unset($_COOKIE[$key]); // Delete Cookie
211
            } else {
212
                // Set Cookie
213 2
                if (is_array($value)) {
214
                    $value = 'kotori:' . json_encode(array_map('urlencode', $value));
215
                }
216
217 2
                $expire = !empty($options['expire']) ? time() + intval($options['expire']) : 0;
218 2
                setcookie($key, $value, $expire, $options['path'], $options['domain'], $options['secure'], $options['httponly']);
219 2
                $_COOKIE[$key] = $value;
220
            }
221
        }
222
223 2
        return null;
224
    }
225
226
    /**
227
     * Session Initialize
228
     *
229
     * @return void
230
     */
231
    public function sessionStart()
232
    {
233
        if (PHP_SESSION_ACTIVE != session_status()) {
234
            ini_set('session.auto_start', 0);
235
            $config = Container::get('config')->get('session');
236
            if ($config['adapter'] != '') {
237
                $class = '\\Kotori\\Http\\Session\\' . ucfirst($config['adapter']);
238
                if (!class_exists($class) || !session_set_save_handler(new $class($config))) {
239
                    throw new NotFoundException('error session handler:' . $class);
240
                }
241
            }
242
243
            session_name('KOTORI_SESSID');
244
            session_start();
245
        }
246
    }
247
248
    /**
249
     * Set or Get session
250
     *
251
     * @param  mixed  $key
252
     * @param  string $value
253
     * @return mixed
254
     */
255 2
    public function session($key = '', $value = '')
0 ignored issues
show
Coding Style introduced by
session uses the super-global variable $_SESSION which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
256
    {
257 2
        if (is_null($key)) {
258
            if (empty($_SESSION)) {
259
                return null;
260
            }
261
262
            unset($_SESSION);
263 2
        } elseif ('' === $key) {
264
            // Get All Session
265
            return $_SESSION;
266
        }
267
268 2
        if ('' === $value) {
269 2
            return isset($_SESSION[$key]) ? $_SESSION[$key] : null;
270
        } else {
271 2
            if (is_null($value)) {
272 1
                unset($_SESSION[$key]);
273
            } else {
274 2
                $_SESSION[$key] = $value;
275
            }
276
        }
277
278 2
        return null;
279
    }
280
281
    /**
282
     * Is HTTPS?
283
     *
284
     * Determines if the application is accessed via an encrypted
285
     * (HTTPS) connection.
286
     *
287
     * @return  boolean
288
     */
289 2
    public function isSecure()
0 ignored issues
show
Coding Style introduced by
isSecure uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
290
    {
291 2
        if (!empty($_SERVER['HTTPS']) && strtolower($_SERVER['HTTPS']) !== 'off') {
292
            return true;
293 2
        } elseif (isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && 'https' === $_SERVER['HTTP_X_FORWARDED_PROTO']) {
294
            return true;
295 2
        } elseif (!empty($_SERVER['HTTP_FRONT_END_HTTPS']) && strtolower($_SERVER['HTTP_FRONT_END_HTTPS']) !== 'off') {
296
            return true;
297
        }
298
299 2
        return false;
300
    }
301
302
    /**
303
     * Base URL
304
     *
305
     * Returns base url
306
     *
307
     * @return string
308
     */
309 1
    public function getBaseUrl()
0 ignored issues
show
Coding Style introduced by
getBaseUrl uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
310
    {
311 1
        if (isset($_SERVER['HTTP_HOST']) && preg_match('/^((\[[0-9a-f:]+\])|(\d{1,3}(\.\d{1,3}){3})|[a-z0-9\-\.]+)(:\d+)?$/i', $_SERVER['HTTP_HOST'])) {
312 1
            $base_url = ($this->isSecure() ? 'https' : 'http') . '://' . $_SERVER['HTTP_HOST']
313 1
            . substr($_SERVER['SCRIPT_NAME'], 0, strpos($_SERVER['SCRIPT_NAME'], basename($_SERVER['SCRIPT_FILENAME'])));
314
        } else {
315
            $base_url = 'http://localhost/';
316
        }
317
318 1
        return rtrim($base_url, '/') . '/';
319
    }
320
321
    /**
322
     * Returns Client Ip Address
323
     *
324
     * @param  int     $type
325
     * @return string
326
     */
327 1
    public function getClientIp($type = 0)
0 ignored issues
show
Coding Style introduced by
getClientIp uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
328
    {
329 1
        $type = $type ? 1 : 0;
330
331 1
        if ($this->ip !== null) {
332
            return $this->ip[$type];
333
        }
334
335 1
        if (isset($_SERVER['HTTP_CF_CONNECTING_IP'])) {
336
            $this->ip = $_SERVER['HTTP_CF_CONNECTING_IP'];
337 1
        } elseif (isset($_SERVER['HTTP_X_FORWARDED_FOR'])) {
338
            $arr = explode(',', $_SERVER['HTTP_X_FORWARDED_FOR']);
339
            $pos = array_search('unknown', $arr);
340
            if (false !== $pos) {
341
                unset($arr[$pos]);
342
            }
343
344
            $this->ip = trim($arr[0]);
345 1
        } elseif (isset($_SERVER['HTTP_CLIENT_IP'])) {
346
            $this->ip = $_SERVER['HTTP_CLIENT_IP'];
347 1
        } elseif (isset($_SERVER['REMOTE_ADDR'])) {
348 1
            $this->ip = $_SERVER['REMOTE_ADDR'];
349
        }
350
351
        // Check ip
352 1
        $long = sprintf("%u", ip2long($this->ip));
353 1
        $this->ip = $long ? [$this->ip, $long] : ['0.0.0.0', 0];
354 1
        return $this->ip[$type];
355
    }
356
357
    /**
358
     * Returns Http Host
359
     *
360
     * @return string
361
     */
362 1
    public function getHostName()
0 ignored issues
show
Coding Style introduced by
getHostName uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
363
    {
364 1
        $possibleHostSources = ['HTTP_X_FORWARDED_HOST', 'HTTP_HOST', 'SERVER_NAME', 'SERVER_ADDR'];
365
        $sourceTransformations = [
366 1
            "HTTP_X_FORWARDED_HOST" => function ($value) {
367
                $elements = explode(',', $value);
368
                return trim(end($elements));
369 1
            },
370
        ];
371 1
        $host = '';
372 1
        foreach ($possibleHostSources as $source) {
373 1
            if (!empty($host)) {
374 1
                break;
375
            }
376
377 1
            if (empty($_SERVER[$source])) {
378 1
                continue;
379
            }
380
381 1
            $host = $_SERVER[$source];
382 1
            if (array_key_exists($source, $sourceTransformations)) {
383 1
                $host = $sourceTransformations[$source]($host);
384
            }
385
        }
386
387
        // Remove port number from host
388 1
        $host = preg_replace('/:\d+$/', '', $host);
389
390 1
        return trim($host);
391
    }
392
393
    /**
394
     * Return specified header
395
     *
396
     * @param  string $name
397
     * @return string
398
     */
399 1
    public function getHeader($name)
0 ignored issues
show
Coding Style introduced by
getHeader uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
400
    {
401 1
        if (empty($this->headers)) {
402 1
            if (function_exists('apache_request_headers')) {
403
                $this->headers = apache_request_headers();
404
            } else {
405 1
                $server = $_SERVER;
406 1
                foreach ($server as $key => $value) {
407 1
                    if (0 === strpos($key, 'HTTP_')) {
408 1
                        $key = str_replace('_', '-', strtolower(substr($key, 5)));
409 1
                        $this->headers[$key] = $value;
410
                    }
411
                }
412
413 1
                if (isset($server['CONTENT_TYPE'])) {
414
                    $this->headers['content-type'] = $server['CONTENT_TYPE'];
415
                }
416
417 1
                if (isset($server['CONTENT_LENGTH'])) {
418
                    $this->headers['content-length'] = $server['CONTENT_LENGTH'];
419
                }
420
            }
421
422 1
            $this->headers = array_change_key_case($this->headers);
423
        }
424
425 1
        $name = str_replace('_', '-', strtolower($name));
426 1
        return isset($this->headers[$name]) ? $this->headers[$name] : null;
427
    }
428
429
    /**
430
     * Detect whether request method is GET
431
     *
432
     * @return boolean
433
     */
434
    public function isGet()
0 ignored issues
show
Coding Style introduced by
isGet uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
435
    {
436
        return 'get' == strtolower($_SERVER['REQUEST_METHOD']);
437
    }
438
439
    /**
440
     * Detect whether request method is POST
441
     *
442
     * @return boolean
443
     */
444
    public function isPost()
0 ignored issues
show
Coding Style introduced by
isPost uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
445
    {
446
        return 'post' == strtolower($_SERVER['REQUEST_METHOD']);
447
    }
448
449
    /**
450
     * Detect whether request method is PUT
451
     *
452
     * @return boolean
453
     */
454
    public function isPut()
0 ignored issues
show
Coding Style introduced by
isPut uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
455
    {
456
        return 'put' == strtolower($_SERVER['REQUEST_METHOD']);
457
    }
458
459
    /**
460
     * Detect whether request method is PATCH
461
     *
462
     * @return boolean
463
     */
464
    public function isPatch()
0 ignored issues
show
Coding Style introduced by
isPatch uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
465
    {
466
        return 'patch' == strtolower($_SERVER['REQUEST_METHOD']);
467
    }
468
469
    /**
470
     * Detect whether request method is DELETE
471
     *
472
     * @return boolean
473
     */
474
    public function isDelete()
0 ignored issues
show
Coding Style introduced by
isDelete uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
475
    {
476
        return 'delete' == strtolower($_SERVER['REQUEST_METHOD']);
477
    }
478
479
    /**
480
     * Detect whether request method is OPTIONS
481
     *
482
     * @return boolean
483
     */
484
    public function isOptions()
0 ignored issues
show
Coding Style introduced by
isOptions uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
485
    {
486
        return 'options' == strtolower($_SERVER['REQUEST_METHOD']);
487
    }
488
489
    /**
490
     * Detect whether request method is AJAX
491
     *
492
     * @return boolean
493
     */
494
    public function isAjax()
0 ignored issues
show
Coding Style introduced by
isAjax uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
495
    {
496
        return ((isset($_SERVER['HTTP_X_REQUESTED_WITH']) && strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) == 'xmlhttprequest')) ? true : false;
497
    }
498
499
    /**
500
     * Is CLI?
501
     *
502
     * Test to see if a request was made from the command line.
503
     *
504
     * @return  boolean
505
     */
506 3
    public function isCli()
507
    {
508 3
        return PHP_SAPI === 'cli';
509
    }
510
511
    /**
512
     * Detect whether user agent is Mobile
513
     *
514
     * @return boolean
515
     */
516 1
    public function isMobile()
0 ignored issues
show
Coding Style introduced by
isMobile uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
517
    {
518 1
        $userAgent = isset($_SERVER['USER_AGENT']) ? $_SERVER['USER_AGENT'] : null;
519 1
        if ($userAgent == null) {
520 1
            return false;
521
        }
522
523
        return preg_match('/android.+mobile|avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|symbian|treo|up\.(browser|link)|vodafone|wap|windows (ce|phone)|xda|xiino/i', $userAgent) || preg_match('/1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(di|rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\-|your|zeto|zte\-/i', substr($userAgent, 0, 4));
524
    }
525
}
526