Mercurial > hg > isophonics-drupal-site
comparison vendor/symfony/http-foundation/Request.php @ 17:129ea1e6d783
Update, including to Drupal core 8.6.10
author | Chris Cannam |
---|---|
date | Thu, 28 Feb 2019 13:21:36 +0000 |
parents | c2387f117808 |
children | af1871eacc83 |
comparison
equal
deleted
inserted
replaced
16:c2387f117808 | 17:129ea1e6d783 |
---|---|
59 const METHOD_CONNECT = 'CONNECT'; | 59 const METHOD_CONNECT = 'CONNECT'; |
60 | 60 |
61 /** | 61 /** |
62 * @var string[] | 62 * @var string[] |
63 */ | 63 */ |
64 protected static $trustedProxies = array(); | 64 protected static $trustedProxies = []; |
65 | 65 |
66 /** | 66 /** |
67 * @var string[] | 67 * @var string[] |
68 */ | 68 */ |
69 protected static $trustedHostPatterns = array(); | 69 protected static $trustedHostPatterns = []; |
70 | 70 |
71 /** | 71 /** |
72 * @var string[] | 72 * @var string[] |
73 */ | 73 */ |
74 protected static $trustedHosts = array(); | 74 protected static $trustedHosts = []; |
75 | 75 |
76 /** | 76 /** |
77 * Names for headers that can be trusted when | 77 * Names for headers that can be trusted when |
78 * using trusted proxies. | 78 * using trusted proxies. |
79 * | 79 * |
82 * The other headers are non-standard, but widely used | 82 * The other headers are non-standard, but widely used |
83 * by popular reverse proxies (like Apache mod_proxy or Amazon EC2). | 83 * by popular reverse proxies (like Apache mod_proxy or Amazon EC2). |
84 * | 84 * |
85 * @deprecated since version 3.3, to be removed in 4.0 | 85 * @deprecated since version 3.3, to be removed in 4.0 |
86 */ | 86 */ |
87 protected static $trustedHeaders = array( | 87 protected static $trustedHeaders = [ |
88 self::HEADER_FORWARDED => 'FORWARDED', | 88 self::HEADER_FORWARDED => 'FORWARDED', |
89 self::HEADER_CLIENT_IP => 'X_FORWARDED_FOR', | 89 self::HEADER_CLIENT_IP => 'X_FORWARDED_FOR', |
90 self::HEADER_CLIENT_HOST => 'X_FORWARDED_HOST', | 90 self::HEADER_CLIENT_HOST => 'X_FORWARDED_HOST', |
91 self::HEADER_CLIENT_PROTO => 'X_FORWARDED_PROTO', | 91 self::HEADER_CLIENT_PROTO => 'X_FORWARDED_PROTO', |
92 self::HEADER_CLIENT_PORT => 'X_FORWARDED_PORT', | 92 self::HEADER_CLIENT_PORT => 'X_FORWARDED_PORT', |
93 ); | 93 ]; |
94 | 94 |
95 protected static $httpMethodParameterOverride = false; | 95 protected static $httpMethodParameterOverride = false; |
96 | 96 |
97 /** | 97 /** |
98 * Custom parameters. | 98 * Custom parameters. |
224 private $isForwardedValid = true; | 224 private $isForwardedValid = true; |
225 | 225 |
226 private static $trustedHeaderSet = -1; | 226 private static $trustedHeaderSet = -1; |
227 | 227 |
228 /** @deprecated since version 3.3, to be removed in 4.0 */ | 228 /** @deprecated since version 3.3, to be removed in 4.0 */ |
229 private static $trustedHeaderNames = array( | 229 private static $trustedHeaderNames = [ |
230 self::HEADER_FORWARDED => 'FORWARDED', | 230 self::HEADER_FORWARDED => 'FORWARDED', |
231 self::HEADER_CLIENT_IP => 'X_FORWARDED_FOR', | 231 self::HEADER_CLIENT_IP => 'X_FORWARDED_FOR', |
232 self::HEADER_CLIENT_HOST => 'X_FORWARDED_HOST', | 232 self::HEADER_CLIENT_HOST => 'X_FORWARDED_HOST', |
233 self::HEADER_CLIENT_PROTO => 'X_FORWARDED_PROTO', | 233 self::HEADER_CLIENT_PROTO => 'X_FORWARDED_PROTO', |
234 self::HEADER_CLIENT_PORT => 'X_FORWARDED_PORT', | 234 self::HEADER_CLIENT_PORT => 'X_FORWARDED_PORT', |
235 ); | 235 ]; |
236 | 236 |
237 private static $forwardedParams = array( | 237 private static $forwardedParams = [ |
238 self::HEADER_X_FORWARDED_FOR => 'for', | 238 self::HEADER_X_FORWARDED_FOR => 'for', |
239 self::HEADER_X_FORWARDED_HOST => 'host', | 239 self::HEADER_X_FORWARDED_HOST => 'host', |
240 self::HEADER_X_FORWARDED_PROTO => 'proto', | 240 self::HEADER_X_FORWARDED_PROTO => 'proto', |
241 self::HEADER_X_FORWARDED_PORT => 'host', | 241 self::HEADER_X_FORWARDED_PORT => 'host', |
242 ); | 242 ]; |
243 | 243 |
244 /** | 244 /** |
245 * @param array $query The GET parameters | 245 * @param array $query The GET parameters |
246 * @param array $request The POST parameters | 246 * @param array $request The POST parameters |
247 * @param array $attributes The request attributes (parameters parsed from the PATH_INFO, ...) | 247 * @param array $attributes The request attributes (parameters parsed from the PATH_INFO, ...) |
248 * @param array $cookies The COOKIE parameters | 248 * @param array $cookies The COOKIE parameters |
249 * @param array $files The FILES parameters | 249 * @param array $files The FILES parameters |
250 * @param array $server The SERVER parameters | 250 * @param array $server The SERVER parameters |
251 * @param string|resource|null $content The raw body data | 251 * @param string|resource|null $content The raw body data |
252 */ | 252 */ |
253 public function __construct(array $query = array(), array $request = array(), array $attributes = array(), array $cookies = array(), array $files = array(), array $server = array(), $content = null) | 253 public function __construct(array $query = [], array $request = [], array $attributes = [], array $cookies = [], array $files = [], array $server = [], $content = null) |
254 { | 254 { |
255 $this->initialize($query, $request, $attributes, $cookies, $files, $server, $content); | 255 $this->initialize($query, $request, $attributes, $cookies, $files, $server, $content); |
256 } | 256 } |
257 | 257 |
258 /** | 258 /** |
266 * @param array $cookies The COOKIE parameters | 266 * @param array $cookies The COOKIE parameters |
267 * @param array $files The FILES parameters | 267 * @param array $files The FILES parameters |
268 * @param array $server The SERVER parameters | 268 * @param array $server The SERVER parameters |
269 * @param string|resource|null $content The raw body data | 269 * @param string|resource|null $content The raw body data |
270 */ | 270 */ |
271 public function initialize(array $query = array(), array $request = array(), array $attributes = array(), array $cookies = array(), array $files = array(), array $server = array(), $content = null) | 271 public function initialize(array $query = [], array $request = [], array $attributes = [], array $cookies = [], array $files = [], array $server = [], $content = null) |
272 { | 272 { |
273 $this->request = new ParameterBag($request); | 273 $this->request = new ParameterBag($request); |
274 $this->query = new ParameterBag($query); | 274 $this->query = new ParameterBag($query); |
275 $this->attributes = new ParameterBag($attributes); | 275 $this->attributes = new ParameterBag($attributes); |
276 $this->cookies = new ParameterBag($cookies); | 276 $this->cookies = new ParameterBag($cookies); |
300 { | 300 { |
301 // With the php's bug #66606, the php's built-in web server | 301 // With the php's bug #66606, the php's built-in web server |
302 // stores the Content-Type and Content-Length header values in | 302 // stores the Content-Type and Content-Length header values in |
303 // HTTP_CONTENT_TYPE and HTTP_CONTENT_LENGTH fields. | 303 // HTTP_CONTENT_TYPE and HTTP_CONTENT_LENGTH fields. |
304 $server = $_SERVER; | 304 $server = $_SERVER; |
305 if ('cli-server' === PHP_SAPI) { | 305 if ('cli-server' === \PHP_SAPI) { |
306 if (array_key_exists('HTTP_CONTENT_LENGTH', $_SERVER)) { | 306 if (array_key_exists('HTTP_CONTENT_LENGTH', $_SERVER)) { |
307 $server['CONTENT_LENGTH'] = $_SERVER['HTTP_CONTENT_LENGTH']; | 307 $server['CONTENT_LENGTH'] = $_SERVER['HTTP_CONTENT_LENGTH']; |
308 } | 308 } |
309 if (array_key_exists('HTTP_CONTENT_TYPE', $_SERVER)) { | 309 if (array_key_exists('HTTP_CONTENT_TYPE', $_SERVER)) { |
310 $server['CONTENT_TYPE'] = $_SERVER['HTTP_CONTENT_TYPE']; | 310 $server['CONTENT_TYPE'] = $_SERVER['HTTP_CONTENT_TYPE']; |
311 } | 311 } |
312 } | 312 } |
313 | 313 |
314 $request = self::createRequestFromFactory($_GET, $_POST, array(), $_COOKIE, $_FILES, $server); | 314 $request = self::createRequestFromFactory($_GET, $_POST, [], $_COOKIE, $_FILES, $server); |
315 | 315 |
316 if (0 === strpos($request->headers->get('CONTENT_TYPE'), 'application/x-www-form-urlencoded') | 316 if (0 === strpos($request->headers->get('CONTENT_TYPE'), 'application/x-www-form-urlencoded') |
317 && in_array(strtoupper($request->server->get('REQUEST_METHOD', 'GET')), array('PUT', 'DELETE', 'PATCH')) | 317 && \in_array(strtoupper($request->server->get('REQUEST_METHOD', 'GET')), ['PUT', 'DELETE', 'PATCH']) |
318 ) { | 318 ) { |
319 parse_str($request->getContent(), $data); | 319 parse_str($request->getContent(), $data); |
320 $request->request = new ParameterBag($data); | 320 $request->request = new ParameterBag($data); |
321 } | 321 } |
322 | 322 |
337 * @param array $server The server parameters ($_SERVER) | 337 * @param array $server The server parameters ($_SERVER) |
338 * @param string|resource|null $content The raw body data | 338 * @param string|resource|null $content The raw body data |
339 * | 339 * |
340 * @return static | 340 * @return static |
341 */ | 341 */ |
342 public static function create($uri, $method = 'GET', $parameters = array(), $cookies = array(), $files = array(), $server = array(), $content = null) | 342 public static function create($uri, $method = 'GET', $parameters = [], $cookies = [], $files = [], $server = [], $content = null) |
343 { | 343 { |
344 $server = array_replace(array( | 344 $server = array_replace([ |
345 'SERVER_NAME' => 'localhost', | 345 'SERVER_NAME' => 'localhost', |
346 'SERVER_PORT' => 80, | 346 'SERVER_PORT' => 80, |
347 'HTTP_HOST' => 'localhost', | 347 'HTTP_HOST' => 'localhost', |
348 'HTTP_USER_AGENT' => 'Symfony/3.X', | 348 'HTTP_USER_AGENT' => 'Symfony/3.X', |
349 'HTTP_ACCEPT' => 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8', | 349 'HTTP_ACCEPT' => 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8', |
352 'REMOTE_ADDR' => '127.0.0.1', | 352 'REMOTE_ADDR' => '127.0.0.1', |
353 'SCRIPT_NAME' => '', | 353 'SCRIPT_NAME' => '', |
354 'SCRIPT_FILENAME' => '', | 354 'SCRIPT_FILENAME' => '', |
355 'SERVER_PROTOCOL' => 'HTTP/1.1', | 355 'SERVER_PROTOCOL' => 'HTTP/1.1', |
356 'REQUEST_TIME' => time(), | 356 'REQUEST_TIME' => time(), |
357 ), $server); | 357 ], $server); |
358 | 358 |
359 $server['PATH_INFO'] = ''; | 359 $server['PATH_INFO'] = ''; |
360 $server['REQUEST_METHOD'] = strtoupper($method); | 360 $server['REQUEST_METHOD'] = strtoupper($method); |
361 | 361 |
362 $components = parse_url($uri); | 362 $components = parse_url($uri); |
375 } | 375 } |
376 } | 376 } |
377 | 377 |
378 if (isset($components['port'])) { | 378 if (isset($components['port'])) { |
379 $server['SERVER_PORT'] = $components['port']; | 379 $server['SERVER_PORT'] = $components['port']; |
380 $server['HTTP_HOST'] = $server['HTTP_HOST'].':'.$components['port']; | 380 $server['HTTP_HOST'] .= ':'.$components['port']; |
381 } | 381 } |
382 | 382 |
383 if (isset($components['user'])) { | 383 if (isset($components['user'])) { |
384 $server['PHP_AUTH_USER'] = $components['user']; | 384 $server['PHP_AUTH_USER'] = $components['user']; |
385 } | 385 } |
400 $server['CONTENT_TYPE'] = 'application/x-www-form-urlencoded'; | 400 $server['CONTENT_TYPE'] = 'application/x-www-form-urlencoded'; |
401 } | 401 } |
402 // no break | 402 // no break |
403 case 'PATCH': | 403 case 'PATCH': |
404 $request = $parameters; | 404 $request = $parameters; |
405 $query = array(); | 405 $query = []; |
406 break; | 406 break; |
407 default: | 407 default: |
408 $request = array(); | 408 $request = []; |
409 $query = $parameters; | 409 $query = $parameters; |
410 break; | 410 break; |
411 } | 411 } |
412 | 412 |
413 $queryString = ''; | 413 $queryString = ''; |
426 } | 426 } |
427 | 427 |
428 $server['REQUEST_URI'] = $components['path'].('' !== $queryString ? '?'.$queryString : ''); | 428 $server['REQUEST_URI'] = $components['path'].('' !== $queryString ? '?'.$queryString : ''); |
429 $server['QUERY_STRING'] = $queryString; | 429 $server['QUERY_STRING'] = $queryString; |
430 | 430 |
431 return self::createRequestFromFactory($query, $request, array(), $cookies, $files, $server, $content); | 431 return self::createRequestFromFactory($query, $request, [], $cookies, $files, $server, $content); |
432 } | 432 } |
433 | 433 |
434 /** | 434 /** |
435 * Sets a callable able to create a Request instance. | 435 * Sets a callable able to create a Request instance. |
436 * | 436 * |
530 } catch (\LogicException $e) { | 530 } catch (\LogicException $e) { |
531 return trigger_error($e, E_USER_ERROR); | 531 return trigger_error($e, E_USER_ERROR); |
532 } | 532 } |
533 | 533 |
534 $cookieHeader = ''; | 534 $cookieHeader = ''; |
535 $cookies = array(); | 535 $cookies = []; |
536 | 536 |
537 foreach ($this->cookies as $k => $v) { | 537 foreach ($this->cookies as $k => $v) { |
538 $cookies[] = $k.'='.$v; | 538 $cookies[] = $k.'='.$v; |
539 } | 539 } |
540 | 540 |
564 $_SERVER = $this->server->all(); | 564 $_SERVER = $this->server->all(); |
565 $_COOKIE = $this->cookies->all(); | 565 $_COOKIE = $this->cookies->all(); |
566 | 566 |
567 foreach ($this->headers->all() as $key => $value) { | 567 foreach ($this->headers->all() as $key => $value) { |
568 $key = strtoupper(str_replace('-', '_', $key)); | 568 $key = strtoupper(str_replace('-', '_', $key)); |
569 if (in_array($key, array('CONTENT_TYPE', 'CONTENT_LENGTH'))) { | 569 if (\in_array($key, ['CONTENT_TYPE', 'CONTENT_LENGTH'])) { |
570 $_SERVER[$key] = implode(', ', $value); | 570 $_SERVER[$key] = implode(', ', $value); |
571 } else { | 571 } else { |
572 $_SERVER['HTTP_'.$key] = implode(', ', $value); | 572 $_SERVER['HTTP_'.$key] = implode(', ', $value); |
573 } | 573 } |
574 } | 574 } |
575 | 575 |
576 $request = array('g' => $_GET, 'p' => $_POST, 'c' => $_COOKIE); | 576 $request = ['g' => $_GET, 'p' => $_POST, 'c' => $_COOKIE]; |
577 | 577 |
578 $requestOrder = ini_get('request_order') ?: ini_get('variables_order'); | 578 $requestOrder = ini_get('request_order') ?: ini_get('variables_order'); |
579 $requestOrder = preg_replace('#[^cgp]#', '', strtolower($requestOrder)) ?: 'gp'; | 579 $requestOrder = preg_replace('#[^cgp]#', '', strtolower($requestOrder)) ?: 'gp'; |
580 | 580 |
581 $_REQUEST = array(); | 581 $_REQUEST = []; |
582 foreach (str_split($requestOrder) as $order) { | 582 foreach (str_split($requestOrder) as $order) { |
583 $_REQUEST = array_merge($_REQUEST, $request[$order]); | 583 $_REQUEST = array_merge($_REQUEST, $request[$order]); |
584 } | 584 } |
585 } | 585 } |
586 | 586 |
596 */ | 596 */ |
597 public static function setTrustedProxies(array $proxies/*, int $trustedHeaderSet*/) | 597 public static function setTrustedProxies(array $proxies/*, int $trustedHeaderSet*/) |
598 { | 598 { |
599 self::$trustedProxies = $proxies; | 599 self::$trustedProxies = $proxies; |
600 | 600 |
601 if (2 > func_num_args()) { | 601 if (2 > \func_num_args()) { |
602 @trigger_error(sprintf('The %s() method expects a bit field of Request::HEADER_* as second argument since Symfony 3.3. Defining it will be required in 4.0. ', __METHOD__), E_USER_DEPRECATED); | 602 @trigger_error(sprintf('The %s() method expects a bit field of Request::HEADER_* as second argument since Symfony 3.3. Defining it will be required in 4.0. ', __METHOD__), E_USER_DEPRECATED); |
603 | 603 |
604 return; | 604 return; |
605 } | 605 } |
606 $trustedHeaderSet = (int) func_get_arg(1); | 606 $trustedHeaderSet = (int) func_get_arg(1); |
642 { | 642 { |
643 self::$trustedHostPatterns = array_map(function ($hostPattern) { | 643 self::$trustedHostPatterns = array_map(function ($hostPattern) { |
644 return sprintf('{%s}i', $hostPattern); | 644 return sprintf('{%s}i', $hostPattern); |
645 }, $hostPatterns); | 645 }, $hostPatterns); |
646 // we need to reset trusted hosts on trusted host patterns change | 646 // we need to reset trusted hosts on trusted host patterns change |
647 self::$trustedHosts = array(); | 647 self::$trustedHosts = []; |
648 } | 648 } |
649 | 649 |
650 /** | 650 /** |
651 * Gets the list of trusted host patterns. | 651 * Gets the list of trusted host patterns. |
652 * | 652 * |
716 * | 716 * |
717 * @deprecated since version 3.3, to be removed in 4.0. Use the Request::getTrustedHeaderSet() method instead. | 717 * @deprecated since version 3.3, to be removed in 4.0. Use the Request::getTrustedHeaderSet() method instead. |
718 */ | 718 */ |
719 public static function getTrustedHeaderName($key) | 719 public static function getTrustedHeaderName($key) |
720 { | 720 { |
721 if (2 > func_num_args() || func_get_arg(1)) { | 721 if (2 > \func_num_args() || func_get_arg(1)) { |
722 @trigger_error(sprintf('The "%s()" method is deprecated since Symfony 3.3 and will be removed in 4.0. Use the Request::getTrustedHeaderSet() method instead.', __METHOD__), E_USER_DEPRECATED); | 722 @trigger_error(sprintf('The "%s()" method is deprecated since Symfony 3.3 and will be removed in 4.0. Use the Request::getTrustedHeaderSet() method instead.', __METHOD__), E_USER_DEPRECATED); |
723 } | 723 } |
724 | 724 |
725 if (!array_key_exists($key, self::$trustedHeaders)) { | 725 if (!array_key_exists($key, self::$trustedHeaders)) { |
726 throw new \InvalidArgumentException(sprintf('Unable to get the trusted header name for key "%s".', $key)); | 726 throw new \InvalidArgumentException(sprintf('Unable to get the trusted header name for key "%s".', $key)); |
743 { | 743 { |
744 if ('' == $qs) { | 744 if ('' == $qs) { |
745 return ''; | 745 return ''; |
746 } | 746 } |
747 | 747 |
748 $parts = array(); | 748 $parts = []; |
749 $order = array(); | 749 $order = []; |
750 | 750 |
751 foreach (explode('&', $qs) as $param) { | 751 foreach (explode('&', $qs) as $param) { |
752 if ('' === $param || '=' === $param[0]) { | 752 if ('' === $param || '=' === $param[0]) { |
753 // Ignore useless delimiters, e.g. "x=y&". | 753 // Ignore useless delimiters, e.g. "x=y&". |
754 // Also ignore pairs with empty key, even if there was a value, e.g. "=value", as such nameless values cannot be retrieved anyway. | 754 // Also ignore pairs with empty key, even if there was a value, e.g. "=value", as such nameless values cannot be retrieved anyway. |
891 public function getClientIps() | 891 public function getClientIps() |
892 { | 892 { |
893 $ip = $this->server->get('REMOTE_ADDR'); | 893 $ip = $this->server->get('REMOTE_ADDR'); |
894 | 894 |
895 if (!$this->isFromTrustedProxy()) { | 895 if (!$this->isFromTrustedProxy()) { |
896 return array($ip); | 896 return [$ip]; |
897 } | 897 } |
898 | 898 |
899 return $this->getTrustedValues(self::HEADER_CLIENT_IP, $ip) ?: array($ip); | 899 return $this->getTrustedValues(self::HEADER_CLIENT_IP, $ip) ?: [$ip]; |
900 } | 900 } |
901 | 901 |
902 /** | 902 /** |
903 * Returns the client IP address. | 903 * Returns the client IP address. |
904 * | 904 * |
1184 if ($path === $basePath = $this->getPathInfo()) { | 1184 if ($path === $basePath = $this->getPathInfo()) { |
1185 return ''; | 1185 return ''; |
1186 } | 1186 } |
1187 | 1187 |
1188 $sourceDirs = explode('/', isset($basePath[0]) && '/' === $basePath[0] ? substr($basePath, 1) : $basePath); | 1188 $sourceDirs = explode('/', isset($basePath[0]) && '/' === $basePath[0] ? substr($basePath, 1) : $basePath); |
1189 $targetDirs = explode('/', isset($path[0]) && '/' === $path[0] ? substr($path, 1) : $path); | 1189 $targetDirs = explode('/', substr($path, 1)); |
1190 array_pop($sourceDirs); | 1190 array_pop($sourceDirs); |
1191 $targetFile = array_pop($targetDirs); | 1191 $targetFile = array_pop($targetDirs); |
1192 | 1192 |
1193 foreach ($sourceDirs as $i => $dir) { | 1193 foreach ($sourceDirs as $i => $dir) { |
1194 if (isset($targetDirs[$i]) && $dir === $targetDirs[$i]) { | 1194 if (isset($targetDirs[$i]) && $dir === $targetDirs[$i]) { |
1197 break; | 1197 break; |
1198 } | 1198 } |
1199 } | 1199 } |
1200 | 1200 |
1201 $targetDirs[] = $targetFile; | 1201 $targetDirs[] = $targetFile; |
1202 $path = str_repeat('../', count($sourceDirs)).implode('/', $targetDirs); | 1202 $path = str_repeat('../', \count($sourceDirs)).implode('/', $targetDirs); |
1203 | 1203 |
1204 // A reference to the same base directory or an empty subdirectory must be prefixed with "./". | 1204 // A reference to the same base directory or an empty subdirectory must be prefixed with "./". |
1205 // This also applies to a segment with a colon character (e.g., "file:colon") that cannot be used | 1205 // This also applies to a segment with a colon character (e.g., "file:colon") that cannot be used |
1206 // as the first segment of a relative-path reference, as it would be mistaken for a scheme name | 1206 // as the first segment of a relative-path reference, as it would be mistaken for a scheme name |
1207 // (see http://tools.ietf.org/html/rfc3986#section-4.2). | 1207 // (see http://tools.ietf.org/html/rfc3986#section-4.2). |
1240 * @return bool | 1240 * @return bool |
1241 */ | 1241 */ |
1242 public function isSecure() | 1242 public function isSecure() |
1243 { | 1243 { |
1244 if ($this->isFromTrustedProxy() && $proto = $this->getTrustedValues(self::HEADER_CLIENT_PROTO)) { | 1244 if ($this->isFromTrustedProxy() && $proto = $this->getTrustedValues(self::HEADER_CLIENT_PROTO)) { |
1245 return in_array(strtolower($proto[0]), array('https', 'on', 'ssl', '1'), true); | 1245 return \in_array(strtolower($proto[0]), ['https', 'on', 'ssl', '1'], true); |
1246 } | 1246 } |
1247 | 1247 |
1248 $https = $this->server->get('HTTPS'); | 1248 $https = $this->server->get('HTTPS'); |
1249 | 1249 |
1250 return !empty($https) && 'off' !== strtolower($https); | 1250 return !empty($https) && 'off' !== strtolower($https); |
1290 $this->isHostValid = false; | 1290 $this->isHostValid = false; |
1291 | 1291 |
1292 throw new SuspiciousOperationException(sprintf('Invalid Host "%s".', $host)); | 1292 throw new SuspiciousOperationException(sprintf('Invalid Host "%s".', $host)); |
1293 } | 1293 } |
1294 | 1294 |
1295 if (count(self::$trustedHostPatterns) > 0) { | 1295 if (\count(self::$trustedHostPatterns) > 0) { |
1296 // to avoid host header injection attacks, you should provide a list of trusted host patterns | 1296 // to avoid host header injection attacks, you should provide a list of trusted host patterns |
1297 | 1297 |
1298 if (in_array($host, self::$trustedHosts)) { | 1298 if (\in_array($host, self::$trustedHosts)) { |
1299 return $host; | 1299 return $host; |
1300 } | 1300 } |
1301 | 1301 |
1302 foreach (self::$trustedHostPatterns as $pattern) { | 1302 foreach (self::$trustedHostPatterns as $pattern) { |
1303 if (preg_match($pattern, $host)) { | 1303 if (preg_match($pattern, $host)) { |
1351 | 1351 |
1352 if ('POST' === $this->method) { | 1352 if ('POST' === $this->method) { |
1353 if ($method = $this->headers->get('X-HTTP-METHOD-OVERRIDE')) { | 1353 if ($method = $this->headers->get('X-HTTP-METHOD-OVERRIDE')) { |
1354 $this->method = strtoupper($method); | 1354 $this->method = strtoupper($method); |
1355 } elseif (self::$httpMethodParameterOverride) { | 1355 } elseif (self::$httpMethodParameterOverride) { |
1356 $this->method = strtoupper($this->request->get('_method', $this->query->get('_method', 'POST'))); | 1356 $method = $this->request->get('_method', $this->query->get('_method', 'POST')); |
1357 if (\is_string($method)) { | |
1358 $this->method = strtoupper($method); | |
1359 } | |
1357 } | 1360 } |
1358 } | 1361 } |
1359 } | 1362 } |
1360 | 1363 |
1361 return $this->method; | 1364 return $this->method; |
1400 { | 1403 { |
1401 if (null === static::$formats) { | 1404 if (null === static::$formats) { |
1402 static::initializeFormats(); | 1405 static::initializeFormats(); |
1403 } | 1406 } |
1404 | 1407 |
1405 return isset(static::$formats[$format]) ? static::$formats[$format] : array(); | 1408 return isset(static::$formats[$format]) ? static::$formats[$format] : []; |
1406 } | 1409 } |
1407 | 1410 |
1408 /** | 1411 /** |
1409 * Gets the format associated with the mime type. | 1412 * Gets the format associated with the mime type. |
1410 * | 1413 * |
1414 */ | 1417 */ |
1415 public function getFormat($mimeType) | 1418 public function getFormat($mimeType) |
1416 { | 1419 { |
1417 $canonicalMimeType = null; | 1420 $canonicalMimeType = null; |
1418 if (false !== $pos = strpos($mimeType, ';')) { | 1421 if (false !== $pos = strpos($mimeType, ';')) { |
1419 $canonicalMimeType = substr($mimeType, 0, $pos); | 1422 $canonicalMimeType = trim(substr($mimeType, 0, $pos)); |
1420 } | 1423 } |
1421 | 1424 |
1422 if (null === static::$formats) { | 1425 if (null === static::$formats) { |
1423 static::initializeFormats(); | 1426 static::initializeFormats(); |
1424 } | 1427 } |
1425 | 1428 |
1426 foreach (static::$formats as $format => $mimeTypes) { | 1429 foreach (static::$formats as $format => $mimeTypes) { |
1427 if (in_array($mimeType, (array) $mimeTypes)) { | 1430 if (\in_array($mimeType, (array) $mimeTypes)) { |
1428 return $format; | 1431 return $format; |
1429 } | 1432 } |
1430 if (null !== $canonicalMimeType && in_array($canonicalMimeType, (array) $mimeTypes)) { | 1433 if (null !== $canonicalMimeType && \in_array($canonicalMimeType, (array) $mimeTypes)) { |
1431 return $format; | 1434 return $format; |
1432 } | 1435 } |
1433 } | 1436 } |
1434 } | 1437 } |
1435 | 1438 |
1443 { | 1446 { |
1444 if (null === static::$formats) { | 1447 if (null === static::$formats) { |
1445 static::initializeFormats(); | 1448 static::initializeFormats(); |
1446 } | 1449 } |
1447 | 1450 |
1448 static::$formats[$format] = is_array($mimeTypes) ? $mimeTypes : array($mimeTypes); | 1451 static::$formats[$format] = \is_array($mimeTypes) ? $mimeTypes : [$mimeTypes]; |
1449 } | 1452 } |
1450 | 1453 |
1451 /** | 1454 /** |
1452 * Gets the request format. | 1455 * Gets the request format. |
1453 * | 1456 * |
1455 * | 1458 * |
1456 * * format defined by the user (with setRequestFormat()) | 1459 * * format defined by the user (with setRequestFormat()) |
1457 * * _format request attribute | 1460 * * _format request attribute |
1458 * * $default | 1461 * * $default |
1459 * | 1462 * |
1460 * @param string $default The default format | 1463 * @param string|null $default The default format |
1461 * | 1464 * |
1462 * @return string The request format | 1465 * @return string The request format |
1463 */ | 1466 */ |
1464 public function getRequestFormat($default = 'html') | 1467 public function getRequestFormat($default = 'html') |
1465 { | 1468 { |
1555 * | 1558 * |
1556 * @return bool | 1559 * @return bool |
1557 */ | 1560 */ |
1558 public function isMethodSafe(/* $andCacheable = true */) | 1561 public function isMethodSafe(/* $andCacheable = true */) |
1559 { | 1562 { |
1560 if (!func_num_args() || func_get_arg(0)) { | 1563 if (!\func_num_args() || func_get_arg(0)) { |
1561 // This deprecation should be turned into a BadMethodCallException in 4.0 (without adding the argument in the signature) | 1564 // This deprecation should be turned into a BadMethodCallException in 4.0 (without adding the argument in the signature) |
1562 // then setting $andCacheable to false should be deprecated in 4.1 | 1565 // then setting $andCacheable to false should be deprecated in 4.1 |
1563 @trigger_error('Checking only for cacheable HTTP methods with Symfony\Component\HttpFoundation\Request::isMethodSafe() is deprecated since Symfony 3.2 and will throw an exception in 4.0. Disable checking only for cacheable methods by calling the method with `false` as first argument or use the Request::isMethodCacheable() instead.', E_USER_DEPRECATED); | 1566 @trigger_error('Checking only for cacheable HTTP methods with Symfony\Component\HttpFoundation\Request::isMethodSafe() is deprecated since Symfony 3.2 and will throw an exception in 4.0. Disable checking only for cacheable methods by calling the method with `false` as first argument or use the Request::isMethodCacheable() instead.', E_USER_DEPRECATED); |
1564 | 1567 |
1565 return in_array($this->getMethod(), array('GET', 'HEAD')); | 1568 return \in_array($this->getMethod(), ['GET', 'HEAD']); |
1566 } | 1569 } |
1567 | 1570 |
1568 return in_array($this->getMethod(), array('GET', 'HEAD', 'OPTIONS', 'TRACE')); | 1571 return \in_array($this->getMethod(), ['GET', 'HEAD', 'OPTIONS', 'TRACE']); |
1569 } | 1572 } |
1570 | 1573 |
1571 /** | 1574 /** |
1572 * Checks whether or not the method is idempotent. | 1575 * Checks whether or not the method is idempotent. |
1573 * | 1576 * |
1574 * @return bool | 1577 * @return bool |
1575 */ | 1578 */ |
1576 public function isMethodIdempotent() | 1579 public function isMethodIdempotent() |
1577 { | 1580 { |
1578 return in_array($this->getMethod(), array('HEAD', 'GET', 'PUT', 'DELETE', 'TRACE', 'OPTIONS', 'PURGE')); | 1581 return \in_array($this->getMethod(), ['HEAD', 'GET', 'PUT', 'DELETE', 'TRACE', 'OPTIONS', 'PURGE']); |
1579 } | 1582 } |
1580 | 1583 |
1581 /** | 1584 /** |
1582 * Checks whether the method is cacheable or not. | 1585 * Checks whether the method is cacheable or not. |
1583 * | 1586 * |
1584 * @see https://tools.ietf.org/html/rfc7231#section-4.2.3 | 1587 * @see https://tools.ietf.org/html/rfc7231#section-4.2.3 |
1585 * | 1588 * |
1586 * @return bool | 1589 * @return bool True for GET and HEAD, false otherwise |
1587 */ | 1590 */ |
1588 public function isMethodCacheable() | 1591 public function isMethodCacheable() |
1589 { | 1592 { |
1590 return in_array($this->getMethod(), array('GET', 'HEAD')); | 1593 return \in_array($this->getMethod(), ['GET', 'HEAD']); |
1591 } | 1594 } |
1592 | 1595 |
1593 /** | 1596 /** |
1594 * Returns the protocol version. | 1597 * Returns the protocol version. |
1595 * | 1598 * |
1623 * | 1626 * |
1624 * @throws \LogicException | 1627 * @throws \LogicException |
1625 */ | 1628 */ |
1626 public function getContent($asResource = false) | 1629 public function getContent($asResource = false) |
1627 { | 1630 { |
1628 $currentContentIsResource = is_resource($this->content); | 1631 $currentContentIsResource = \is_resource($this->content); |
1629 if (\PHP_VERSION_ID < 50600 && false === $this->content) { | 1632 if (\PHP_VERSION_ID < 50600 && false === $this->content) { |
1630 throw new \LogicException('getContent() can only be called once when using the resource return type and PHP below 5.6.'); | 1633 throw new \LogicException('getContent() can only be called once when using the resource return type and PHP below 5.6.'); |
1631 } | 1634 } |
1632 | 1635 |
1633 if (true === $asResource) { | 1636 if (true === $asResource) { |
1636 | 1639 |
1637 return $this->content; | 1640 return $this->content; |
1638 } | 1641 } |
1639 | 1642 |
1640 // Content passed in parameter (test) | 1643 // Content passed in parameter (test) |
1641 if (is_string($this->content)) { | 1644 if (\is_string($this->content)) { |
1642 $resource = fopen('php://temp', 'r+'); | 1645 $resource = fopen('php://temp', 'r+'); |
1643 fwrite($resource, $this->content); | 1646 fwrite($resource, $this->content); |
1644 rewind($resource); | 1647 rewind($resource); |
1645 | 1648 |
1646 return $resource; | 1649 return $resource; |
1699 | 1702 |
1700 if (!$preferredLanguages) { | 1703 if (!$preferredLanguages) { |
1701 return $locales[0]; | 1704 return $locales[0]; |
1702 } | 1705 } |
1703 | 1706 |
1704 $extendedPreferredLanguages = array(); | 1707 $extendedPreferredLanguages = []; |
1705 foreach ($preferredLanguages as $language) { | 1708 foreach ($preferredLanguages as $language) { |
1706 $extendedPreferredLanguages[] = $language; | 1709 $extendedPreferredLanguages[] = $language; |
1707 if (false !== $position = strpos($language, '_')) { | 1710 if (false !== $position = strpos($language, '_')) { |
1708 $superLanguage = substr($language, 0, $position); | 1711 $superLanguage = substr($language, 0, $position); |
1709 if (!in_array($superLanguage, $preferredLanguages)) { | 1712 if (!\in_array($superLanguage, $preferredLanguages)) { |
1710 $extendedPreferredLanguages[] = $superLanguage; | 1713 $extendedPreferredLanguages[] = $superLanguage; |
1711 } | 1714 } |
1712 } | 1715 } |
1713 } | 1716 } |
1714 | 1717 |
1727 if (null !== $this->languages) { | 1730 if (null !== $this->languages) { |
1728 return $this->languages; | 1731 return $this->languages; |
1729 } | 1732 } |
1730 | 1733 |
1731 $languages = AcceptHeader::fromString($this->headers->get('Accept-Language'))->all(); | 1734 $languages = AcceptHeader::fromString($this->headers->get('Accept-Language'))->all(); |
1732 $this->languages = array(); | 1735 $this->languages = []; |
1733 foreach ($languages as $lang => $acceptHeaderItem) { | 1736 foreach ($languages as $lang => $acceptHeaderItem) { |
1734 if (false !== strpos($lang, '-')) { | 1737 if (false !== strpos($lang, '-')) { |
1735 $codes = explode('-', $lang); | 1738 $codes = explode('-', $lang); |
1736 if ('i' === $codes[0]) { | 1739 if ('i' === $codes[0]) { |
1737 // Language not listed in ISO 639 that are not variants | 1740 // Language not listed in ISO 639 that are not variants |
1738 // of any listed language, which can be registered with the | 1741 // of any listed language, which can be registered with the |
1739 // i-prefix, such as i-cherokee | 1742 // i-prefix, such as i-cherokee |
1740 if (count($codes) > 1) { | 1743 if (\count($codes) > 1) { |
1741 $lang = $codes[1]; | 1744 $lang = $codes[1]; |
1742 } | 1745 } |
1743 } else { | 1746 } else { |
1744 for ($i = 0, $max = count($codes); $i < $max; ++$i) { | 1747 for ($i = 0, $max = \count($codes); $i < $max; ++$i) { |
1745 if (0 === $i) { | 1748 if (0 === $i) { |
1746 $lang = strtolower($codes[0]); | 1749 $lang = strtolower($codes[0]); |
1747 } else { | 1750 } else { |
1748 $lang .= '_'.strtoupper($codes[$i]); | 1751 $lang .= '_'.strtoupper($codes[$i]); |
1749 } | 1752 } |
1824 | 1827 |
1825 protected function prepareRequestUri() | 1828 protected function prepareRequestUri() |
1826 { | 1829 { |
1827 $requestUri = ''; | 1830 $requestUri = ''; |
1828 | 1831 |
1829 if ($this->headers->has('X_ORIGINAL_URL')) { | 1832 if ('1' == $this->server->get('IIS_WasUrlRewritten') && '' != $this->server->get('UNENCODED_URL')) { |
1830 // IIS with Microsoft Rewrite Module | |
1831 $requestUri = $this->headers->get('X_ORIGINAL_URL'); | |
1832 $this->headers->remove('X_ORIGINAL_URL'); | |
1833 $this->server->remove('HTTP_X_ORIGINAL_URL'); | |
1834 $this->server->remove('UNENCODED_URL'); | |
1835 $this->server->remove('IIS_WasUrlRewritten'); | |
1836 } elseif ($this->headers->has('X_REWRITE_URL')) { | |
1837 // IIS with ISAPI_Rewrite | |
1838 $requestUri = $this->headers->get('X_REWRITE_URL'); | |
1839 $this->headers->remove('X_REWRITE_URL'); | |
1840 } elseif ('1' == $this->server->get('IIS_WasUrlRewritten') && '' != $this->server->get('UNENCODED_URL')) { | |
1841 // IIS7 with URL Rewrite: make sure we get the unencoded URL (double slash problem) | 1833 // IIS7 with URL Rewrite: make sure we get the unencoded URL (double slash problem) |
1842 $requestUri = $this->server->get('UNENCODED_URL'); | 1834 $requestUri = $this->server->get('UNENCODED_URL'); |
1843 $this->server->remove('UNENCODED_URL'); | 1835 $this->server->remove('UNENCODED_URL'); |
1844 $this->server->remove('IIS_WasUrlRewritten'); | 1836 $this->server->remove('IIS_WasUrlRewritten'); |
1845 } elseif ($this->server->has('REQUEST_URI')) { | 1837 } elseif ($this->server->has('REQUEST_URI')) { |
1846 $requestUri = $this->server->get('REQUEST_URI'); | 1838 $requestUri = $this->server->get('REQUEST_URI'); |
1847 // HTTP proxy reqs setup request URI with scheme and host [and port] + the URL path, only use URL path | 1839 |
1848 $schemeAndHttpHost = $this->getSchemeAndHttpHost(); | 1840 if ('' !== $requestUri && '/' === $requestUri[0]) { |
1849 if (0 === strpos($requestUri, $schemeAndHttpHost)) { | 1841 // To only use path and query remove the fragment. |
1850 $requestUri = substr($requestUri, strlen($schemeAndHttpHost)); | 1842 if (false !== $pos = strpos($requestUri, '#')) { |
1843 $requestUri = substr($requestUri, 0, $pos); | |
1844 } | |
1845 } else { | |
1846 // HTTP proxy reqs setup request URI with scheme and host [and port] + the URL path, | |
1847 // only use URL path. | |
1848 $uriComponents = parse_url($requestUri); | |
1849 | |
1850 if (isset($uriComponents['path'])) { | |
1851 $requestUri = $uriComponents['path']; | |
1852 } | |
1853 | |
1854 if (isset($uriComponents['query'])) { | |
1855 $requestUri .= '?'.$uriComponents['query']; | |
1856 } | |
1851 } | 1857 } |
1852 } elseif ($this->server->has('ORIG_PATH_INFO')) { | 1858 } elseif ($this->server->has('ORIG_PATH_INFO')) { |
1853 // IIS 5.0, PHP as CGI | 1859 // IIS 5.0, PHP as CGI |
1854 $requestUri = $this->server->get('ORIG_PATH_INFO'); | 1860 $requestUri = $this->server->get('ORIG_PATH_INFO'); |
1855 if ('' != $this->server->get('QUERY_STRING')) { | 1861 if ('' != $this->server->get('QUERY_STRING')) { |
1885 $path = $this->server->get('PHP_SELF', ''); | 1891 $path = $this->server->get('PHP_SELF', ''); |
1886 $file = $this->server->get('SCRIPT_FILENAME', ''); | 1892 $file = $this->server->get('SCRIPT_FILENAME', ''); |
1887 $segs = explode('/', trim($file, '/')); | 1893 $segs = explode('/', trim($file, '/')); |
1888 $segs = array_reverse($segs); | 1894 $segs = array_reverse($segs); |
1889 $index = 0; | 1895 $index = 0; |
1890 $last = count($segs); | 1896 $last = \count($segs); |
1891 $baseUrl = ''; | 1897 $baseUrl = ''; |
1892 do { | 1898 do { |
1893 $seg = $segs[$index]; | 1899 $seg = $segs[$index]; |
1894 $baseUrl = '/'.$seg.$baseUrl; | 1900 $baseUrl = '/'.$seg.$baseUrl; |
1895 ++$index; | 1901 ++$index; |
1905 if ($baseUrl && false !== $prefix = $this->getUrlencodedPrefix($requestUri, $baseUrl)) { | 1911 if ($baseUrl && false !== $prefix = $this->getUrlencodedPrefix($requestUri, $baseUrl)) { |
1906 // full $baseUrl matches | 1912 // full $baseUrl matches |
1907 return $prefix; | 1913 return $prefix; |
1908 } | 1914 } |
1909 | 1915 |
1910 if ($baseUrl && false !== $prefix = $this->getUrlencodedPrefix($requestUri, rtrim(dirname($baseUrl), '/'.DIRECTORY_SEPARATOR).'/')) { | 1916 if ($baseUrl && false !== $prefix = $this->getUrlencodedPrefix($requestUri, rtrim(\dirname($baseUrl), '/'.\DIRECTORY_SEPARATOR).'/')) { |
1911 // directory portion of $baseUrl matches | 1917 // directory portion of $baseUrl matches |
1912 return rtrim($prefix, '/'.DIRECTORY_SEPARATOR); | 1918 return rtrim($prefix, '/'.\DIRECTORY_SEPARATOR); |
1913 } | 1919 } |
1914 | 1920 |
1915 $truncatedRequestUri = $requestUri; | 1921 $truncatedRequestUri = $requestUri; |
1916 if (false !== $pos = strpos($requestUri, '?')) { | 1922 if (false !== $pos = strpos($requestUri, '?')) { |
1917 $truncatedRequestUri = substr($requestUri, 0, $pos); | 1923 $truncatedRequestUri = substr($requestUri, 0, $pos); |
1924 } | 1930 } |
1925 | 1931 |
1926 // If using mod_rewrite or ISAPI_Rewrite strip the script filename | 1932 // If using mod_rewrite or ISAPI_Rewrite strip the script filename |
1927 // out of baseUrl. $pos !== 0 makes sure it is not matching a value | 1933 // out of baseUrl. $pos !== 0 makes sure it is not matching a value |
1928 // from PATH_INFO or QUERY_STRING | 1934 // from PATH_INFO or QUERY_STRING |
1929 if (strlen($requestUri) >= strlen($baseUrl) && (false !== $pos = strpos($requestUri, $baseUrl)) && 0 !== $pos) { | 1935 if (\strlen($requestUri) >= \strlen($baseUrl) && (false !== $pos = strpos($requestUri, $baseUrl)) && 0 !== $pos) { |
1930 $baseUrl = substr($requestUri, 0, $pos + strlen($baseUrl)); | 1936 $baseUrl = substr($requestUri, 0, $pos + \strlen($baseUrl)); |
1931 } | 1937 } |
1932 | 1938 |
1933 return rtrim($baseUrl, '/'.DIRECTORY_SEPARATOR); | 1939 return rtrim($baseUrl, '/'.\DIRECTORY_SEPARATOR); |
1934 } | 1940 } |
1935 | 1941 |
1936 /** | 1942 /** |
1937 * Prepares the base path. | 1943 * Prepares the base path. |
1938 * | 1944 * |
1945 return ''; | 1951 return ''; |
1946 } | 1952 } |
1947 | 1953 |
1948 $filename = basename($this->server->get('SCRIPT_FILENAME')); | 1954 $filename = basename($this->server->get('SCRIPT_FILENAME')); |
1949 if (basename($baseUrl) === $filename) { | 1955 if (basename($baseUrl) === $filename) { |
1950 $basePath = dirname($baseUrl); | 1956 $basePath = \dirname($baseUrl); |
1951 } else { | 1957 } else { |
1952 $basePath = $baseUrl; | 1958 $basePath = $baseUrl; |
1953 } | 1959 } |
1954 | 1960 |
1955 if ('\\' === DIRECTORY_SEPARATOR) { | 1961 if ('\\' === \DIRECTORY_SEPARATOR) { |
1956 $basePath = str_replace('\\', '/', $basePath); | 1962 $basePath = str_replace('\\', '/', $basePath); |
1957 } | 1963 } |
1958 | 1964 |
1959 return rtrim($basePath, '/'); | 1965 return rtrim($basePath, '/'); |
1960 } | 1966 } |
1980 | 1986 |
1981 if (null === ($baseUrl = $this->getBaseUrl())) { | 1987 if (null === ($baseUrl = $this->getBaseUrl())) { |
1982 return $requestUri; | 1988 return $requestUri; |
1983 } | 1989 } |
1984 | 1990 |
1985 $pathInfo = substr($requestUri, strlen($baseUrl)); | 1991 $pathInfo = substr($requestUri, \strlen($baseUrl)); |
1986 if (false === $pathInfo || '' === $pathInfo) { | 1992 if (false === $pathInfo || '' === $pathInfo) { |
1987 // If substr() returns false then PATH_INFO is set to an empty string | 1993 // If substr() returns false then PATH_INFO is set to an empty string |
1988 return '/'; | 1994 return '/'; |
1989 } | 1995 } |
1990 | 1996 |
1994 /** | 2000 /** |
1995 * Initializes HTTP request formats. | 2001 * Initializes HTTP request formats. |
1996 */ | 2002 */ |
1997 protected static function initializeFormats() | 2003 protected static function initializeFormats() |
1998 { | 2004 { |
1999 static::$formats = array( | 2005 static::$formats = [ |
2000 'html' => array('text/html', 'application/xhtml+xml'), | 2006 'html' => ['text/html', 'application/xhtml+xml'], |
2001 'txt' => array('text/plain'), | 2007 'txt' => ['text/plain'], |
2002 'js' => array('application/javascript', 'application/x-javascript', 'text/javascript'), | 2008 'js' => ['application/javascript', 'application/x-javascript', 'text/javascript'], |
2003 'css' => array('text/css'), | 2009 'css' => ['text/css'], |
2004 'json' => array('application/json', 'application/x-json'), | 2010 'json' => ['application/json', 'application/x-json'], |
2005 'jsonld' => array('application/ld+json'), | 2011 'jsonld' => ['application/ld+json'], |
2006 'xml' => array('text/xml', 'application/xml', 'application/x-xml'), | 2012 'xml' => ['text/xml', 'application/xml', 'application/x-xml'], |
2007 'rdf' => array('application/rdf+xml'), | 2013 'rdf' => ['application/rdf+xml'], |
2008 'atom' => array('application/atom+xml'), | 2014 'atom' => ['application/atom+xml'], |
2009 'rss' => array('application/rss+xml'), | 2015 'rss' => ['application/rss+xml'], |
2010 'form' => array('application/x-www-form-urlencoded'), | 2016 'form' => ['application/x-www-form-urlencoded'], |
2011 ); | 2017 ]; |
2012 } | 2018 } |
2013 | 2019 |
2014 /** | 2020 /** |
2015 * Sets the default PHP locale. | 2021 * Sets the default PHP locale. |
2016 * | 2022 * |
2042 { | 2048 { |
2043 if (0 !== strpos(rawurldecode($string), $prefix)) { | 2049 if (0 !== strpos(rawurldecode($string), $prefix)) { |
2044 return false; | 2050 return false; |
2045 } | 2051 } |
2046 | 2052 |
2047 $len = strlen($prefix); | 2053 $len = \strlen($prefix); |
2048 | 2054 |
2049 if (preg_match(sprintf('#^(%%[[:xdigit:]]{2}|.){%d}#', $len), $string, $match)) { | 2055 if (preg_match(sprintf('#^(%%[[:xdigit:]]{2}|.){%d}#', $len), $string, $match)) { |
2050 return $match[0]; | 2056 return $match[0]; |
2051 } | 2057 } |
2052 | 2058 |
2053 return false; | 2059 return false; |
2054 } | 2060 } |
2055 | 2061 |
2056 private static function createRequestFromFactory(array $query = array(), array $request = array(), array $attributes = array(), array $cookies = array(), array $files = array(), array $server = array(), $content = null) | 2062 private static function createRequestFromFactory(array $query = [], array $request = [], array $attributes = [], array $cookies = [], array $files = [], array $server = [], $content = null) |
2057 { | 2063 { |
2058 if (self::$requestFactory) { | 2064 if (self::$requestFactory) { |
2059 $request = call_user_func(self::$requestFactory, $query, $request, $attributes, $cookies, $files, $server, $content); | 2065 $request = \call_user_func(self::$requestFactory, $query, $request, $attributes, $cookies, $files, $server, $content); |
2060 | 2066 |
2061 if (!$request instanceof self) { | 2067 if (!$request instanceof self) { |
2062 throw new \LogicException('The Request factory must return an instance of Symfony\Component\HttpFoundation\Request.'); | 2068 throw new \LogicException('The Request factory must return an instance of Symfony\Component\HttpFoundation\Request.'); |
2063 } | 2069 } |
2064 | 2070 |
2081 return self::$trustedProxies && IpUtils::checkIp($this->server->get('REMOTE_ADDR'), self::$trustedProxies); | 2087 return self::$trustedProxies && IpUtils::checkIp($this->server->get('REMOTE_ADDR'), self::$trustedProxies); |
2082 } | 2088 } |
2083 | 2089 |
2084 private function getTrustedValues($type, $ip = null) | 2090 private function getTrustedValues($type, $ip = null) |
2085 { | 2091 { |
2086 $clientValues = array(); | 2092 $clientValues = []; |
2087 $forwardedValues = array(); | 2093 $forwardedValues = []; |
2088 | 2094 |
2089 if (self::$trustedHeaders[$type] && $this->headers->has(self::$trustedHeaders[$type])) { | 2095 if (self::$trustedHeaders[$type] && $this->headers->has(self::$trustedHeaders[$type])) { |
2090 foreach (explode(',', $this->headers->get(self::$trustedHeaders[$type])) as $v) { | 2096 foreach (explode(',', $this->headers->get(self::$trustedHeaders[$type])) as $v) { |
2091 $clientValues[] = (self::HEADER_CLIENT_PORT === $type ? '0.0.0.0:' : '').trim($v); | 2097 $clientValues[] = (self::HEADER_CLIENT_PORT === $type ? '0.0.0.0:' : '').trim($v); |
2092 } | 2098 } |
2093 } | 2099 } |
2094 | 2100 |
2095 if (self::$trustedHeaders[self::HEADER_FORWARDED] && $this->headers->has(self::$trustedHeaders[self::HEADER_FORWARDED])) { | 2101 if (self::$trustedHeaders[self::HEADER_FORWARDED] && $this->headers->has(self::$trustedHeaders[self::HEADER_FORWARDED])) { |
2096 $forwardedValues = $this->headers->get(self::$trustedHeaders[self::HEADER_FORWARDED]); | 2102 $forwardedValues = $this->headers->get(self::$trustedHeaders[self::HEADER_FORWARDED]); |
2097 $forwardedValues = preg_match_all(sprintf('{(?:%s)=(?:"?\[?)([a-zA-Z0-9\.:_\-/]*+)}', self::$forwardedParams[$type]), $forwardedValues, $matches) ? $matches[1] : array(); | 2103 $forwardedValues = preg_match_all(sprintf('{(?:%s)="?([a-zA-Z0-9\.:_\-/\[\]]*+)}', self::$forwardedParams[$type]), $forwardedValues, $matches) ? $matches[1] : []; |
2104 if (self::HEADER_CLIENT_PORT === $type) { | |
2105 foreach ($forwardedValues as $k => $v) { | |
2106 if (']' === substr($v, -1) || false === $v = strrchr($v, ':')) { | |
2107 $v = $this->isSecure() ? ':443' : ':80'; | |
2108 } | |
2109 $forwardedValues[$k] = '0.0.0.0'.$v; | |
2110 } | |
2111 } | |
2098 } | 2112 } |
2099 | 2113 |
2100 if (null !== $ip) { | 2114 if (null !== $ip) { |
2101 $clientValues = $this->normalizeAndFilterClientIps($clientValues, $ip); | 2115 $clientValues = $this->normalizeAndFilterClientIps($clientValues, $ip); |
2102 $forwardedValues = $this->normalizeAndFilterClientIps($forwardedValues, $ip); | 2116 $forwardedValues = $this->normalizeAndFilterClientIps($forwardedValues, $ip); |
2109 if (!$forwardedValues) { | 2123 if (!$forwardedValues) { |
2110 return $clientValues; | 2124 return $clientValues; |
2111 } | 2125 } |
2112 | 2126 |
2113 if (!$this->isForwardedValid) { | 2127 if (!$this->isForwardedValid) { |
2114 return null !== $ip ? array('0.0.0.0', $ip) : array(); | 2128 return null !== $ip ? ['0.0.0.0', $ip] : []; |
2115 } | 2129 } |
2116 $this->isForwardedValid = false; | 2130 $this->isForwardedValid = false; |
2117 | 2131 |
2118 throw new ConflictingHeadersException(sprintf('The request has both a trusted "%s" header and a trusted "%s" header, conflicting with each other. You should either configure your proxy to remove one of them, or configure your project to distrust the offending one.', self::$trustedHeaders[self::HEADER_FORWARDED], self::$trustedHeaders[$type])); | 2132 throw new ConflictingHeadersException(sprintf('The request has both a trusted "%s" header and a trusted "%s" header, conflicting with each other. You should either configure your proxy to remove one of them, or configure your project to distrust the offending one.', self::$trustedHeaders[self::HEADER_FORWARDED], self::$trustedHeaders[$type])); |
2119 } | 2133 } |
2120 | 2134 |
2121 private function normalizeAndFilterClientIps(array $clientIps, $ip) | 2135 private function normalizeAndFilterClientIps(array $clientIps, $ip) |
2122 { | 2136 { |
2123 if (!$clientIps) { | 2137 if (!$clientIps) { |
2124 return array(); | 2138 return []; |
2125 } | 2139 } |
2126 $clientIps[] = $ip; // Complete the IP chain with the IP the request actually came from | 2140 $clientIps[] = $ip; // Complete the IP chain with the IP the request actually came from |
2127 $firstTrustedIp = null; | 2141 $firstTrustedIp = null; |
2128 | 2142 |
2129 foreach ($clientIps as $key => $clientIp) { | 2143 foreach ($clientIps as $key => $clientIp) { |
2130 // Remove port (unfortunately, it does happen) | 2144 if (strpos($clientIp, '.')) { |
2131 if (preg_match('{((?:\d+\.){3}\d+)\:\d+}', $clientIp, $match)) { | 2145 // Strip :port from IPv4 addresses. This is allowed in Forwarded |
2132 $clientIps[$key] = $clientIp = $match[1]; | 2146 // and may occur in X-Forwarded-For. |
2147 $i = strpos($clientIp, ':'); | |
2148 if ($i) { | |
2149 $clientIps[$key] = $clientIp = substr($clientIp, 0, $i); | |
2150 } | |
2151 } elseif (0 === strpos($clientIp, '[')) { | |
2152 // Strip brackets and :port from IPv6 addresses. | |
2153 $i = strpos($clientIp, ']', 1); | |
2154 $clientIps[$key] = $clientIp = substr($clientIp, 1, $i - 1); | |
2133 } | 2155 } |
2134 | 2156 |
2135 if (!filter_var($clientIp, FILTER_VALIDATE_IP)) { | 2157 if (!filter_var($clientIp, FILTER_VALIDATE_IP)) { |
2136 unset($clientIps[$key]); | 2158 unset($clientIps[$key]); |
2137 | 2159 |
2147 } | 2169 } |
2148 } | 2170 } |
2149 } | 2171 } |
2150 | 2172 |
2151 // Now the IP chain contains only untrusted proxies and the client IP | 2173 // Now the IP chain contains only untrusted proxies and the client IP |
2152 return $clientIps ? array_reverse($clientIps) : array($firstTrustedIp); | 2174 return $clientIps ? array_reverse($clientIps) : [$firstTrustedIp]; |
2153 } | 2175 } |
2154 } | 2176 } |