-
-
Notifications
You must be signed in to change notification settings - Fork 9.7k
Description
Symfony version(s) affected: 3.4+
Description
There is currently no way to unset a HTTP request header through the BrowserKit AbstractBrowser
/ Client
. This was requested before in #20306, but actually implementing an unsetServerParameter
method would not help in our case.
The problem we're facing here (in API Platform) is that when we send a request using HttpKernelBrowser
/ Client
:
symfony/src/Symfony/Component/HttpKernel/Client.php
Lines 136 to 138 in f1edae0
protected function filterRequest(DomRequest $request) | |
{ | |
$httpRequest = Request::create($request->getUri(), $request->getMethod(), $request->getParameters(), $request->getCookies(), $request->getFiles(), $request->getServer(), $request->getContent()); |
it calls (HttpFoundation) Request::create
which adds some default request headers:
symfony/src/Symfony/Component/HttpFoundation/Request.php
Lines 309 to 324 in f1edae0
public static function create($uri, $method = 'GET', $parameters = [], $cookies = [], $files = [], $server = [], $content = null) | |
{ | |
$server = array_replace([ | |
'SERVER_NAME' => 'localhost', | |
'SERVER_PORT' => 80, | |
'HTTP_HOST' => 'localhost', | |
'HTTP_USER_AGENT' => 'Symfony', | |
'HTTP_ACCEPT' => 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8', | |
'HTTP_ACCEPT_LANGUAGE' => 'en-us,en;q=0.5', | |
'HTTP_ACCEPT_CHARSET' => 'ISO-8859-1,utf-8;q=0.7,*;q=0.7', | |
'REMOTE_ADDR' => '127.0.0.1', | |
'SCRIPT_NAME' => '', | |
'SCRIPT_FILENAME' => '', | |
'SERVER_PROTOCOL' => 'HTTP/1.1', | |
'REQUEST_TIME' => time(), | |
], $server); |
This includes the Accept
header, which we need to be able to remove in order to test content negotiation scenarios where the client doesn't send the Accept
header, thereby resulting in the use of the default media type.
How to reproduce
We had been using a workaround to unset the Accept
header in our test suite, basically:
$client->setServerParameter('HTTP_ACCEPT', null);
The end result in the HeaderBag
is:
array(1) {
["accept"]=>
array(1) {
[0]=>
NULL
}
}
However, fixes in HeaderBag::get
, specifically the change made to this line:
return \count($headers[$key]) ? (string) $headers[$key][0] : $default; |
means that we get an empty string now instead of null
.
Possible Solution
So this breaks our test suite. We could find new workarounds, including checking for the case where the Accept
header is an empty string (weird!), or overriding / extending some parts of the chain which sends the request in our test suite.
However, we're wondering if there might be a better way of fixing this for everyone. It was an ugly workaround in the first place.
This problem also affects ApiTestCase
in API Platform, as the user would be unable to send a request without any of the default headers.
Additional context