diff options
-rw-r--r-- | net/base/load_flags.h | 7 | ||||
-rw-r--r-- | net/http/http_network_transaction.cc | 14 | ||||
-rw-r--r-- | net/http/http_network_transaction_unittest.cc | 46 | ||||
-rw-r--r-- | net/tools/testserver/testserver.py | 21 | ||||
-rw-r--r-- | net/url_request/url_request_http_job.cc | 3 | ||||
-rw-r--r-- | net/url_request/url_request_unittest.cc | 85 |
6 files changed, 170 insertions, 6 deletions
diff --git a/net/base/load_flags.h b/net/base/load_flags.h index 2c007a6..49c6daf 100644 --- a/net/base/load_flags.h +++ b/net/base/load_flags.h @@ -70,6 +70,13 @@ enum { // Requires EV certificate verification. LOAD_VERIFY_EV_CERT = 1 << 16, + + // This load will not send any cookies. + LOAD_DO_NOT_SEND_COOKIES = 1 << 17, + + // This load will not send authentication data (user name/password) + // to the server (as opposed to the proxy). + LOAD_DO_NOT_SEND_AUTH_DATA = 1 << 18, }; } // namespace net diff --git a/net/http/http_network_transaction.cc b/net/http/http_network_transaction.cc index 7f5942e..4af1fa3 100644 --- a/net/http/http_network_transaction.cc +++ b/net/http/http_network_transaction.cc @@ -1683,7 +1683,8 @@ bool HttpNetworkTransaction::ShouldApplyProxyAuth() const { } bool HttpNetworkTransaction::ShouldApplyServerAuth() const { - return !establishing_tunnel_; + return !establishing_tunnel_ && + !(request_->load_flags & LOAD_DO_NOT_SEND_AUTH_DATA); } std::string HttpNetworkTransaction::BuildAuthorizationHeader( @@ -1886,10 +1887,13 @@ int HttpNetworkTransaction::HandleAuthChallenge() { auth_identity_[target].invalid = true; - // Find the best authentication challenge that we support. - HttpAuth::ChooseBestChallenge(response_.headers.get(), - target, - &auth_handler_[target]); + if (target != HttpAuth::AUTH_SERVER || + !(request_->load_flags & LOAD_DO_NOT_SEND_AUTH_DATA)) { + // Find the best authentication challenge that we support. + HttpAuth::ChooseBestChallenge(response_.headers.get(), + target, + &auth_handler_[target]); + } if (!auth_handler_[target]) { if (establishing_tunnel_) { diff --git a/net/http/http_network_transaction_unittest.cc b/net/http/http_network_transaction_unittest.cc index 9993b1d..d63546d 100644 --- a/net/http/http_network_transaction_unittest.cc +++ b/net/http/http_network_transaction_unittest.cc @@ -729,6 +729,48 @@ TEST_F(HttpNetworkTransactionTest, BasicAuth) { EXPECT_EQ(100, response->headers->GetContentLength()); } +TEST_F(HttpNetworkTransactionTest, DoNotSendAuth) { + SessionDependencies session_deps; + scoped_ptr<HttpTransaction> trans( + new HttpNetworkTransaction( + CreateSession(&session_deps), + &session_deps.socket_factory)); + + HttpRequestInfo request; + request.method = "GET"; + request.url = GURL("http://www.google.com/"); + request.load_flags = net::LOAD_DO_NOT_SEND_AUTH_DATA; + + MockWrite data_writes[] = { + MockWrite("GET / HTTP/1.1\r\n" + "Host: www.google.com\r\n" + "Connection: keep-alive\r\n\r\n"), + }; + + MockRead data_reads[] = { + MockRead("HTTP/1.0 401 Unauthorized\r\n"), + MockRead("WWW-Authenticate: Basic realm=\"MyRealm1\"\r\n"), + MockRead("Content-Type: text/html; charset=iso-8859-1\r\n"), + // Large content-length -- won't matter, as connection will be reset. + MockRead("Content-Length: 10000\r\n\r\n"), + MockRead(false, ERR_FAILED), + }; + + StaticMockSocket data(data_reads, data_writes); + session_deps.socket_factory.AddMockSocket(&data); + TestCompletionCallback callback; + + int rv = trans->Start(&request, &callback, NULL); + EXPECT_EQ(ERR_IO_PENDING, rv); + + rv = callback.WaitForResult(); + EXPECT_EQ(0, rv); + + const HttpResponseInfo* response = trans->GetResponseInfo(); + ASSERT_FALSE(response == NULL); + EXPECT_TRUE(response->auth_challenge.get() == NULL); +} + // Test the request-challenge-retry sequence for basic auth, over a keep-alive // connection. TEST_F(HttpNetworkTransactionTest, BasicAuthKeepAlive) { @@ -979,7 +1021,9 @@ TEST_F(HttpNetworkTransactionTest, BasicAuthProxyKeepAlive) { HttpRequestInfo request; request.method = "GET"; request.url = GURL("https://www.google.com/"); - request.load_flags = 0; + // Ensure that proxy authentication is attempted even + // when the no authentication data flag is set. + request.load_flags = net::LOAD_DO_NOT_SEND_AUTH_DATA; // Since we have proxy, should try to establish tunnel. MockWrite data_writes1[] = { diff --git a/net/tools/testserver/testserver.py b/net/tools/testserver/testserver.py index aeee5e2..065ea7b 100644 --- a/net/tools/testserver/testserver.py +++ b/net/tools/testserver/testserver.py @@ -117,6 +117,7 @@ class TestPageHandler(BaseHTTPServer.BaseHTTPRequestHandler): self.FileHandler, self.RealFileWithCommonHeaderHandler, self.RealBZ2FileWithCommonHeaderHandler, + self.SetCookieHandler, self.AuthBasicHandler, self.AuthDigestHandler, self.SlowServerHandler, @@ -699,6 +700,26 @@ class TestPageHandler(BaseHTTPServer.BaseHTTPRequestHandler): return True + def SetCookieHandler(self): + """This handler just sets a cookie, for testing cookie handling.""" + + if not self._ShouldHandleRequest("/set-cookie"): + return False + + query_char = self.path.find('?') + if query_char != -1: + cookie_values = self.path[query_char + 1:].split('&') + else: + cookie_values = ("",) + self.send_response(200) + self.send_header('Content-type', 'text/html') + for cookie_value in cookie_values: + self.send_header('Set-Cookie', '%s' % cookie_value) + self.end_headers() + for cookie_value in cookie_values: + self.wfile.write('%s' % cookie_value) + return True + def AuthBasicHandler(self): """This handler tests 'Basic' authentication. It just sends a page with title 'user/pass' if you succeed.""" diff --git a/net/url_request/url_request_http_job.cc b/net/url_request/url_request_http_job.cc index b019c48..b0438fa 100644 --- a/net/url_request/url_request_http_job.cc +++ b/net/url_request/url_request_http_job.cc @@ -661,6 +661,9 @@ void URLRequestHttpJob::AddExtraHeaders() { } std::string URLRequestHttpJob::AssembleRequestCookies() { + if (request_info_.load_flags & net::LOAD_DO_NOT_SEND_COOKIES) + return std::string(); + URLRequestContext* context = request_->context(); if (context) { // Add in the cookie header. TODO might we need more than one header? diff --git a/net/url_request/url_request_unittest.cc b/net/url_request/url_request_unittest.cc index afa2c6c..b224c2e 100644 --- a/net/url_request/url_request_unittest.cc +++ b/net/url_request/url_request_unittest.cc @@ -1307,6 +1307,91 @@ TEST_F(URLRequestTestHTTP, BasicAuthWithCookies) { } } +TEST_F(URLRequestTest, DoNotSendCookies) { + scoped_refptr<HTTPTestServer> server = + HTTPTestServer::CreateServer(L"", NULL); + ASSERT_TRUE(NULL != server.get()); + scoped_refptr<URLRequestContext> context = new URLRequestTestContext(); + + // Set up a cookie. + { + TestDelegate d; + URLRequest req(server->TestServerPage("set-cookie?CookieToNotSend=1"), &d); + req.set_context(context); + req.Start(); + MessageLoop::current()->Run(); + } + + // Verify that the cookie is set. + { + TestDelegate d; + TestURLRequest req(server->TestServerPage("echoheader?Cookie"), &d); + req.set_context(context); + req.Start(); + MessageLoop::current()->Run(); + + EXPECT_TRUE(d.data_received().find("CookieToNotSend=1") + != std::string::npos); + } + + // Verify that the cookie isn't sent when LOAD_DO_NOT_SEND_COOKIES is set. + { + TestDelegate d; + TestURLRequest req(server->TestServerPage("echoheader?Cookie"), &d); + req.set_load_flags(net::LOAD_DO_NOT_SEND_COOKIES); + req.set_context(context); + req.Start(); + MessageLoop::current()->Run(); + + EXPECT_TRUE(d.data_received().find("Cookie: CookieToNotSend=1") + == std::string::npos); + } +} + +TEST_F(URLRequestTest, DoNotSaveCookies) { + scoped_refptr<HTTPTestServer> server = + HTTPTestServer::CreateServer(L"", NULL); + ASSERT_TRUE(NULL != server.get()); + scoped_refptr<URLRequestContext> context = new URLRequestTestContext(); + + // Set up a cookie. + { + TestDelegate d; + URLRequest req(server->TestServerPage("set-cookie?CookieToNotUpdate=2"), + &d); + req.set_context(context); + req.Start(); + MessageLoop::current()->Run(); + } + + // Try to set-up another cookie and update the previous cookie. + { + scoped_refptr<URLRequestContext> context = new URLRequestTestContext(); + TestDelegate d; + URLRequest req(server->TestServerPage( + "set-cookie?CookieToNotSave=1&CookieToNotUpdate=1"), &d); + req.set_load_flags(net::LOAD_DO_NOT_SAVE_COOKIES); + req.set_context(context); + req.Start(); + + MessageLoop::current()->Run(); + } + + // Verify the cookies weren't saved or updated. + { + TestDelegate d; + TestURLRequest req(server->TestServerPage("echoheader?Cookie"), &d); + req.set_context(context); + req.Start(); + MessageLoop::current()->Run(); + + EXPECT_TRUE(d.data_received().find("CookieToNotSave=1") + == std::string::npos); + EXPECT_TRUE(d.data_received().find("CookieToNotUpdate=2") + != std::string::npos); + } +} + // In this test, we do a POST which the server will 302 redirect. // The subsequent transaction should use GET, and should not send the // Content-Type header. |