Skip to content

Commit

Permalink
Make URL HEAD request result in empty response body
Browse files Browse the repository at this point in the history
Now URL HEAD request result in non-empty response,
so I added some changes where the request appears.

Bug: 757387
Change-Id: I67354d134faa7962af680d01fb114e0cf13523db
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1767285
Commit-Queue: Canon Mukai <canonmukai@google.com>
Reviewed-by: Matt Menke <mmenke@chromium.org>
Reviewed-by: Kinuko Yasuda <kinuko@chromium.org>
Reviewed-by: Adam Rice <ricea@chromium.org>
Reviewed-by: Yutaka Hirano <yhirano@chromium.org>
Cr-Commit-Position: refs/heads/master@{#690685}
  • Loading branch information
CanonMukai authored and Commit Bot committed Aug 27, 2019
1 parent 84d1534 commit ff237dd
Show file tree
Hide file tree
Showing 15 changed files with 91 additions and 46 deletions.
4 changes: 2 additions & 2 deletions content/browser/data_url_loader_factory.cc
Original file line number Diff line number Diff line change
Expand Up @@ -58,8 +58,8 @@ void DataURLLoaderFactory::CreateLoaderAndStart(
url = &request.url;
}

int result = net::URLRequestDataJob::BuildResponse(*url, &mime_type, &charset,
&data, headers.get());
int result = net::URLRequestDataJob::BuildResponse(
*url, request.method, &mime_type, &charset, &data, headers.get());
url_ = GURL(); // Don't need it anymore.

if (result != net::OK) {
Expand Down
8 changes: 7 additions & 1 deletion net/url_request/url_request_data_job.cc
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
namespace net {

int URLRequestDataJob::BuildResponse(const GURL& url,
base::StringPiece method,
std::string* mime_type,
std::string* charset,
std::string* data,
Expand All @@ -39,6 +40,10 @@ int URLRequestDataJob::BuildResponse(const GURL& url,
headers->AddHeader(content_type_header);
}

if (base::EqualsCaseInsensitiveASCII(method, "HEAD")) {
data->clear();
}

return OK;
}

Expand All @@ -59,7 +64,8 @@ int URLRequestDataJob::GetData(std::string* mime_type,

// TODO(tyoshino): Get the headers and export via
// URLRequestJob::GetResponseInfo().
return BuildResponse(url, mime_type, charset, data, nullptr);
return BuildResponse(url, request_->method(), mime_type, charset, data,
nullptr);
}

URLRequestDataJob::~URLRequestDataJob() = default;
Expand Down
1 change: 1 addition & 0 deletions net/url_request/url_request_data_job.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ class NET_EXPORT URLRequestDataJob : public URLRequestSimpleJob {
// Extracts info from a data scheme URL. Returns OK if successful. Returns
// ERR_INVALID_URL otherwise.
static int BuildResponse(const GURL& url,
base::StringPiece method,
std::string* mime_type,
std::string* charset,
std::string* data,
Expand Down
38 changes: 31 additions & 7 deletions net/url_request/url_request_data_job_unittest.cc
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,9 @@ TEST(BuildResponseTest, Simple) {
scoped_refptr<HttpResponseHeaders> headers(
new HttpResponseHeaders(std::string()));

ASSERT_EQ(OK,
URLRequestDataJob::BuildResponse(GURL("data:,Hello"), &mime_type,
&charset, &data, headers.get()));
ASSERT_EQ(OK, URLRequestDataJob::BuildResponse(GURL("data:,Hello"), "GET",
&mime_type, &charset, &data,
headers.get()));

EXPECT_EQ("text/plain", mime_type);
EXPECT_EQ("US-ASCII", charset);
Expand All @@ -39,6 +39,30 @@ TEST(BuildResponseTest, Simple) {
value.clear();
}

TEST(BuildResponseTest, HeadMethod) {
std::string mime_type;
std::string charset;
std::string data;
scoped_refptr<HttpResponseHeaders> headers =
HttpResponseHeaders::TryToCreate("");

ASSERT_EQ(OK, URLRequestDataJob::BuildResponse(GURL("data:,Hello"), "HEAD",
&mime_type, &charset, &data,
headers.get()));

EXPECT_EQ("text/plain", mime_type);
EXPECT_EQ("US-ASCII", charset);
EXPECT_EQ("", data);

HttpVersion version = headers->GetHttpVersion();
EXPECT_EQ(1, version.major_value());
EXPECT_EQ(1, version.minor_value());
EXPECT_EQ("OK", headers->GetStatusText());
std::string content_type;
EXPECT_TRUE(headers->GetNormalizedHeader("Content-Type", &content_type));
EXPECT_EQ(content_type, "text/plain;charset=US-ASCII");
}

TEST(BuildResponseTest, InvalidInput) {
std::string mime_type;
std::string charset;
Expand All @@ -47,7 +71,7 @@ TEST(BuildResponseTest, InvalidInput) {
new HttpResponseHeaders(std::string()));

EXPECT_EQ(ERR_INVALID_URL,
URLRequestDataJob::BuildResponse(GURL("bogus"), &mime_type,
URLRequestDataJob::BuildResponse(GURL("bogus"), "GET", &mime_type,
&charset, &data, headers.get()));
}

Expand All @@ -61,8 +85,8 @@ TEST(BuildResponseTest, InvalidMimeType) {
// MIME type contains delimiters. Must be accepted but Content-Type header
// should be generated as if the mediatype was text/plain.
EXPECT_EQ(OK, URLRequestDataJob::BuildResponse(GURL("data:f(o/b)r,test"),
&mime_type, &charset, &data,
headers.get()));
"GET", &mime_type, &charset,
&data, headers.get()));

std::string value;
EXPECT_TRUE(headers->GetNormalizedHeader("Content-Type", &value));
Expand All @@ -78,7 +102,7 @@ TEST(BuildResponseTest, InvalidCharset) {

// MIME type contains delimiters. Must be rejected.
EXPECT_EQ(ERR_INVALID_URL, URLRequestDataJob::BuildResponse(
GURL("data:text/html;charset=(),test"),
GURL("data:text/html;charset=(),test"), "GET",
&mime_type, &charset, &data, headers.get()));
}

Expand Down
18 changes: 18 additions & 0 deletions net/websockets/websocket_deflater_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,24 @@ TEST(WebSocketDeflaterTest, WindowBits10) {
ToString(actual.get()));
}

// I add this test.
TEST(WebSocketDeflaterTest, WindowBits11) {
WebSocketDeflater deflater(WebSocketDeflater::DO_NOT_TAKE_OVER_CONTEXT);
deflater.Initialize(10);
// Set the head and tail of |input| so that back-reference
// can be used if the window size is sufficiently-large.
const std::string word = "Chromium";
std::string input = word + std::string(256, 'a') + word;
scoped_refptr<IOBufferWithSize> actual;

ASSERT_TRUE(deflater.AddBytes(input.data(), input.size()));
ASSERT_TRUE(deflater.Finish());
actual = deflater.GetOutput(deflater.CurrentOutputSize());
EXPECT_EQ(
std::string("r\xce(\xca\xcf\xcd,\xcdM\x1c\xe1\xc0\x19\x1a\x0e\0\0", 17),
ToString(actual.get()));
}

} // namespace

} // namespace net
Original file line number Diff line number Diff line change
Expand Up @@ -685,7 +685,8 @@ Resource* ResourceFetcher::ResourceForStaticData(
scoped_refptr<SharedBuffer> data;
if (url.ProtocolIsData()) {
int result;
std::tie(result, response, data) = network_utils::ParseDataURL(url);
std::tie(result, response, data) = network_utils::ParseDataURL(
url, params.GetResourceRequest().HttpMethod());
if (result != net::OK) {
return nullptr;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1246,7 +1246,7 @@ void ResourceLoader::RequestSynchronously(const ResourceRequest& request) {
// CanHandleDataURLRequestLocally() has already checked if the data url can
// be handled here.
std::tie(result, response, data) =
network_utils::ParseDataURL(resource_->Url());
network_utils::ParseDataURL(resource_->Url(), request.HttpMethod());
if (result != net::OK) {
error_out = WebURLError(result, resource_->Url());
} else {
Expand Down Expand Up @@ -1454,8 +1454,8 @@ void ResourceLoader::HandleDataUrl() {
// data url with invalid mime type in some cases.
// CanHandleDataURLRequestLocally() has already checked if the data url can be
// handled here.
std::tie(result, response, data) =
network_utils::ParseDataURL(resource_->Url());
std::tie(result, response, data) = network_utils::ParseDataURL(
resource_->Url(), resource_->GetResourceRequest().HttpMethod());
if (result != net::OK) {
HandleError(ResourceError(result, resource_->Url(), base::nullopt));
return;
Expand Down
6 changes: 4 additions & 2 deletions third_party/blink/renderer/platform/network/network_utils.cc
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,8 @@ String GetDomainAndRegistry(const String& host, PrivateRegistryFilter filter) {
}

std::tuple<int, ResourceResponse, scoped_refptr<SharedBuffer>> ParseDataURL(
const KURL& url) {
const KURL& url,
const String& method) {
// The following code contains duplication of GetInfoFromDataURL() and
// WebURLLoaderImpl::PopulateURLResponse() in
// content/child/web_url_loader_impl.cc. Merge them once content/child is
Expand All @@ -77,7 +78,8 @@ std::tuple<int, ResourceResponse, scoped_refptr<SharedBuffer>> ParseDataURL(
auto headers = base::MakeRefCounted<net::HttpResponseHeaders>(std::string());

int result = net::URLRequestDataJob::BuildResponse(
GURL(url), &utf8_mime_type, &utf8_charset, &data_string, headers.get());
GURL(url), method.Ascii(), &utf8_mime_type, &utf8_charset, &data_string,
headers.get());
if (result != net::OK)
return std::make_tuple(result, ResourceResponse(), nullptr);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ PLATFORM_EXPORT String GetDomainAndRegistry(const String& host,
// was successful. The result is returned as net error code. It returns net::OK
// if decoding succeeds, otherwise it failed.
PLATFORM_EXPORT std::tuple<int, ResourceResponse, scoped_refptr<SharedBuffer>>
ParseDataURL(const KURL&);
ParseDataURL(const KURL&, const String& method);

// Returns true if the URL is a data URL and its MIME type is in the list of
// supported/recognized MIME types.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -150,7 +150,8 @@ void WebURLLoaderMockFactoryImpl::FillNavigationParamsResponse(
ResourceResponse response;
scoped_refptr<SharedBuffer> buffer;
int result;
std::tie(result, response, buffer) = network_utils::ParseDataURL(kurl);
std::tie(result, response, buffer) =
network_utils::ParseDataURL(kurl, params->http_method);
DCHECK(buffer);
DCHECK_EQ(net::OK, result);
params->response = WrappedResourceResponse(response);
Expand Down

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ FAIL XHR method GET with MIME type image/png assert_equals: expected "Hello, Wor
PASS XHR method POST with MIME type text/plain
PASS XHR method PUT with MIME type text/plain
PASS XHR method DELETE with MIME type text/plain
FAIL XHR method HEAD with MIME type text/plain assert_equals: expected "" but got "Hello, World!"
PASS XHR method HEAD with MIME type text/plain
PASS XHR method UNICORN with MIME type text/plain
Harness: the test ran to completion.

19 changes: 19 additions & 0 deletions third_party/blink/web_tests/http/tests/fetch/script-tests/fetch.js
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,25 @@ promise_test(function(t) {
function() {});
}, 'fetch invalid data: URL');

promise_test(function(t) {
return fetch('data:,Foobar',
{
method: 'HEAD'
})
.then(function(response) {
assert_equals(response.status, 200);
assert_equals(response.statusText, 'OK');
assert_equals(response.headers.get('Content-Type'),
'text/plain;charset=US-ASCII');
assert_equals(size(response.headers), 1);
assert_equals(response.type, 'basic', 'type must match.');
return response.text();
})
.then(function(text) {
assert_equals(text, '');
});
}, 'fetch data: URL with the HEAD method');

// Only [Exposed=(Window,DedicatedWorker,SharedWorker)].
if ('createObjectURL' in URL) {
// Tests for blob: scheme.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,11 +26,6 @@ var TEST_TARGETS = [
[fetchResolved, noContentLength, hasContentType, noServerHeader, hasBody,
typeBasic],
[checkJsonpSuccess]],
[BASE_URL + 'url=' + encodeURIComponent(url) +
'&mode=same-origin&method=HEAD',
[fetchResolved, noContentLength, hasContentType, noServerHeader, hasBody,
typeBasic],
[checkJsonpSuccess]],

// data: requests with same-origin redirects.
[REDIRECT_URL + encodeURIComponent(url) + '&mode=same-origin&method=GET',
Expand Down

0 comments on commit ff237dd

Please sign in to comment.