Index: net/http/http_stream_factory_impl_unittest.cc |
diff --git a/net/http/http_stream_factory_impl_unittest.cc b/net/http/http_stream_factory_impl_unittest.cc |
index 0200b8f984cbbc2c8649fda32015b8ff7ae21bec..210e940ad4b9b05440fba64308a6964d4cb6615c 100644 |
--- a/net/http/http_stream_factory_impl_unittest.cc |
+++ b/net/http/http_stream_factory_impl_unittest.cc |
@@ -5,6 +5,7 @@ |
#include "net/http/http_stream_factory_impl.h" |
#include <string> |
+#include <vector> |
#include "base/basictypes.h" |
#include "net/base/net_log.h" |
@@ -16,26 +17,72 @@ |
#include "net/http/http_network_session_peer.h" |
#include "net/http/http_network_transaction.h" |
#include "net/http/http_request_info.h" |
+#include "net/http/http_server_properties.h" |
#include "net/http/http_server_properties_impl.h" |
#include "net/http/http_stream.h" |
#include "net/http/transport_security_state.h" |
#include "net/proxy/proxy_info.h" |
#include "net/proxy/proxy_service.h" |
+#include "net/socket/client_socket_handle.h" |
#include "net/socket/mock_client_socket_pool_manager.h" |
+#include "net/socket/next_proto.h" |
#include "net/socket/socket_test_util.h" |
#include "net/spdy/spdy_session.h" |
#include "net/spdy/spdy_session_pool.h" |
+#include "net/spdy/spdy_test_util_common.h" |
+#include "net/ssl/ssl_config_service.h" |
#include "net/ssl/ssl_config_service_defaults.h" |
+// This file can be included from net/http even though |
+// it is in net/websockets because it doesn't |
+// introduce any link dependency to net/websockets. |
+#include "net/websockets/websocket_stream_base.h" |
#include "testing/gtest/include/gtest/gtest.h" |
namespace net { |
namespace { |
-class MockHttpStreamFactoryImpl : public HttpStreamFactoryImpl { |
+class UseAlternateProtocolsScopedSetter { |
public: |
- MockHttpStreamFactoryImpl(HttpNetworkSession* session) |
- : HttpStreamFactoryImpl(session), |
+ UseAlternateProtocolsScopedSetter(bool use_alternate_protocols) |
+ : use_alternate_protocols_(HttpStreamFactory::use_alternate_protocols()) { |
+ HttpStreamFactory::set_use_alternate_protocols(use_alternate_protocols); |
+ } |
+ ~UseAlternateProtocolsScopedSetter() { |
+ HttpStreamFactory::set_use_alternate_protocols(use_alternate_protocols_); |
+ } |
+ |
+ private: |
+ bool use_alternate_protocols_; |
+}; |
+ |
+class MockWebSocketStream : public WebSocketStreamBase { |
+ public: |
+ enum StreamType { |
+ kStreamTypeBasic, |
+ kStreamTypeSpdy, |
+ }; |
+ |
+ explicit MockWebSocketStream(StreamType type) : type_(type) {} |
+ |
+ virtual ~MockWebSocketStream() {} |
+ |
+ virtual WebSocketStream* AsWebSocketStream() OVERRIDE { return NULL; } |
+ |
+ StreamType type() const { |
+ return type_; |
+ } |
+ |
+ private: |
+ const StreamType type_; |
+}; |
+ |
+// HttpStreamFactoryImpl subclass that can wait until a preconnect is complete. |
+class MockHttpStreamFactoryImplForPreconnect : public HttpStreamFactoryImpl { |
+ public: |
+ MockHttpStreamFactoryImplForPreconnect(HttpNetworkSession* session, |
+ bool for_websockets) |
+ : HttpStreamFactoryImpl(session, for_websockets), |
preconnect_done_(false), |
waiting_for_preconnect_(false) {} |
@@ -77,6 +124,19 @@ class StreamRequestWaiter : public HttpStreamRequest::Delegate { |
base::MessageLoop::current()->Quit(); |
stream_.reset(stream); |
used_ssl_config_ = used_ssl_config; |
+ used_proxy_info_ = used_proxy_info; |
+ } |
+ |
+ virtual void OnWebSocketStreamReady( |
+ const SSLConfig& used_ssl_config, |
+ const ProxyInfo& used_proxy_info, |
+ WebSocketStreamBase* stream) OVERRIDE { |
+ stream_done_ = true; |
+ if (waiting_for_stream_) |
+ base::MessageLoop::current()->Quit(); |
+ websocket_stream_.reset(stream); |
+ used_ssl_config_ = used_ssl_config; |
+ used_proxy_info_ = used_proxy_info; |
} |
virtual void OnStreamFailed( |
@@ -113,20 +173,75 @@ class StreamRequestWaiter : public HttpStreamRequest::Delegate { |
return used_ssl_config_; |
} |
+ const ProxyInfo& used_proxy_info() const { |
+ return used_proxy_info_; |
+ } |
+ |
HttpStreamBase* stream() { |
return stream_.get(); |
} |
+ MockWebSocketStream* websocket_stream() { |
+ return static_cast<MockWebSocketStream*>(websocket_stream_.get()); |
+ } |
+ |
+ bool stream_done() const { return stream_done_; } |
private: |
bool waiting_for_stream_; |
bool stream_done_; |
scoped_ptr<HttpStreamBase> stream_; |
+ scoped_ptr<WebSocketStreamBase> websocket_stream_; |
SSLConfig used_ssl_config_; |
+ ProxyInfo used_proxy_info_; |
DISALLOW_COPY_AND_ASSIGN(StreamRequestWaiter); |
}; |
+class WebSocketSpdyStream : public MockWebSocketStream { |
+ public: |
+ explicit WebSocketSpdyStream(SpdySession* spdy_session) |
+ : MockWebSocketStream(kStreamTypeSpdy), spdy_session_(spdy_session) {} |
+ |
+ virtual ~WebSocketSpdyStream() {} |
+ |
+ SpdySession* spdy_session() { return spdy_session_.get(); } |
+ |
+ private: |
+ scoped_refptr<SpdySession> spdy_session_; |
+}; |
+ |
+class WebSocketBasicStream : public MockWebSocketStream { |
+ public: |
+ explicit WebSocketBasicStream(ClientSocketHandle* connection) |
+ : MockWebSocketStream(kStreamTypeBasic), connection_(connection) {} |
+ |
+ virtual ~WebSocketBasicStream() { |
+ connection_->socket()->Disconnect(); |
+ } |
+ |
+ ClientSocketHandle* connection() { return connection_.get(); } |
+ |
+ private: |
+ scoped_ptr<ClientSocketHandle> connection_; |
+}; |
+ |
+class WebSocketStreamFactory : public WebSocketStreamBase::Factory { |
+ public: |
+ virtual ~WebSocketStreamFactory() {} |
+ |
+ virtual WebSocketStreamBase* CreateBasicStream(ClientSocketHandle* connection, |
+ bool using_proxy) OVERRIDE { |
+ return new WebSocketBasicStream(connection); |
+ } |
+ |
+ virtual WebSocketStreamBase* CreateSpdyStream( |
+ SpdySession* spdy_session, |
+ bool use_relative_url) OVERRIDE { |
+ return new WebSocketSpdyStream(spdy_session); |
+ } |
+}; |
+ |
struct SessionDependencies { |
// Custom proxy service dependency. |
explicit SessionDependencies(ProxyService* proxy_service) |
@@ -163,6 +278,7 @@ HttpNetworkSession* CreateSession(SessionDependencies* session_deps) { |
session_deps->http_auth_handler_factory.get(); |
params.net_log = session_deps->net_log; |
params.http_server_properties = &session_deps->http_server_properties; |
+ |
return new HttpNetworkSession(params); |
} |
@@ -182,8 +298,8 @@ void PreconnectHelperForURL(int num_streams, |
const GURL& url, |
HttpNetworkSession* session) { |
HttpNetworkSessionPeer peer(session); |
- MockHttpStreamFactoryImpl* mock_factory = |
- new MockHttpStreamFactoryImpl(session); |
+ MockHttpStreamFactoryImplForPreconnect* mock_factory = |
+ new MockHttpStreamFactoryImplForPreconnect(session, false); |
peer.SetHttpStreamFactory(mock_factory); |
SSLConfig ssl_config; |
session->ssl_config_service()->GetSSLConfig(&ssl_config); |
@@ -465,7 +581,7 @@ TEST(HttpStreamFactoryTest, JobNotifiesProxy) { |
scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
- // Now request a stream. It should succeed using the second proxy in the |
+ // Now request a stream. It should succeed using the second proxy in the |
// list. |
HttpRequestInfo request_info; |
request_info.method = "GET"; |
@@ -537,7 +653,7 @@ int GetSocketPoolGroupCount(ClientSocketPool* pool) { |
} |
return count; |
} |
-}; |
+} // namespace |
TEST(HttpStreamFactoryTest, PrivacyModeUsesDifferentSocketPoolGroup) { |
SessionDependencies session_deps(ProxyService::CreateDirect()); |
@@ -615,6 +731,442 @@ TEST(HttpStreamFactoryTest, GetLoadState) { |
waiter.WaitForStream(); |
} |
+TEST(HttpStreamFactoryTest, RequestHttpStream) { |
+ SessionDependencies session_deps(ProxyService::CreateDirect()); |
+ |
+ StaticSocketDataProvider socket_data; |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory.AddSocketDataProvider(&socket_data); |
+ |
+ scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
+ |
+ // Now request a stream. It should succeed using the second proxy in the |
+ // list. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("http://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->http_stream_factory()->RequestStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ ASSERT_TRUE(NULL != waiter.stream()); |
+ EXPECT_TRUE(NULL == waiter.websocket_stream()); |
+ EXPECT_FALSE(waiter.stream()->IsSpdyHttpStream()); |
+ |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount(session->GetSSLSocketPool( |
+ HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_TRUE(waiter.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, RequestHttpStreamOverSSL) { |
+ SessionDependencies session_deps(ProxyService::CreateDirect()); |
+ |
+ MockRead mock_read(ASYNC, OK); |
+ StaticSocketDataProvider socket_data(&mock_read, 1, NULL, 0); |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory.AddSocketDataProvider(&socket_data); |
+ |
+ SSLSocketDataProvider ssl_socket_data(ASYNC, OK); |
+ session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_socket_data); |
+ |
+ scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
+ |
+ // Now request a stream. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("https://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->http_stream_factory()->RequestStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ ASSERT_TRUE(NULL != waiter.stream()); |
+ EXPECT_TRUE(NULL == waiter.websocket_stream()); |
+ EXPECT_FALSE(waiter.stream()->IsSpdyHttpStream()); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_TRUE(waiter.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, RequestHttpStreamOverProxy) { |
+ SessionDependencies session_deps(ProxyService::CreateFixed("myproxy:8888")); |
+ |
+ StaticSocketDataProvider socket_data; |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory.AddSocketDataProvider(&socket_data); |
+ |
+ scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
+ |
+ // Now request a stream. It should succeed using the second proxy in the |
+ // list. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("http://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->http_stream_factory()->RequestStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ ASSERT_TRUE(NULL != waiter.stream()); |
+ EXPECT_TRUE(NULL == waiter.websocket_stream()); |
+ EXPECT_FALSE(waiter.stream()->IsSpdyHttpStream()); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount(session->GetSocketPoolForHTTPProxy( |
+ HttpNetworkSession::NORMAL_SOCKET_POOL, |
+ HostPortPair("myproxy", 8888)))); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount(session->GetSocketPoolForSSLWithProxy( |
+ HttpNetworkSession::NORMAL_SOCKET_POOL, |
+ HostPortPair("myproxy", 8888)))); |
+ EXPECT_FALSE(waiter.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, RequestWebSocketBasicStream) { |
+ SessionDependencies session_deps(ProxyService::CreateDirect()); |
+ |
+ StaticSocketDataProvider socket_data; |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory.AddSocketDataProvider(&socket_data); |
+ |
+ scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
+ |
+ // Now request a stream. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("ws://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ WebSocketStreamFactory factory; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->websocket_stream_factory()->RequestWebSocketStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ &factory, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ EXPECT_TRUE(NULL == waiter.stream()); |
+ ASSERT_TRUE(NULL != waiter.websocket_stream()); |
+ EXPECT_EQ(MockWebSocketStream::kStreamTypeBasic, |
+ waiter.websocket_stream()->type()); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_TRUE(waiter.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, RequestWebSocketBasicStreamOverSSL) { |
+ SessionDependencies session_deps(ProxyService::CreateDirect()); |
+ |
+ MockRead mock_read(ASYNC, OK); |
+ StaticSocketDataProvider socket_data(&mock_read, 1, NULL, 0); |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory.AddSocketDataProvider(&socket_data); |
+ |
+ SSLSocketDataProvider ssl_socket_data(ASYNC, OK); |
+ session_deps.socket_factory.AddSSLSocketDataProvider(&ssl_socket_data); |
+ |
+ scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
+ |
+ // Now request a stream. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("wss://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ WebSocketStreamFactory factory; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->websocket_stream_factory()->RequestWebSocketStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ &factory, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ EXPECT_TRUE(NULL == waiter.stream()); |
+ ASSERT_TRUE(NULL != waiter.websocket_stream()); |
+ EXPECT_EQ(MockWebSocketStream::kStreamTypeBasic, |
+ waiter.websocket_stream()->type()); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_TRUE(waiter.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, RequestWebSocketBasicStreamOverProxy) { |
+ SessionDependencies session_deps(ProxyService::CreateFixed("myproxy:8888")); |
+ |
+ MockRead read(SYNCHRONOUS, "HTTP/1.0 200 Connection established\r\n\r\n"); |
+ StaticSocketDataProvider socket_data(&read, 1, 0, 0); |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory.AddSocketDataProvider(&socket_data); |
+ |
+ scoped_refptr<HttpNetworkSession> session(CreateSession(&session_deps)); |
+ |
+ // Now request a stream. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("ws://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ WebSocketStreamFactory factory; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->websocket_stream_factory()->RequestWebSocketStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ &factory, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ EXPECT_TRUE(NULL == waiter.stream()); |
+ ASSERT_TRUE(NULL != waiter.websocket_stream()); |
+ EXPECT_EQ(MockWebSocketStream::kStreamTypeBasic, |
+ waiter.websocket_stream()->type()); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount(session->GetSocketPoolForHTTPProxy( |
+ HttpNetworkSession::NORMAL_SOCKET_POOL, |
+ HostPortPair("myproxy", 8888)))); |
+ EXPECT_EQ(0, GetSocketPoolGroupCount(session->GetSocketPoolForSSLWithProxy( |
+ HttpNetworkSession::NORMAL_SOCKET_POOL, |
+ HostPortPair("myproxy", 8888)))); |
+ EXPECT_FALSE(waiter.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, RequestSpdyHttpStream) { |
+ SpdySessionDependencies session_deps(kProtoSPDY3, |
+ ProxyService::CreateDirect()); |
+ |
+ MockRead mock_read(ASYNC, OK); |
+ StaticSocketDataProvider socket_data(&mock_read, 1, NULL, 0); |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory->AddSocketDataProvider(&socket_data); |
+ |
+ SSLSocketDataProvider ssl_socket_data(ASYNC, OK); |
+ ssl_socket_data.SetNextProto(kProtoSPDY3); |
+ session_deps.socket_factory->AddSSLSocketDataProvider(&ssl_socket_data); |
+ |
+ HostPortPair host_port_pair("www.google.com", 443); |
+ scoped_refptr<HttpNetworkSession> |
+ session(SpdySessionDependencies::SpdyCreateSession(&session_deps)); |
+ |
+ // Now request a stream. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("https://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->http_stream_factory()->RequestStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ EXPECT_TRUE(NULL == waiter.websocket_stream()); |
+ ASSERT_TRUE(NULL != waiter.stream()); |
+ EXPECT_TRUE(waiter.stream()->IsSpdyHttpStream()); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_TRUE(waiter.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, RequestWebSocketSpdyStream) { |
+ SpdySessionDependencies session_deps(kProtoSPDY3, |
+ ProxyService::CreateDirect()); |
+ |
+ MockRead mock_read(SYNCHRONOUS, ERR_IO_PENDING); |
+ StaticSocketDataProvider socket_data(&mock_read, 1, NULL, 0); |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory->AddSocketDataProvider(&socket_data); |
+ |
+ SSLSocketDataProvider ssl_socket_data(ASYNC, OK); |
+ ssl_socket_data.SetNextProto(kProtoSPDY3); |
+ session_deps.socket_factory->AddSSLSocketDataProvider(&ssl_socket_data); |
+ |
+ HostPortPair host_port_pair("www.google.com", 80); |
+ scoped_refptr<HttpNetworkSession> |
+ session(SpdySessionDependencies::SpdyCreateSession(&session_deps)); |
+ |
+ // Now request a stream. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("wss://www.google.com"); |
+ request_info.load_flags = 0; |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter1; |
+ WebSocketStreamFactory factory; |
+ scoped_ptr<HttpStreamRequest> request1( |
+ session->websocket_stream_factory()->RequestWebSocketStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter1, |
+ &factory, |
+ BoundNetLog())); |
+ waiter1.WaitForStream(); |
+ EXPECT_TRUE(waiter1.stream_done()); |
+ ASSERT_TRUE(NULL != waiter1.websocket_stream()); |
+ EXPECT_EQ(MockWebSocketStream::kStreamTypeSpdy, |
+ waiter1.websocket_stream()->type()); |
+ EXPECT_TRUE(NULL == waiter1.stream()); |
+ |
+ StreamRequestWaiter waiter2; |
+ scoped_ptr<HttpStreamRequest> request2( |
+ session->websocket_stream_factory()->RequestWebSocketStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter2, |
+ &factory, |
+ BoundNetLog())); |
+ waiter2.WaitForStream(); |
+ EXPECT_TRUE(waiter2.stream_done()); |
+ ASSERT_TRUE(NULL != waiter2.websocket_stream()); |
+ EXPECT_EQ(MockWebSocketStream::kStreamTypeSpdy, |
+ waiter2.websocket_stream()->type()); |
+ EXPECT_TRUE(NULL == waiter2.stream()); |
+ EXPECT_NE(waiter2.websocket_stream(), waiter1.websocket_stream()); |
+ EXPECT_EQ(static_cast<WebSocketSpdyStream*>(waiter2.websocket_stream())-> |
+ spdy_session(), |
+ static_cast<WebSocketSpdyStream*>(waiter1.websocket_stream())-> |
+ spdy_session()); |
+ |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_TRUE(waiter1.used_proxy_info().is_direct()); |
+} |
+ |
+TEST(HttpStreamFactoryTest, OrphanedWebSocketStream) { |
+ UseAlternateProtocolsScopedSetter use_alternate_protocols(true); |
+ SpdySessionDependencies session_deps(kProtoSPDY3, |
+ ProxyService::CreateDirect()); |
+ |
+ MockRead mock_read(ASYNC, OK); |
+ StaticSocketDataProvider socket_data(&mock_read, 1, NULL, 0); |
+ socket_data.set_connect_data(MockConnect(ASYNC, OK)); |
+ session_deps.socket_factory->AddSocketDataProvider(&socket_data); |
+ |
+ MockRead mock_read2(ASYNC, OK); |
+ StaticSocketDataProvider socket_data2(&mock_read2, 1, NULL, 0); |
+ socket_data2.set_connect_data(MockConnect(ASYNC, ERR_IO_PENDING)); |
+ session_deps.socket_factory->AddSocketDataProvider(&socket_data2); |
+ |
+ SSLSocketDataProvider ssl_socket_data(ASYNC, OK); |
+ ssl_socket_data.SetNextProto(kProtoSPDY3); |
+ session_deps.socket_factory->AddSSLSocketDataProvider(&ssl_socket_data); |
+ |
+ scoped_refptr<HttpNetworkSession> |
+ session(SpdySessionDependencies::SpdyCreateSession(&session_deps)); |
+ |
+ // Now request a stream. |
+ HttpRequestInfo request_info; |
+ request_info.method = "GET"; |
+ request_info.url = GURL("ws://www.google.com:8888"); |
+ request_info.load_flags = 0; |
+ |
+ session->http_server_properties()->SetAlternateProtocol( |
+ HostPortPair("www.google.com", 8888), |
+ 9999, |
+ NPN_SPDY_3); |
+ |
+ SSLConfig ssl_config; |
+ StreamRequestWaiter waiter; |
+ WebSocketStreamFactory factory; |
+ scoped_ptr<HttpStreamRequest> request( |
+ session->websocket_stream_factory()->RequestWebSocketStream( |
+ request_info, |
+ DEFAULT_PRIORITY, |
+ ssl_config, |
+ ssl_config, |
+ &waiter, |
+ &factory, |
+ BoundNetLog())); |
+ waiter.WaitForStream(); |
+ EXPECT_TRUE(waiter.stream_done()); |
+ EXPECT_TRUE(NULL == waiter.stream()); |
+ ASSERT_TRUE(NULL != waiter.websocket_stream()); |
+ EXPECT_EQ(MockWebSocketStream::kStreamTypeSpdy, |
+ waiter.websocket_stream()->type()); |
+ |
+ // Make sure that there was an alternative connection |
+ // which consumes extra connections. |
+ EXPECT_EQ(2, GetSocketPoolGroupCount( |
+ session->GetTransportSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_EQ(1, GetSocketPoolGroupCount( |
+ session->GetSSLSocketPool(HttpNetworkSession::NORMAL_SOCKET_POOL))); |
+ EXPECT_TRUE(waiter.used_proxy_info().is_direct()); |
+ |
+ // Make sure there is no orphaned job. it is already canceled. |
+ ASSERT_EQ(0u, static_cast<HttpStreamFactoryImpl*>( |
+ session->websocket_stream_factory())->num_orphaned_jobs()); |
+} |
+ |
} // namespace |
} // namespace net |