Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(720)

Side by Side Diff: chrome/test/chromedriver/net/websocket_unittest.cc

Issue 11316115: [chromedriver] Write websocket client and sync websocket client. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: . Created 8 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include <string>
6 #include <vector>
7
8 #include "base/bind.h"
9 #include "base/compiler_specific.h"
10 #include "base/location.h"
11 #include "base/memory/scoped_ptr.h"
12 #include "base/message_loop.h"
13 #include "base/message_loop_proxy.h"
14 #include "base/run_loop.h"
15 #include "base/single_thread_task_runner.h"
16 #include "base/stringprintf.h"
17 #include "base/time.h"
18 #include "chrome/test/chromedriver/net/websocket.h"
19 #include "googleurl/src/gurl.h"
20 #include "net/base/ip_endpoint.h"
21 #include "net/base/net_errors.h"
22 #include "net/base/tcp_listen_socket.h"
23 #include "net/server/http_server.h"
24 #include "net/server/http_server_request_info.h"
25 #include "net/url_request/url_request_context_getter.h"
26 #include "net/url_request/url_request_test_util.h"
27 #include "testing/gtest/include/gtest/gtest.h"
28
29 namespace {
30
31 void OnConnectFinished(int* save_error, int error) {
32 MessageLoop::current()->Quit();
33 *save_error = error;
34 }
35
36 class Listener : public WebSocketListener {
37 public:
38 explicit Listener(const std::vector<std::string>& messages)
39 : messages_(messages) {}
40
41 virtual ~Listener() {
42 EXPECT_TRUE(messages_.empty());
43 }
44
45 virtual void OnMessageReceived(const std::string& message) OVERRIDE {
46 ASSERT_TRUE(messages_.size());
47 EXPECT_EQ(messages_[0], message);
48 messages_.erase(messages_.begin());
49 if (messages_.empty())
50 MessageLoop::current()->Quit();
51 }
52
53 virtual void OnClose() OVERRIDE {
54 EXPECT_TRUE(false);
55 }
56
57 private:
58 std::vector<std::string> messages_;
59 };
60
61 class CloseListener : public WebSocketListener {
62 public:
63 explicit CloseListener(bool expect_close) : expect_close_(expect_close) {}
64
65 virtual ~CloseListener() {
66 EXPECT_FALSE(expect_close_);
67 }
68
69 virtual void OnMessageReceived(const std::string& message) OVERRIDE {}
70
71 virtual void OnClose() OVERRIDE {
72 EXPECT_TRUE(expect_close_);
73 if (expect_close_)
74 MessageLoop::current()->Quit();
75 expect_close_ = false;
76 }
77
78 private:
79 bool expect_close_;
80 };
81
82 class WebSocketTest : public testing::Test,
83 public net::HttpServer::Delegate {
84 public:
85 enum WebSocketRequestResponse {
86 kAccept = 0,
87 kNotFound,
88 kClose
89 };
90
91 WebSocketTest()
92 : ALLOW_THIS_IN_INITIALIZER_LIST(server_(CreateServer())),
93 context_getter_(
94 new net::TestURLRequestContextGetter(loop_.message_loop_proxy())),
95 ws_request_response_(kAccept),
96 close_on_message_(false),
97 quit_on_close_(false) {
98 net::IPEndPoint address;
99 CHECK_EQ(net::OK, server_->GetLocalAddress(&address));
100 server_url_ = GURL(base::StringPrintf("ws://127.0.0.1:%d", address.port()));
101 }
102
103 // Overridden from net::HttpServer::Delegate:
104 virtual void OnHttpRequest(int connection_id,
105 const net::HttpServerRequestInfo& info) {}
106
107 virtual void OnWebSocketRequest(int connection_id,
108 const net::HttpServerRequestInfo& info) {
109 switch (ws_request_response_) {
110 case kAccept:
111 server_->AcceptWebSocket(connection_id, info);
112 break;
113 case kNotFound:
114 server_->Send404(connection_id);
115 break;
116 case kClose:
117 // net::HttpServer doesn't allow us to close connection during callback.
118 MessageLoop::current()->PostTask(
119 FROM_HERE,
120 base::Bind(&net::HttpServer::Close, server_, connection_id));
121 break;
122 }
123 }
124
125 virtual void OnWebSocketMessage(int connection_id,
126 const std::string& data) {
127 if (close_on_message_) {
128 // net::HttpServer doesn't allow us to close connection during callback.
129 MessageLoop::current()->PostTask(
130 FROM_HERE,
131 base::Bind(&net::HttpServer::Close, server_, connection_id));
132 } else {
133 server_->SendOverWebSocket(connection_id, data);
134 }
135 }
136
137 virtual void OnClose(int connection_id) {
138 if (quit_on_close_)
139 MessageLoop::current()->Quit();
140 }
141
142 protected:
143 net::HttpServer* CreateServer() {
144 net::TCPListenSocketFactory factory("127.0.0.1", 0);
145 return new net::HttpServer(factory, this);
146 }
147
148 scoped_ptr<WebSocket> CreateWebSocket(const GURL& url,
149 WebSocketListener* listener) {
150 int error;
151 scoped_ptr<WebSocket> sock(new WebSocket(
152 context_getter_, url, listener));
153 sock->Connect(base::Bind(&OnConnectFinished, &error));
154 loop_.PostDelayedTask(
155 FROM_HERE, MessageLoop::QuitWhenIdleClosure(),
156 base::TimeDelta::FromSeconds(10));
157 base::RunLoop().Run();
158 if (error == net::OK)
159 return sock.Pass();
160 return scoped_ptr<WebSocket>();
161 }
162
163 scoped_ptr<WebSocket> CreateConnectedWebSocket(WebSocketListener* listener) {
164 return CreateWebSocket(server_url_, listener);
165 }
166
167 void ReadSend(const std::vector<std::string>& messages) {
168 Listener listener(messages);
169 scoped_ptr<WebSocket> sock(CreateConnectedWebSocket(&listener));
170 ASSERT_TRUE(sock);
171 for (size_t i = 0; i < messages.size(); ++i) {
172 ASSERT_TRUE(sock->Send(messages[i]));
173 }
174 base::RunLoop run_loop;
175 loop_.PostDelayedTask(
176 FROM_HERE, run_loop.QuitClosure(),
177 base::TimeDelta::FromSeconds(10));
178 run_loop.Run();
179 }
180
181 MessageLoopForIO loop_;
182 scoped_refptr<net::HttpServer> server_;
183 scoped_refptr<net::URLRequestContextGetter> context_getter_;
184 GURL server_url_;
185 WebSocketRequestResponse ws_request_response_;
186 bool close_on_message_;
187 bool quit_on_close_;
188 };
189
190 } // namespace
191
192 TEST_F(WebSocketTest, CreateDestroy) {
193 CloseListener listener(false);
194 WebSocket sock(context_getter_, GURL("http://ok"), &listener);
195 }
196
197 TEST_F(WebSocketTest, Connect) {
198 CloseListener listener(false);
199 ASSERT_TRUE(CreateWebSocket(server_url_, &listener));
200 quit_on_close_ = true;
201 base::RunLoop run_loop;
202 loop_.PostDelayedTask(
203 FROM_HERE, run_loop.QuitClosure(),
204 base::TimeDelta::FromSeconds(10));
205 run_loop.Run();
206 }
207
208 TEST_F(WebSocketTest, ConnectNoServer) {
209 CloseListener listener(false);
210 ASSERT_FALSE(CreateWebSocket(GURL("ws://127.0.0.1:33333"), NULL));
211 }
212
213 TEST_F(WebSocketTest, Connect404) {
214 ws_request_response_ = kNotFound;
215 CloseListener listener(false);
216 ASSERT_FALSE(CreateWebSocket(server_url_, NULL));
217 quit_on_close_ = true;
218 base::RunLoop run_loop;
219 loop_.PostDelayedTask(
220 FROM_HERE, run_loop.QuitClosure(),
221 base::TimeDelta::FromSeconds(10));
222 run_loop.Run();
223 }
224
225 TEST_F(WebSocketTest, ConnectServerClosesConn) {
226 ws_request_response_ = kClose;
227 CloseListener listener(false);
228 ASSERT_FALSE(CreateWebSocket(server_url_, &listener));
229 }
230
231 TEST_F(WebSocketTest, CloseOnRead) {
232 close_on_message_ = true;
233 CloseListener listener(true);
234 scoped_ptr<WebSocket> sock(CreateConnectedWebSocket(&listener));
235 ASSERT_TRUE(sock);
236 ASSERT_TRUE(sock->Send("hi"));
237 base::RunLoop run_loop;
238 loop_.PostDelayedTask(
239 FROM_HERE, run_loop.QuitClosure(),
240 base::TimeDelta::FromSeconds(10));
241 run_loop.Run();
242 }
243
244 TEST_F(WebSocketTest, CloseOnSend) {
245 CloseListener listener(true);
246 scoped_ptr<WebSocket> sock(CreateConnectedWebSocket(&listener));
247 ASSERT_TRUE(sock);
248 server_ = NULL;
249 loop_.PostTask(
250 FROM_HERE,
251 base::Bind(base::IgnoreResult(&WebSocket::Send),
252 base::Unretained(sock.get()), "hi"));
253 base::RunLoop run_loop;
254 loop_.PostDelayedTask(
255 FROM_HERE, run_loop.QuitClosure(),
256 base::TimeDelta::FromSeconds(10));
257 run_loop.Run();
258 }
259
260 TEST_F(WebSocketTest, ReadSend) {
261 std::vector<std::string> messages;
262 messages.push_back("hello");
263 ReadSend(messages);
264 }
265
266 TEST_F(WebSocketTest, ReadSendLarge) {
267 std::vector<std::string> messages;
268 // Sends/reads 200kb. For some reason pushing this above 240kb on my
269 // machine results in receiving no data back from the http server.
270 messages.push_back(std::string(200 << 10, 'a'));
271 ReadSend(messages);
272 }
273
274 TEST_F(WebSocketTest, ReadSendMultiple) {
275 std::vector<std::string> messages;
276 messages.push_back("1");
277 messages.push_back("2");
278 messages.push_back("3");
279 ReadSend(messages);
280 }
OLDNEW
« chrome/test/chromedriver/net/websocket.cc ('K') | « chrome/test/chromedriver/net/websocket.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698