Chromium Code Reviews| Index: net/http/http_stream_factory_impl_job_controller_unittest.cc |
| diff --git a/net/http/http_stream_factory_impl_job_controller_unittest.cc b/net/http/http_stream_factory_impl_job_controller_unittest.cc |
| index 395372995aeba3dba4f535ea7c029862ba479aae..f2845e0c8ade5222577783bfae2356f5b10aadb8 100644 |
| --- a/net/http/http_stream_factory_impl_job_controller_unittest.cc |
| +++ b/net/http/http_stream_factory_impl_job_controller_unittest.cc |
| @@ -8,6 +8,7 @@ |
| #include "base/memory/ptr_util.h" |
| #include "base/run_loop.h" |
| +#include "net/base/test_proxy_delegate.h" |
| #include "net/dns/mock_host_resolver.h" |
| #include "net/http/http_basic_stream.h" |
| #include "net/http/http_stream_factory_impl_request.h" |
| @@ -18,6 +19,7 @@ |
| #include "net/proxy/proxy_service.h" |
| #include "net/quic/test_tools/quic_stream_factory_peer.h" |
| #include "net/spdy/spdy_test_util_common.h" |
| +#include "testing/gmock/include/gmock/gmock.h" |
| #include "testing/gmock_mutant.h" |
| #include "testing/gtest/include/gtest/gtest.h" |
| @@ -108,7 +110,21 @@ class HttpStreamFactoryImplJobControllerTest |
| session_deps_.enable_quic = true; |
| } |
| - void Initialize() { |
| + void Initialize(bool use_alternative_proxy) { |
| + if (use_alternative_proxy) { |
| + std::unique_ptr<ProxyService> proxy_service = |
| + ProxyService::CreateFixedFromPacResult("HTTPS myproxy.org:443"); |
| + session_deps_.proxy_service.reset(proxy_service.release()); |
| + |
| + std::unique_ptr<TestProxyDelegate> test_proxy_delegate( |
| + new TestProxyDelegate()); |
| + test_proxy_delegate_ = test_proxy_delegate.get(); |
| + |
| + test_proxy_delegate->set_alternative_proxy_server( |
| + ProxyServer::FromPacString("QUIC myproxy.org:443")); |
| + EXPECT_TRUE(test_proxy_delegate->alternative_proxy_server().is_quic()); |
| + session_deps_.proxy_delegate.reset(test_proxy_delegate.release()); |
| + } |
| session_ = SpdySessionDependencies::SpdyCreateSession(&session_deps_); |
| factory_ = |
| static_cast<HttpStreamFactoryImpl*>(session_->http_stream_factory()); |
| @@ -117,6 +133,10 @@ class HttpStreamFactoryImplJobControllerTest |
| HttpStreamFactoryImplPeer::AddJobController(factory_, job_controller_); |
| } |
| + TestProxyDelegate* test_proxy_delegate() const { |
| + return test_proxy_delegate_; |
| + } |
| + |
| ~HttpStreamFactoryImplJobControllerTest() {} |
| void SetAlternativeService(const HttpRequestInfo& request_info, |
| @@ -128,6 +148,8 @@ class HttpStreamFactoryImplJobControllerTest |
| server, alternative_service, expiration); |
| } |
| + // Not owned by |this|. |
| + TestProxyDelegate* test_proxy_delegate_; |
| TestJobFactory job_factory_; |
| MockHttpStreamRequestDelegate request_delegate_; |
| SpdySessionDependencies session_deps_; |
| @@ -149,7 +171,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, |
| session_deps_.proxy_service.reset(new ProxyService( |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -179,7 +201,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, |
| session_deps_.proxy_service.reset(new ProxyService( |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -213,7 +235,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, CancelJobsBeforeBinding) { |
| session_deps_.proxy_service.reset(new ProxyService( |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -246,7 +268,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, OnStreamFailedForBothJobs) { |
| session_deps_.proxy_service.reset(new ProxyService( |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -290,7 +312,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, |
| session_deps_.proxy_service.reset(new ProxyService( |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -342,7 +364,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, |
| session_deps_.proxy_service.reset(new ProxyService( |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -390,7 +412,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, GetLoadStateAfterMainJobFailed) { |
| session_deps_.proxy_service.reset(new ProxyService( |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -441,7 +463,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, DoNotResumeMainJobBeforeWait) { |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(new FailingProxyResolverFactory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -467,7 +489,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, DoNotResumeMainJobBeforeWait) { |
| TEST_F(HttpStreamFactoryImplJobControllerTest, InvalidPortForQuic) { |
| // Using a restricted port 101 for QUIC should fail and the alternative job |
| // should post OnStreamFailedCall on the controller to resume the main job. |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -509,7 +531,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, |
| session_deps_.host_resolver.reset(host_resolver); |
| session_deps_.host_resolver->set_synchronous_mode(false); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -573,7 +595,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, |
| base::WrapUnique(new ProxyConfigServiceFixed(proxy_config)), |
| base::WrapUnique(proxy_resolver_factory), nullptr)); |
| - Initialize(); |
| + Initialize(false); |
| HttpRequestInfo request_info; |
| request_info.method = "GET"; |
| @@ -626,7 +648,7 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, DelayedTCP) { |
| HangingResolver* resolver = new HangingResolver(); |
| session_deps_.host_resolver.reset(resolver); |
| - Initialize(); |
| + Initialize(false); |
| // Enable delayed TCP and set time delay for waiting job. |
| QuicStreamFactory* quic_stream_factory = session_->quic_stream_factory(); |
| @@ -663,4 +685,96 @@ TEST_F(HttpStreamFactoryImplJobControllerTest, DelayedTCP) { |
| base::RunLoop().RunUntilIdle(); |
| } |
| + |
| +// Verifies that the main job is resumed properly after a delay when the |
| +// alternative proxy server job hangs. |
| +TEST_F(HttpStreamFactoryImplJobControllerTest, DelayedTCPAlternativeProxy) { |
|
Zhongyi Shi
2016/08/20 06:15:40
Now that you are here, shall we add a test case co
tbansal1
2016/08/22 15:42:33
Done.
|
| + // Using hanging resolver will cause the alternative job to hang indefinitely. |
| + HangingResolver* resolver = new HangingResolver(); |
| + session_deps_.host_resolver.reset(resolver); |
| + |
| + Initialize(true); |
| + EXPECT_TRUE(test_proxy_delegate()->alternative_proxy_server().is_quic()); |
| + |
| + // Enable delayed TCP and set time delay for waiting job. |
| + QuicStreamFactory* quic_stream_factory = session_->quic_stream_factory(); |
| + test::QuicStreamFactoryPeer::SetDelayTcpRace(quic_stream_factory, true); |
| + quic_stream_factory->set_require_confirmation(false); |
| + ServerNetworkStats stats1; |
| + stats1.srtt = base::TimeDelta::FromMicroseconds(10); |
| + session_->http_server_properties()->SetServerNetworkStats( |
| + url::SchemeHostPort(GURL("https://myproxy.org")), stats1); |
| + |
| + HttpRequestInfo request_info; |
| + request_info.method = "GET"; |
| + request_info.url = GURL("http://mail.example.org/"); |
| + |
| + request_.reset( |
| + job_controller_->Start(request_info, &request_delegate_, nullptr, |
| + BoundNetLog(), HttpStreamRequest::HTTP_STREAM, |
| + DEFAULT_PRIORITY, SSLConfig(), SSLConfig())); |
| + EXPECT_TRUE(job_controller_->main_job()); |
| + EXPECT_TRUE(job_controller_->main_job()->is_waiting()); |
| + EXPECT_TRUE(job_controller_->alternative_job()); |
| + |
| + // The alternative proxy server job stalls when connecting to the alternative |
| + // proxy server, and controller should resume the main job after delay. |
| + // Verify the waiting time for delayed main job. |
| + EXPECT_CALL(*job_factory_.main_job(), Resume()) |
| + .WillOnce(Invoke(testing::CreateFunctor( |
| + &JobControllerPeer::VerifyWaitingTimeForMainJob, job_controller_, |
| + base::TimeDelta::FromMicroseconds(15)))); |
| + |
| + base::RunLoop().RunUntilIdle(); |
| + // Since the main job did not complete successfully, the alternative proxy |
| + // server should not be marked as bad. |
| + EXPECT_TRUE(test_proxy_delegate()->alternative_proxy_server().is_valid()); |
| +} |
| + |
| +// Verifies that the alternative proxy server job fails immediately, and the |
| +// main job is not blocked. |
|
Zhongyi Shi
2016/08/20 06:15:40
nit: remove redundant space in comments.
tbansal1
2016/08/22 15:42:33
Done.
|
| +TEST_F(HttpStreamFactoryImplJobControllerTest, FailAlternativeProxy) { |
| + // Using failing resolver will cause the alternative job to fail. |
| + FailingHostResolver* resolver = new FailingHostResolver(); |
| + session_deps_.host_resolver.reset(resolver); |
| + |
| + Initialize(true); |
| + EXPECT_TRUE(test_proxy_delegate()->alternative_proxy_server().is_quic()); |
| + |
| + // Enable delayed TCP and set time delay for waiting job. |
| + QuicStreamFactory* quic_stream_factory = session_->quic_stream_factory(); |
| + test::QuicStreamFactoryPeer::SetDelayTcpRace(quic_stream_factory, true); |
| + quic_stream_factory->set_require_confirmation(false); |
| + ServerNetworkStats stats1; |
| + stats1.srtt = base::TimeDelta::FromMicroseconds(300 * 1000); |
| + session_->http_server_properties()->SetServerNetworkStats( |
| + url::SchemeHostPort(GURL("https://myproxy.org")), stats1); |
| + |
| + HttpRequestInfo request_info; |
| + request_info.method = "GET"; |
| + request_info.url = GURL("http://mail.example.org/"); |
| + |
| + request_.reset( |
| + job_controller_->Start(request_info, &request_delegate_, nullptr, |
| + BoundNetLog(), HttpStreamRequest::HTTP_STREAM, |
| + DEFAULT_PRIORITY, SSLConfig(), SSLConfig())); |
| + EXPECT_TRUE(job_controller_->main_job()); |
| + EXPECT_TRUE(job_controller_->alternative_job()); |
| + |
| + EXPECT_CALL(request_delegate_, OnStreamFailed(_, _)).Times(1); |
| + EXPECT_CALL(request_delegate_, OnStreamReady(_, _, _)).Times(0); |
| + EXPECT_CALL(*job_factory_.main_job(), MarkOtherJobComplete(_)).Times(1); |
| + |
| + // Since the alternative proxy server job fails to connect, the main job |
| + // should not be blocked. |
| + EXPECT_CALL(*job_factory_.main_job(), Resume()).Times(0); |
| + |
| + base::RunLoop().RunUntilIdle(); |
| + EXPECT_FALSE(job_controller_->alternative_job()); |
| + EXPECT_FALSE(job_controller_->main_job()->is_waiting()); |
| + // Since the main job did not complete successfully, the alternative proxy |
| + // server should not be marked as bad. |
| + EXPECT_TRUE(test_proxy_delegate()->alternative_proxy_server().is_valid()); |
| +} |
| + |
| } // namespace net |