• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (c) 2011 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/memory/scoped_ptr.h"
9 #include "net/websockets/websocket_handshake_draft75.h"
10 #include "testing/gtest/include/gtest/gtest.h"
11 #include "testing/gmock/include/gmock/gmock.h"
12 #include "testing/platform_test.h"
13 
14 namespace net {
15 
TEST(WebSocketHandshakeDraft75Test,Connect)16 TEST(WebSocketHandshakeDraft75Test, Connect) {
17   const std::string kExpectedClientHandshakeMessage =
18       "GET /demo HTTP/1.1\r\n"
19       "Upgrade: WebSocket\r\n"
20       "Connection: Upgrade\r\n"
21       "Host: example.com\r\n"
22       "Origin: http://example.com\r\n"
23       "WebSocket-Protocol: sample\r\n"
24       "\r\n";
25 
26   scoped_ptr<WebSocketHandshakeDraft75> handshake(
27       new WebSocketHandshakeDraft75(GURL("ws://example.com/demo"),
28                                     "http://example.com",
29                                     "ws://example.com/demo",
30                                     "sample"));
31   EXPECT_EQ(WebSocketHandshake::MODE_INCOMPLETE, handshake->mode());
32   EXPECT_EQ(kExpectedClientHandshakeMessage,
33             handshake->CreateClientHandshakeMessage());
34 
35   const char kResponse[] = "HTTP/1.1 101 Web Socket Protocol Handshake\r\n"
36       "Upgrade: WebSocket\r\n"
37       "Connection: Upgrade\r\n"
38       "WebSocket-Origin: http://example.com\r\n"
39       "WebSocket-Location: ws://example.com/demo\r\n"
40       "WebSocket-Protocol: sample\r\n"
41       "\r\n";
42 
43   EXPECT_EQ(WebSocketHandshake::MODE_INCOMPLETE, handshake->mode());
44   // too short
45   EXPECT_EQ(-1, handshake->ReadServerHandshake(kResponse, 16));
46   EXPECT_EQ(WebSocketHandshake::MODE_INCOMPLETE, handshake->mode());
47   // only status line
48   EXPECT_EQ(-1, handshake->ReadServerHandshake(
49       kResponse,
50       WebSocketHandshakeDraft75::kServerHandshakeHeaderLength));
51   EXPECT_EQ(WebSocketHandshake::MODE_NORMAL, handshake->mode());
52   // by upgrade header
53   EXPECT_EQ(-1, handshake->ReadServerHandshake(
54       kResponse,
55       WebSocketHandshakeDraft75::kServerHandshakeHeaderLength +
56       WebSocketHandshakeDraft75::kUpgradeHeaderLength));
57   EXPECT_EQ(WebSocketHandshake::MODE_NORMAL, handshake->mode());
58   // by connection header
59   EXPECT_EQ(-1, handshake->ReadServerHandshake(
60       kResponse,
61       WebSocketHandshakeDraft75::kServerHandshakeHeaderLength +
62       WebSocketHandshakeDraft75::kUpgradeHeaderLength +
63       WebSocketHandshakeDraft75::kConnectionHeaderLength));
64   EXPECT_EQ(WebSocketHandshake::MODE_NORMAL, handshake->mode());
65 
66   EXPECT_EQ(-1, handshake->ReadServerHandshake(
67       kResponse, sizeof(kResponse) - 2));
68   EXPECT_EQ(WebSocketHandshake::MODE_NORMAL, handshake->mode());
69 
70   int handshake_length = strlen(kResponse);
71   EXPECT_EQ(handshake_length, handshake->ReadServerHandshake(
72       kResponse, sizeof(kResponse) - 1));  // -1 for terminating \0
73   EXPECT_EQ(WebSocketHandshake::MODE_CONNECTED, handshake->mode());
74 }
75 
TEST(WebSocketHandshakeDraft75Test,ServerSentData)76 TEST(WebSocketHandshakeDraft75Test, ServerSentData) {
77   const std::string kExpectedClientHandshakeMessage =
78       "GET /demo HTTP/1.1\r\n"
79       "Upgrade: WebSocket\r\n"
80       "Connection: Upgrade\r\n"
81       "Host: example.com\r\n"
82       "Origin: http://example.com\r\n"
83       "WebSocket-Protocol: sample\r\n"
84       "\r\n";
85   scoped_ptr<WebSocketHandshakeDraft75> handshake(
86       new WebSocketHandshakeDraft75(GURL("ws://example.com/demo"),
87                                     "http://example.com",
88                                     "ws://example.com/demo",
89                                     "sample"));
90   EXPECT_EQ(WebSocketHandshake::MODE_INCOMPLETE, handshake->mode());
91   EXPECT_EQ(kExpectedClientHandshakeMessage,
92             handshake->CreateClientHandshakeMessage());
93 
94   const char kResponse[] ="HTTP/1.1 101 Web Socket Protocol Handshake\r\n"
95       "Upgrade: WebSocket\r\n"
96       "Connection: Upgrade\r\n"
97       "WebSocket-Origin: http://example.com\r\n"
98       "WebSocket-Location: ws://example.com/demo\r\n"
99       "WebSocket-Protocol: sample\r\n"
100       "\r\n"
101       "\0Hello\xff";
102 
103   int handshake_length = strlen(kResponse);
104   EXPECT_EQ(handshake_length, handshake->ReadServerHandshake(
105       kResponse, sizeof(kResponse) - 1));  // -1 for terminating \0
106   EXPECT_EQ(WebSocketHandshake::MODE_CONNECTED, handshake->mode());
107 }
108 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_Simple)109 TEST(WebSocketHandshakeDraft75Test, CreateClientHandshakeMessage_Simple) {
110   scoped_ptr<WebSocketHandshakeDraft75> handshake(
111       new WebSocketHandshakeDraft75(GURL("ws://example.com/demo"),
112                                     "http://example.com",
113                                     "ws://example.com/demo",
114                                     "sample"));
115   EXPECT_EQ("GET /demo HTTP/1.1\r\n"
116             "Upgrade: WebSocket\r\n"
117             "Connection: Upgrade\r\n"
118             "Host: example.com\r\n"
119             "Origin: http://example.com\r\n"
120             "WebSocket-Protocol: sample\r\n"
121             "\r\n",
122             handshake->CreateClientHandshakeMessage());
123 }
124 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_PathAndQuery)125 TEST(WebSocketHandshakeDraft75Test, CreateClientHandshakeMessage_PathAndQuery) {
126   scoped_ptr<WebSocketHandshakeDraft75> handshake(
127       new WebSocketHandshakeDraft75(GURL("ws://example.com/Test?q=xxx&p=%20"),
128                                     "http://example.com",
129                                     "ws://example.com/demo",
130                                     "sample"));
131   // Path and query should be preserved as-is.
132   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
133               testing::HasSubstr("GET /Test?q=xxx&p=%20 HTTP/1.1\r\n"));
134 }
135 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_Host)136 TEST(WebSocketHandshakeDraft75Test, CreateClientHandshakeMessage_Host) {
137   scoped_ptr<WebSocketHandshakeDraft75> handshake(
138       new WebSocketHandshakeDraft75(GURL("ws://Example.Com/demo"),
139                                     "http://Example.Com",
140                                     "ws://Example.Com/demo",
141                                     "sample"));
142   // Host should be lowercased
143   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
144               testing::HasSubstr("Host: example.com\r\n"));
145   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
146               testing::HasSubstr("Origin: http://example.com\r\n"));
147 }
148 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_TrimPort80)149 TEST(WebSocketHandshakeDraft75Test, CreateClientHandshakeMessage_TrimPort80) {
150   scoped_ptr<WebSocketHandshakeDraft75> handshake(
151       new WebSocketHandshakeDraft75(GURL("ws://example.com:80/demo"),
152                                     "http://example.com",
153                                     "ws://example.com/demo",
154                                     "sample"));
155   // :80 should be trimmed as it's the default port for ws://.
156   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
157               testing::HasSubstr("Host: example.com\r\n"));
158 }
159 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_TrimPort443)160 TEST(WebSocketHandshakeDraft75Test, CreateClientHandshakeMessage_TrimPort443) {
161   scoped_ptr<WebSocketHandshakeDraft75> handshake(
162       new WebSocketHandshakeDraft75(GURL("wss://example.com:443/demo"),
163                                     "http://example.com",
164                                     "wss://example.com/demo",
165                                     "sample"));
166   // :443 should be trimmed as it's the default port for wss://.
167   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
168               testing::HasSubstr("Host: example.com\r\n"));
169 }
170 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_NonDefaultPortForWs)171 TEST(WebSocketHandshakeDraft75Test,
172      CreateClientHandshakeMessage_NonDefaultPortForWs) {
173   scoped_ptr<WebSocketHandshakeDraft75> handshake(
174       new WebSocketHandshakeDraft75(GURL("ws://example.com:8080/demo"),
175                                     "http://example.com",
176                                     "wss://example.com/demo",
177                                     "sample"));
178   // :8080 should be preserved as it's not the default port for ws://.
179   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
180               testing::HasSubstr("Host: example.com:8080\r\n"));
181 }
182 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_NonDefaultPortForWss)183 TEST(WebSocketHandshakeDraft75Test,
184      CreateClientHandshakeMessage_NonDefaultPortForWss) {
185   scoped_ptr<WebSocketHandshakeDraft75> handshake(
186       new WebSocketHandshakeDraft75(GURL("wss://example.com:4443/demo"),
187                                     "http://example.com",
188                                     "wss://example.com/demo",
189                                     "sample"));
190   // :4443 should be preserved as it's not the default port for wss://.
191   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
192               testing::HasSubstr("Host: example.com:4443\r\n"));
193 }
194 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_WsBut443)195 TEST(WebSocketHandshakeDraft75Test, CreateClientHandshakeMessage_WsBut443) {
196   scoped_ptr<WebSocketHandshakeDraft75> handshake(
197       new WebSocketHandshakeDraft75(GURL("ws://example.com:443/demo"),
198                                     "http://example.com",
199                                     "ws://example.com/demo",
200                                     "sample"));
201   // :443 should be preserved as it's not the default port for ws://.
202   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
203               testing::HasSubstr("Host: example.com:443\r\n"));
204 }
205 
TEST(WebSocketHandshakeDraft75Test,CreateClientHandshakeMessage_WssBut80)206 TEST(WebSocketHandshakeDraft75Test, CreateClientHandshakeMessage_WssBut80) {
207   scoped_ptr<WebSocketHandshakeDraft75> handshake(
208       new WebSocketHandshakeDraft75(GURL("wss://example.com:80/demo"),
209                                     "http://example.com",
210                                     "wss://example.com/demo",
211                                     "sample"));
212   // :80 should be preserved as it's not the default port for wss://.
213   EXPECT_THAT(handshake->CreateClientHandshakeMessage(),
214               testing::HasSubstr("Host: example.com:80\r\n"));
215 }
216 
217 }  // namespace net
218