PluginProbe
Yoast SEO – Advanced SEO with real-time guidance and built-in AI / trunk
Yoast SEO – Advanced SEO with real-time guidance and built-in AI vtrunk
28.5 28.4 28.3 28.2 28.1 28.0 27.9 27.8 27.7 27.6 27.5 trunk 18.0 18.1 18.2 18.3 18.4 18.4.1 18.5 18.5.1 18.6 18.7 18.8 18.9 19.0 All 129 releases
← All changes | vendor_prefixed/guzzlehttp/psr7/src/Header.php +110 -25 18.8 → trunk View file →
@@ -1,6 +1,7 @@
1 1 <?php
2 2
3 +declare (strict_types=1);
3 4 namespace YoastSEO_Vendor\GuzzleHttp\Psr7;
4 5
5 6 final class Header
6 7 {
@@ -10,32 +11,65 @@
10 11 * of the header. When a parameter does not contain a value, but just
11 12 * contains a key, this function will inject a key with a '' string value.
12 13 *
13 14 * @param string|array $header Header to parse into components.
14 - *
15 - * @return array Returns the parsed header values.
16 15 */
17 - public static function parse($header)
16 + public static function parse($header) : array
18 17 {
19 18 static $trimmed = "\"' \n\t\r";
20 19 $params = $matches = [];
21 - foreach (self::normalize($header) as $val) {
22 - $part = [];
23 - foreach (\preg_split('/;(?=([^"]*"[^"]*")*[^"]*$)/', $val) as $kvp) {
24 - if (\preg_match_all('/<[^>]+>|[^=]+/', $kvp, $matches)) {
25 - $m = $matches[0];
26 - if (isset($m[1])) {
27 - $part[\trim($m[0], $trimmed)] = \trim($m[1], $trimmed);
28 - } else {
29 - $part[] = \trim($m[0], $trimmed);
20 + foreach ((array) $header as $value) {
21 + foreach (self::splitList($value) as $val) {
22 + $part = [];
23 + foreach (self::splitParameters($val) as $kvp) {
24 + if (\preg_match_all('/<[^>]+>|[^=]+/', $kvp, $matches)) {
25 + $m = $matches[0];
26 + if (isset($m[1])) {
27 + $part[\trim($m[0], $trimmed)] = \trim($m[1], $trimmed);
28 + } else {
29 + $part[] = \trim($m[0], $trimmed);
30 + }
30 31 }
31 32 }
33 + if ($part) {
34 + $params[] = $part;
35 + }
32 36 }
33 - if ($part) {
34 - $params[] = $part;
37 + }
38 + return $params;
39 + }
40 + /**
41 + * Split a header value into semicolon-separated parameters.
42 + *
43 + * @return string[]
44 + */
45 + private static function splitParameters(string $value) : array
46 + {
47 + $values = [];
48 + $start = 0;
49 + $isQuoted = \false;
50 + $isEscaped = \false;
51 + for ($i = 0, $max = \strlen($value); $i < $max; ++$i) {
52 + $char = $value[$i];
53 + if ($isEscaped) {
54 + $isEscaped = \false;
55 + continue;
35 56 }
57 + if ($isQuoted && $char === '\\') {
58 + $isEscaped = \true;
59 + continue;
60 + }
61 + if ($char === '"') {
62 + $isQuoted = !$isQuoted;
63 + continue;
64 + }
65 + if (!$isQuoted && $char === ';') {
66 + $values[] = \substr($value, $start, $i - $start);
67 + $start = $i + 1;
68 + }
36 69 }
37 - return $params;
70 + $values[] = \substr($value, $start);
71 + return $values;
38 72 }
39 73 /**
40 74 * Converts an array of header values that may contain comma separated
41 75 * headers into an array of headers with no comma separated values.
@@ -41,25 +75,76 @@
41 75 * headers into an array of headers with no comma separated values.
42 76 *
43 77 * @param string|array $header Header to normalize.
44 78 *
45 - * @return array Returns the normalized header field values.
79 + * @deprecated Use self::splitList() instead.
46 80 */
47 - public static function normalize($header)
81 + public static function normalize($header) : array
48 82 {
49 - if (!\is_array($header)) {
50 - return \array_map('trim', \explode(',', $header));
83 + \YoastSEO_Vendor\trigger_deprecation('guzzlehttp/psr7', '2.3', 'Header::normalize() is deprecated and will be removed in guzzlehttp/psr7 3.0. Use Header::splitList() instead.');
84 + $result = [];
85 + foreach ((array) $header as $value) {
86 + foreach (self::splitList($value) as $parsed) {
87 + $result[] = $parsed;
88 + }
51 89 }
90 + return $result;
91 + }
92 + /**
93 + * Splits a HTTP header defined to contain a comma-separated list into
94 + * each individual value. Empty values will be removed.
95 + *
96 + * Example headers include 'accept', 'cache-control' and 'if-none-match'.
97 + *
98 + * This method must not be used to parse headers that are not defined as
99 + * a list, such as 'user-agent' or 'set-cookie'.
100 + *
101 + * @param string|string[] $values Header value as returned by MessageInterface::getHeader()
102 + *
103 + * @return string[]
104 + */
105 + public static function splitList($values) : array
106 + {
107 + if (!\is_array($values)) {
108 + $values = [$values];
109 + }
52 110 $result = [];
53 - foreach ($header as $value) {
54 - foreach ((array) $value as $v) {
55 - if (\strpos($v, ',') === \false) {
56 - $result[] = $v;
111 + foreach ($values as $value) {
112 + if (!\is_string($value)) {
113 + throw new \TypeError('$header must either be a string or an array containing strings.');
114 + }
115 + $v = '';
116 + $isQuoted = \false;
117 + $isEscaped = \false;
118 + for ($i = 0, $max = \strlen($value); $i < $max; ++$i) {
119 + if ($isEscaped) {
120 + $v .= $value[$i];
121 + $isEscaped = \false;
57 122 continue;
58 123 }
59 - foreach (\preg_split('/,(?=([^"]*"[^"]*")*[^"]*$)/', $v) as $vv) {
60 - $result[] = \trim($vv);
124 + if (!$isQuoted && $value[$i] === ',') {
125 + $v = \trim($v, " \n\r\t\x00\v");
126 + if ($v !== '') {
127 + $result[] = $v;
128 + }
129 + $v = '';
130 + continue;
61 131 }
132 + if ($isQuoted && $value[$i] === '\\') {
133 + $isEscaped = \true;
134 + $v .= $value[$i];
135 + continue;
136 + }
137 + if ($value[$i] === '"') {
138 + $isQuoted = !$isQuoted;
139 + $v .= $value[$i];
140 + continue;
141 + }
142 + $v .= $value[$i];
143 + }
144 + $v = \trim($v, " \n\r\t\x00\v");
145 + if ($v !== '') {
146 + $result[] = $v;
62 147 }
63 148 }
64 149 return $result;
65 150 }