diff --git a/src/Symfony/Component/HttpClient/HttpClientTrait.php b/src/Symfony/Component/HttpClient/HttpClientTrait.php index abf7d86c80..0023e3bbb0 100644 --- a/src/Symfony/Component/HttpClient/HttpClientTrait.php +++ b/src/Symfony/Component/HttpClient/HttpClientTrait.php @@ -481,17 +481,20 @@ trait HttpClientTrait } } - foreach ($queryArray as $k => $v) { - if (is_scalar($v)) { - $queryArray[$k] = rawurlencode($k).'='.rawurlencode($v); - } elseif (null === $v) { - unset($queryArray[$k]); - - if ($replace) { + if ($replace) { + foreach ($queryArray as $k => $v) { + if (null === $v) { unset($query[$k]); } - } else { - throw new InvalidArgumentException(sprintf('Unsupported value for query parameter "%s": scalar or null expected, %s given.', $k, \gettype($v))); + } + } + + $queryString = http_build_query($queryArray, '', '&', PHP_QUERY_RFC3986); + $queryArray = []; + + if ($queryString) { + foreach (explode('&', $queryString) as $v) { + $queryArray[rawurldecode(explode('=', $v, 2)[0])] = $v; } } diff --git a/src/Symfony/Component/HttpClient/Tests/HttpClientTraitTest.php b/src/Symfony/Component/HttpClient/Tests/HttpClientTraitTest.php index 5a55ec424e..056181e30e 100644 --- a/src/Symfony/Component/HttpClient/Tests/HttpClientTraitTest.php +++ b/src/Symfony/Component/HttpClient/Tests/HttpClientTraitTest.php @@ -141,6 +141,10 @@ class HttpClientTraitTest extends TestCase yield [[null, null, 'bar', '?a=1&c=c', null], 'bar?a=a&b=b', ['b' => null, 'c' => 'c', 'a' => 1]]; yield [[null, null, 'bar', '?a=b+c&b=b', null], 'bar?a=b+c', ['b' => 'b']]; yield [[null, null, 'bar', '?a=b%2B%20c', null], 'bar?a=b+c', ['a' => 'b+ c']]; + yield [[null, null, 'bar', '?a%5Bb%5D=c', null], 'bar', ['a' => ['b' => 'c']]]; + yield [[null, null, 'bar', '?a%5Bb%5Bc%5D=d', null], 'bar?a[b[c]=d', []]; + yield [[null, null, 'bar', '?a%5Bb%5D%5Bc%5D=dd', null], 'bar?a[b][c]=d&e[f]=g', ['a' => ['b' => ['c' => 'dd']], 'e[f]' => null]]; + yield [[null, null, 'bar', '?a=b&a%5Bb%20c%5D=d&e%3Df=%E2%9C%93', null], 'bar?a=b', ['a' => ['b c' => 'd'], 'e=f' => '✓']]; } /**