http_server_unittest.cc 39 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135
  1. // Copyright 2013 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. #include "net/server/http_server.h"
  5. #include <stdint.h>
  6. #include <algorithm>
  7. #include <memory>
  8. #include <unordered_map>
  9. #include <utility>
  10. #include <vector>
  11. #include "base/auto_reset.h"
  12. #include "base/bind.h"
  13. #include "base/callback_helpers.h"
  14. #include "base/check_op.h"
  15. #include "base/compiler_specific.h"
  16. #include "base/cxx17_backports.h"
  17. #include "base/format_macros.h"
  18. #include "base/location.h"
  19. #include "base/memory/ptr_util.h"
  20. #include "base/memory/ref_counted.h"
  21. #include "base/memory/weak_ptr.h"
  22. #include "base/notreached.h"
  23. #include "base/run_loop.h"
  24. #include "base/strings/string_split.h"
  25. #include "base/strings/string_util.h"
  26. #include "base/strings/stringprintf.h"
  27. #include "base/task/single_thread_task_runner.h"
  28. #include "base/test/repeating_test_future.h"
  29. #include "base/threading/thread_task_runner_handle.h"
  30. #include "base/time/time.h"
  31. #include "net/base/address_list.h"
  32. #include "net/base/io_buffer.h"
  33. #include "net/base/ip_endpoint.h"
  34. #include "net/base/net_errors.h"
  35. #include "net/base/test_completion_callback.h"
  36. #include "net/http/http_response_headers.h"
  37. #include "net/http/http_util.h"
  38. #include "net/log/net_log_source.h"
  39. #include "net/log/net_log_with_source.h"
  40. #include "net/server/http_server_request_info.h"
  41. #include "net/socket/tcp_client_socket.h"
  42. #include "net/socket/tcp_server_socket.h"
  43. #include "net/test/gtest_util.h"
  44. #include "net/test/test_with_task_environment.h"
  45. #include "net/traffic_annotation/network_traffic_annotation_test_helper.h"
  46. #include "net/websockets/websocket_frame.h"
  47. #include "testing/gmock/include/gmock/gmock.h"
  48. #include "testing/gtest/include/gtest/gtest.h"
  49. using net::test::IsOk;
  50. namespace net {
  51. namespace {
  52. const int kMaxExpectedResponseLength = 2048;
  53. class TestHttpClient {
  54. public:
  55. TestHttpClient() = default;
  56. int ConnectAndWait(const IPEndPoint& address) {
  57. AddressList addresses(address);
  58. NetLogSource source;
  59. socket_ = std::make_unique<TCPClientSocket>(addresses, nullptr, nullptr,
  60. nullptr, source);
  61. TestCompletionCallback callback;
  62. int rv = socket_->Connect(callback.callback());
  63. return callback.GetResult(rv);
  64. }
  65. void Send(const std::string& data) {
  66. write_buffer_ = base::MakeRefCounted<DrainableIOBuffer>(
  67. base::MakeRefCounted<StringIOBuffer>(data), data.length());
  68. Write();
  69. }
  70. bool Read(std::string* message, int expected_bytes) {
  71. int total_bytes_received = 0;
  72. message->clear();
  73. while (total_bytes_received < expected_bytes) {
  74. TestCompletionCallback callback;
  75. ReadInternal(&callback);
  76. int bytes_received = callback.WaitForResult();
  77. if (bytes_received <= 0)
  78. return false;
  79. total_bytes_received += bytes_received;
  80. message->append(read_buffer_->data(), bytes_received);
  81. }
  82. return true;
  83. }
  84. bool ReadResponse(std::string* message) {
  85. if (!Read(message, 1))
  86. return false;
  87. while (!IsCompleteResponse(*message)) {
  88. std::string chunk;
  89. if (!Read(&chunk, 1))
  90. return false;
  91. message->append(chunk);
  92. }
  93. return true;
  94. }
  95. void ExpectUsedThenDisconnectedWithNoData() {
  96. // Check that the socket was opened...
  97. ASSERT_TRUE(socket_->WasEverUsed());
  98. // ...then closed when the server disconnected. Verify that the socket was
  99. // closed by checking that a Read() fails.
  100. std::string response;
  101. ASSERT_FALSE(Read(&response, 1u));
  102. ASSERT_TRUE(response.empty());
  103. }
  104. TCPClientSocket& socket() { return *socket_; }
  105. private:
  106. void Write() {
  107. int result = socket_->Write(
  108. write_buffer_.get(), write_buffer_->BytesRemaining(),
  109. base::BindOnce(&TestHttpClient::OnWrite, base::Unretained(this)),
  110. TRAFFIC_ANNOTATION_FOR_TESTS);
  111. if (result != ERR_IO_PENDING)
  112. OnWrite(result);
  113. }
  114. void OnWrite(int result) {
  115. ASSERT_GT(result, 0);
  116. write_buffer_->DidConsume(result);
  117. if (write_buffer_->BytesRemaining())
  118. Write();
  119. }
  120. void ReadInternal(TestCompletionCallback* callback) {
  121. read_buffer_ =
  122. base::MakeRefCounted<IOBufferWithSize>(kMaxExpectedResponseLength);
  123. int result = socket_->Read(read_buffer_.get(), kMaxExpectedResponseLength,
  124. callback->callback());
  125. if (result != ERR_IO_PENDING)
  126. callback->callback().Run(result);
  127. }
  128. bool IsCompleteResponse(const std::string& response) {
  129. // Check end of headers first.
  130. size_t end_of_headers =
  131. HttpUtil::LocateEndOfHeaders(response.data(), response.size());
  132. if (end_of_headers == std::string::npos)
  133. return false;
  134. // Return true if response has data equal to or more than content length.
  135. int64_t body_size = static_cast<int64_t>(response.size()) - end_of_headers;
  136. DCHECK_LE(0, body_size);
  137. auto headers =
  138. base::MakeRefCounted<HttpResponseHeaders>(HttpUtil::AssembleRawHeaders(
  139. base::StringPiece(response.data(), end_of_headers)));
  140. return body_size >= headers->GetContentLength();
  141. }
  142. scoped_refptr<IOBufferWithSize> read_buffer_;
  143. scoped_refptr<DrainableIOBuffer> write_buffer_;
  144. std::unique_ptr<TCPClientSocket> socket_;
  145. };
  146. struct ReceivedRequest {
  147. HttpServerRequestInfo info;
  148. int connection_id;
  149. };
  150. } // namespace
  151. class HttpServerTest : public TestWithTaskEnvironment,
  152. public HttpServer::Delegate {
  153. public:
  154. HttpServerTest() = default;
  155. void SetUp() override {
  156. auto server_socket =
  157. std::make_unique<TCPServerSocket>(nullptr, NetLogSource());
  158. server_socket->ListenWithAddressAndPort("127.0.0.1", 0, 1);
  159. server_ = std::make_unique<HttpServer>(std::move(server_socket), this);
  160. ASSERT_THAT(server_->GetLocalAddress(&server_address_), IsOk());
  161. }
  162. void TearDown() override {
  163. // Run the event loop some to make sure that the memory handed over to
  164. // DeleteSoon gets fully freed.
  165. base::RunLoop().RunUntilIdle();
  166. }
  167. void OnConnect(int connection_id) override {
  168. DCHECK(connection_map_.find(connection_id) == connection_map_.end());
  169. connection_map_[connection_id] = true;
  170. // This is set in CreateConnection(), which must be invoked once for every
  171. // expected connection.
  172. quit_on_create_loop_->Quit();
  173. }
  174. void OnHttpRequest(int connection_id,
  175. const HttpServerRequestInfo& info) override {
  176. received_requests_.AddValue({.info = info, .connection_id = connection_id});
  177. }
  178. void OnWebSocketRequest(int connection_id,
  179. const HttpServerRequestInfo& info) override {
  180. NOTREACHED();
  181. }
  182. void OnWebSocketMessage(int connection_id, std::string data) override {
  183. NOTREACHED();
  184. }
  185. void OnClose(int connection_id) override {
  186. DCHECK(connection_map_.find(connection_id) != connection_map_.end());
  187. connection_map_[connection_id] = false;
  188. if (connection_id == quit_on_close_connection_)
  189. std::move(run_loop_quit_func_).Run();
  190. }
  191. ReceivedRequest WaitForRequest() { return received_requests_.Take(); }
  192. bool HasRequest() const { return !received_requests_.IsEmpty(); }
  193. // Connections should only be created using this method, which waits until
  194. // both the server and the client have received the connected socket.
  195. void CreateConnection(TestHttpClient* client) {
  196. ASSERT_FALSE(quit_on_create_loop_);
  197. quit_on_create_loop_ = std::make_unique<base::RunLoop>();
  198. EXPECT_THAT(client->ConnectAndWait(server_address_), IsOk());
  199. quit_on_create_loop_->Run();
  200. quit_on_create_loop_.reset();
  201. }
  202. void RunUntilConnectionIdClosed(int connection_id) {
  203. quit_on_close_connection_ = connection_id;
  204. auto iter = connection_map_.find(connection_id);
  205. if (iter != connection_map_.end() && !iter->second) {
  206. // Already disconnected.
  207. return;
  208. }
  209. base::RunLoop run_loop;
  210. base::AutoReset<base::OnceClosure> run_loop_quit_func(
  211. &run_loop_quit_func_, run_loop.QuitClosure());
  212. run_loop.Run();
  213. iter = connection_map_.find(connection_id);
  214. ASSERT_TRUE(iter != connection_map_.end());
  215. ASSERT_FALSE(iter->second);
  216. }
  217. void HandleAcceptResult(std::unique_ptr<StreamSocket> socket) {
  218. ASSERT_FALSE(quit_on_create_loop_);
  219. quit_on_create_loop_ = std::make_unique<base::RunLoop>();
  220. server_->accepted_socket_ = std::move(socket);
  221. server_->HandleAcceptResult(OK);
  222. quit_on_create_loop_->Run();
  223. quit_on_create_loop_.reset();
  224. }
  225. std::unordered_map<int, bool>& connection_map() { return connection_map_; }
  226. protected:
  227. std::unique_ptr<HttpServer> server_;
  228. IPEndPoint server_address_;
  229. base::OnceClosure run_loop_quit_func_;
  230. std::unordered_map<int /* connection_id */, bool /* connected */>
  231. connection_map_;
  232. private:
  233. base::test::RepeatingTestFuture<ReceivedRequest> received_requests_;
  234. std::unique_ptr<base::RunLoop> quit_on_create_loop_;
  235. int quit_on_close_connection_ = -1;
  236. };
  237. namespace {
  238. class WebSocketTest : public HttpServerTest {
  239. void OnHttpRequest(int connection_id,
  240. const HttpServerRequestInfo& info) override {
  241. NOTREACHED();
  242. }
  243. void OnWebSocketRequest(int connection_id,
  244. const HttpServerRequestInfo& info) override {
  245. HttpServerTest::OnHttpRequest(connection_id, info);
  246. }
  247. void OnWebSocketMessage(int connection_id, std::string data) override {}
  248. };
  249. class WebSocketAcceptingTest : public WebSocketTest {
  250. public:
  251. void OnWebSocketRequest(int connection_id,
  252. const HttpServerRequestInfo& info) override {
  253. HttpServerTest::OnHttpRequest(connection_id, info);
  254. server_->AcceptWebSocket(connection_id, info, TRAFFIC_ANNOTATION_FOR_TESTS);
  255. }
  256. void OnWebSocketMessage(int connection_id, std::string data) override {
  257. messages_.AddValue(data);
  258. }
  259. std::string GetMessage() { return messages_.Take(); }
  260. private:
  261. base::test::RepeatingTestFuture<std::string> messages_;
  262. };
  263. std::string EncodeFrame(std::string message,
  264. WebSocketFrameHeader::OpCodeEnum op_code,
  265. bool mask,
  266. bool finish) {
  267. WebSocketFrameHeader header(op_code);
  268. header.final = finish;
  269. header.masked = mask;
  270. header.payload_length = message.size();
  271. const int header_size = GetWebSocketFrameHeaderSize(header);
  272. std::string frame_header;
  273. frame_header.resize(header_size);
  274. if (mask) {
  275. WebSocketMaskingKey masking_key = GenerateWebSocketMaskingKey();
  276. WriteWebSocketFrameHeader(header, &masking_key, &frame_header[0],
  277. header_size);
  278. MaskWebSocketFramePayload(masking_key, 0, &message[0], message.size());
  279. } else {
  280. WriteWebSocketFrameHeader(header, nullptr, &frame_header[0], header_size);
  281. }
  282. return frame_header + message;
  283. }
  284. TEST_F(HttpServerTest, Request) {
  285. TestHttpClient client;
  286. CreateConnection(&client);
  287. client.Send("GET /test HTTP/1.1\r\n\r\n");
  288. ReceivedRequest request = WaitForRequest();
  289. ASSERT_EQ("GET", request.info.method);
  290. ASSERT_EQ("/test", request.info.path);
  291. ASSERT_EQ("", request.info.data);
  292. ASSERT_EQ(0u, request.info.headers.size());
  293. ASSERT_TRUE(base::StartsWith(request.info.peer.ToString(), "127.0.0.1",
  294. base::CompareCase::SENSITIVE));
  295. }
  296. TEST_F(HttpServerTest, RequestBrokenTermination) {
  297. TestHttpClient client;
  298. CreateConnection(&client);
  299. client.Send("GET /test HTTP/1.1\r\n\r)");
  300. RunUntilConnectionIdClosed(1);
  301. EXPECT_FALSE(HasRequest());
  302. client.ExpectUsedThenDisconnectedWithNoData();
  303. }
  304. TEST_F(HttpServerTest, RequestWithHeaders) {
  305. TestHttpClient client;
  306. CreateConnection(&client);
  307. const char* const kHeaders[][3] = {
  308. {"Header", ": ", "1"},
  309. {"HeaderWithNoWhitespace", ":", "1"},
  310. {"HeaderWithWhitespace", " : \t ", "1 1 1 \t "},
  311. {"HeaderWithColon", ": ", "1:1"},
  312. {"EmptyHeader", ":", ""},
  313. {"EmptyHeaderWithWhitespace", ": \t ", ""},
  314. {"HeaderWithNonASCII", ": ", "\xf7"},
  315. };
  316. std::string headers;
  317. for (const auto& header : kHeaders) {
  318. headers += std::string(header[0]) + header[1] + header[2] + "\r\n";
  319. }
  320. client.Send("GET /test HTTP/1.1\r\n" + headers + "\r\n");
  321. auto request = WaitForRequest();
  322. ASSERT_EQ("", request.info.data);
  323. for (const auto& header : kHeaders) {
  324. std::string field = base::ToLowerASCII(std::string(header[0]));
  325. std::string value = header[2];
  326. ASSERT_EQ(1u, request.info.headers.count(field)) << field;
  327. ASSERT_EQ(value, request.info.headers[field]) << header[0];
  328. }
  329. }
  330. TEST_F(HttpServerTest, RequestWithDuplicateHeaders) {
  331. TestHttpClient client;
  332. CreateConnection(&client);
  333. const char* const kHeaders[][3] = {
  334. // clang-format off
  335. {"FirstHeader", ": ", "1"},
  336. {"DuplicateHeader", ": ", "2"},
  337. {"MiddleHeader", ": ", "3"},
  338. {"DuplicateHeader", ": ", "4"},
  339. {"LastHeader", ": ", "5"},
  340. // clang-format on
  341. };
  342. std::string headers;
  343. for (const auto& header : kHeaders) {
  344. headers += std::string(header[0]) + header[1] + header[2] + "\r\n";
  345. }
  346. client.Send("GET /test HTTP/1.1\r\n" + headers + "\r\n");
  347. auto request = WaitForRequest();
  348. ASSERT_EQ("", request.info.data);
  349. for (const auto& header : kHeaders) {
  350. std::string field = base::ToLowerASCII(std::string(header[0]));
  351. std::string value = (field == "duplicateheader") ? "2,4" : header[2];
  352. ASSERT_EQ(1u, request.info.headers.count(field)) << field;
  353. ASSERT_EQ(value, request.info.headers[field]) << header[0];
  354. }
  355. }
  356. TEST_F(HttpServerTest, HasHeaderValueTest) {
  357. TestHttpClient client;
  358. CreateConnection(&client);
  359. const char* const kHeaders[] = {
  360. "Header: Abcd",
  361. "HeaderWithNoWhitespace:E",
  362. "HeaderWithWhitespace : \t f \t ",
  363. "DuplicateHeader: g",
  364. "HeaderWithComma: h, i ,j",
  365. "DuplicateHeader: k",
  366. "EmptyHeader:",
  367. "EmptyHeaderWithWhitespace: \t ",
  368. "HeaderWithNonASCII: \xf7",
  369. };
  370. std::string headers;
  371. for (const char* header : kHeaders) {
  372. headers += std::string(header) + "\r\n";
  373. }
  374. client.Send("GET /test HTTP/1.1\r\n" + headers + "\r\n");
  375. auto request = WaitForRequest();
  376. ASSERT_EQ("", request.info.data);
  377. ASSERT_TRUE(request.info.HasHeaderValue("header", "abcd"));
  378. ASSERT_FALSE(request.info.HasHeaderValue("header", "bc"));
  379. ASSERT_TRUE(request.info.HasHeaderValue("headerwithnowhitespace", "e"));
  380. ASSERT_TRUE(request.info.HasHeaderValue("headerwithwhitespace", "f"));
  381. ASSERT_TRUE(request.info.HasHeaderValue("duplicateheader", "g"));
  382. ASSERT_TRUE(request.info.HasHeaderValue("headerwithcomma", "h"));
  383. ASSERT_TRUE(request.info.HasHeaderValue("headerwithcomma", "i"));
  384. ASSERT_TRUE(request.info.HasHeaderValue("headerwithcomma", "j"));
  385. ASSERT_TRUE(request.info.HasHeaderValue("duplicateheader", "k"));
  386. ASSERT_FALSE(request.info.HasHeaderValue("emptyheader", "x"));
  387. ASSERT_FALSE(request.info.HasHeaderValue("emptyheaderwithwhitespace", "x"));
  388. ASSERT_TRUE(request.info.HasHeaderValue("headerwithnonascii", "\xf7"));
  389. }
  390. TEST_F(HttpServerTest, RequestWithBody) {
  391. TestHttpClient client;
  392. CreateConnection(&client);
  393. std::string body = "a" + std::string(1 << 10, 'b') + "c";
  394. client.Send(
  395. base::StringPrintf("GET /test HTTP/1.1\r\n"
  396. "SomeHeader: 1\r\n"
  397. "Content-Length: %" PRIuS "\r\n\r\n%s",
  398. body.length(), body.c_str()));
  399. auto request = WaitForRequest();
  400. ASSERT_EQ(2u, request.info.headers.size());
  401. ASSERT_EQ(body.length(), request.info.data.length());
  402. ASSERT_EQ('a', body[0]);
  403. ASSERT_EQ('c', *body.rbegin());
  404. }
  405. // Tests that |HttpServer::HandleReadResult| will ignore Upgrade header if value
  406. // is not WebSocket.
  407. TEST_F(HttpServerTest, UpgradeIgnored) {
  408. TestHttpClient client;
  409. CreateConnection(&client);
  410. client.Send(
  411. "GET /test HTTP/1.1\r\n"
  412. "Upgrade: h2c\r\n"
  413. "Connection: SomethingElse, Upgrade\r\n"
  414. "\r\n");
  415. WaitForRequest();
  416. }
  417. TEST_F(WebSocketTest, RequestWebSocket) {
  418. TestHttpClient client;
  419. CreateConnection(&client);
  420. client.Send(
  421. "GET /test HTTP/1.1\r\n"
  422. "Upgrade: WebSocket\r\n"
  423. "Connection: SomethingElse, Upgrade\r\n"
  424. "Sec-WebSocket-Version: 8\r\n"
  425. "Sec-WebSocket-Key: key\r\n"
  426. "\r\n");
  427. WaitForRequest();
  428. }
  429. TEST_F(WebSocketTest, RequestWebSocketTrailingJunk) {
  430. TestHttpClient client;
  431. CreateConnection(&client);
  432. client.Send(
  433. "GET /test HTTP/1.1\r\n"
  434. "Upgrade: WebSocket\r\n"
  435. "Connection: SomethingElse, Upgrade\r\n"
  436. "Sec-WebSocket-Version: 8\r\n"
  437. "Sec-WebSocket-Key: key\r\n"
  438. "\r\nHello? Anyone");
  439. RunUntilConnectionIdClosed(1);
  440. client.ExpectUsedThenDisconnectedWithNoData();
  441. }
  442. TEST_F(WebSocketAcceptingTest, SendPingFrameWithNoMessage) {
  443. TestHttpClient client;
  444. CreateConnection(&client);
  445. std::string response;
  446. client.Send(
  447. "GET /test HTTP/1.1\r\n"
  448. "Upgrade: WebSocket\r\n"
  449. "Connection: SomethingElse, Upgrade\r\n"
  450. "Sec-WebSocket-Version: 8\r\n"
  451. "Sec-WebSocket-Key: key\r\n\r\n");
  452. WaitForRequest();
  453. ASSERT_TRUE(client.ReadResponse(&response));
  454. const std::string message = "";
  455. const std::string ping_frame =
  456. EncodeFrame(message, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  457. /* mask= */ true, /* finish= */ true);
  458. const std::string pong_frame =
  459. EncodeFrame(message, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  460. /* mask= */ false, /* finish= */ true);
  461. client.Send(ping_frame);
  462. ASSERT_TRUE(client.Read(&response, pong_frame.length()));
  463. EXPECT_EQ(response, pong_frame);
  464. }
  465. TEST_F(WebSocketAcceptingTest, SendPingFrameWithMessage) {
  466. TestHttpClient client;
  467. CreateConnection(&client);
  468. std::string response;
  469. client.Send(
  470. "GET /test HTTP/1.1\r\n"
  471. "Upgrade: WebSocket\r\n"
  472. "Connection: SomethingElse, Upgrade\r\n"
  473. "Sec-WebSocket-Version: 8\r\n"
  474. "Sec-WebSocket-Key: key\r\n\r\n");
  475. WaitForRequest();
  476. ASSERT_TRUE(client.ReadResponse(&response));
  477. const std::string message = "hello";
  478. const std::string ping_frame =
  479. EncodeFrame(message, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  480. /* mask= */ true, /* finish= */ true);
  481. const std::string pong_frame =
  482. EncodeFrame(message, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  483. /* mask= */ false, /* finish= */ true);
  484. client.Send(ping_frame);
  485. ASSERT_TRUE(client.Read(&response, pong_frame.length()));
  486. EXPECT_EQ(response, pong_frame);
  487. }
  488. TEST_F(WebSocketAcceptingTest, SendPongFrame) {
  489. TestHttpClient client;
  490. CreateConnection(&client);
  491. std::string response;
  492. client.Send(
  493. "GET /test HTTP/1.1\r\n"
  494. "Upgrade: WebSocket\r\n"
  495. "Connection: SomethingElse, Upgrade\r\n"
  496. "Sec-WebSocket-Version: 8\r\n"
  497. "Sec-WebSocket-Key: key\r\n\r\n");
  498. WaitForRequest();
  499. ASSERT_TRUE(client.ReadResponse(&response));
  500. const std::string ping_frame = EncodeFrame(
  501. /* message= */ "", WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  502. /* mask= */ true, /* finish= */ true);
  503. const std::string pong_frame_send = EncodeFrame(
  504. /* message= */ "", WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  505. /* mask= */ true, /* finish= */ true);
  506. const std::string pong_frame_receive = EncodeFrame(
  507. /* message= */ "", WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  508. /* mask= */ false, /* finish= */ true);
  509. client.Send(pong_frame_send);
  510. client.Send(ping_frame);
  511. ASSERT_TRUE(client.Read(&response, pong_frame_receive.length()));
  512. EXPECT_EQ(response, pong_frame_receive);
  513. }
  514. TEST_F(WebSocketAcceptingTest, SendLongTextFrame) {
  515. TestHttpClient client;
  516. CreateConnection(&client);
  517. std::string response;
  518. client.Send(
  519. "GET /test HTTP/1.1\r\n"
  520. "Upgrade: WebSocket\r\n"
  521. "Connection: SomethingElse, Upgrade\r\n"
  522. "Sec-WebSocket-Version: 8\r\n"
  523. "Sec-WebSocket-Key: key\r\n\r\n");
  524. WaitForRequest();
  525. ASSERT_TRUE(client.ReadResponse(&response));
  526. constexpr int kFrameSize = 100000;
  527. const std::string text_frame(kFrameSize, 'a');
  528. const std::string continuation_frame(kFrameSize, 'b');
  529. const std::string text_encoded_frame =
  530. EncodeFrame(text_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeText,
  531. /* mask= */ true,
  532. /* finish= */ false);
  533. const std::string continuation_encoded_frame = EncodeFrame(
  534. continuation_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeContinuation,
  535. /* mask= */ true, /* finish= */ true);
  536. client.Send(text_encoded_frame);
  537. client.Send(continuation_encoded_frame);
  538. std::string received_message = GetMessage();
  539. EXPECT_EQ(received_message.size(),
  540. text_frame.size() + continuation_frame.size());
  541. EXPECT_EQ(received_message, text_frame + continuation_frame);
  542. }
  543. TEST_F(WebSocketAcceptingTest, SendTwoTextFrame) {
  544. TestHttpClient client;
  545. CreateConnection(&client);
  546. std::string response;
  547. client.Send(
  548. "GET /test HTTP/1.1\r\n"
  549. "Upgrade: WebSocket\r\n"
  550. "Connection: SomethingElse, Upgrade\r\n"
  551. "Sec-WebSocket-Version: 8\r\n"
  552. "Sec-WebSocket-Key: key\r\n\r\n");
  553. WaitForRequest();
  554. ASSERT_TRUE(client.ReadResponse(&response));
  555. const std::string text_frame_first = "foo";
  556. const std::string continuation_frame_first = "bar";
  557. const std::string text_encoded_frame_first = EncodeFrame(
  558. text_frame_first, WebSocketFrameHeader::OpCodeEnum::kOpCodeText,
  559. /* mask= */ true,
  560. /* finish= */ false);
  561. const std::string continuation_encoded_frame_first =
  562. EncodeFrame(continuation_frame_first,
  563. WebSocketFrameHeader::OpCodeEnum::kOpCodeContinuation,
  564. /* mask= */ true, /* finish= */ true);
  565. const std::string text_frame_second = "FOO";
  566. const std::string continuation_frame_second = "BAR";
  567. const std::string text_encoded_frame_second = EncodeFrame(
  568. text_frame_second, WebSocketFrameHeader::OpCodeEnum::kOpCodeText,
  569. /* mask= */ true,
  570. /* finish= */ false);
  571. const std::string continuation_encoded_frame_second =
  572. EncodeFrame(continuation_frame_second,
  573. WebSocketFrameHeader::OpCodeEnum::kOpCodeContinuation,
  574. /* mask= */ true, /* finish= */ true);
  575. // text_encoded_frame_first -> text_encoded_frame_second
  576. client.Send(text_encoded_frame_first);
  577. client.Send(continuation_encoded_frame_first);
  578. std::string received_message = GetMessage();
  579. EXPECT_EQ(received_message, "foobar");
  580. client.Send(text_encoded_frame_second);
  581. client.Send(continuation_encoded_frame_second);
  582. received_message = GetMessage();
  583. EXPECT_EQ(received_message, "FOOBAR");
  584. }
  585. TEST_F(WebSocketAcceptingTest, SendPingPongFrame) {
  586. TestHttpClient client;
  587. CreateConnection(&client);
  588. std::string response;
  589. client.Send(
  590. "GET /test HTTP/1.1\r\n"
  591. "Upgrade: WebSocket\r\n"
  592. "Connection: SomethingElse, Upgrade\r\n"
  593. "Sec-WebSocket-Version: 8\r\n"
  594. "Sec-WebSocket-Key: key\r\n\r\n");
  595. WaitForRequest();
  596. ASSERT_TRUE(client.ReadResponse(&response));
  597. const std::string ping_message_first = "";
  598. const std::string ping_frame_first = EncodeFrame(
  599. ping_message_first, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  600. /* mask= */ true, /* finish= */ true);
  601. const std::string pong_frame_receive_first = EncodeFrame(
  602. ping_message_first, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  603. /* mask= */ false, /* finish= */ true);
  604. const std::string pong_frame_send = EncodeFrame(
  605. /* message= */ "", WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  606. /* mask= */ true, /* finish= */ true);
  607. const std::string ping_message_second = "hello";
  608. const std::string ping_frame_second = EncodeFrame(
  609. ping_message_second, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  610. /* mask= */ true, /* finish= */ true);
  611. const std::string pong_frame_receive_second = EncodeFrame(
  612. ping_message_second, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  613. /* mask= */ false, /* finish= */ true);
  614. // ping_frame_first -> pong_frame_send -> ping_frame_second
  615. client.Send(ping_frame_first);
  616. ASSERT_TRUE(client.Read(&response, pong_frame_receive_first.length()));
  617. EXPECT_EQ(response, pong_frame_receive_first);
  618. client.Send(pong_frame_send);
  619. client.Send(ping_frame_second);
  620. ASSERT_TRUE(client.Read(&response, pong_frame_receive_second.length()));
  621. EXPECT_EQ(response, pong_frame_receive_second);
  622. }
  623. TEST_F(WebSocketAcceptingTest, SendTextAndPingFrame) {
  624. TestHttpClient client;
  625. CreateConnection(&client);
  626. std::string response;
  627. client.Send(
  628. "GET /test HTTP/1.1\r\n"
  629. "Upgrade: WebSocket\r\n"
  630. "Connection: SomethingElse, Upgrade\r\n"
  631. "Sec-WebSocket-Version: 8\r\n"
  632. "Sec-WebSocket-Key: key\r\n\r\n");
  633. WaitForRequest();
  634. ASSERT_TRUE(client.ReadResponse(&response));
  635. const std::string text_frame = "foo";
  636. const std::string continuation_frame = "bar";
  637. const std::string text_encoded_frame =
  638. EncodeFrame(text_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeText,
  639. /* mask= */ true,
  640. /* finish= */ false);
  641. const std::string continuation_encoded_frame = EncodeFrame(
  642. continuation_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeContinuation,
  643. /* mask= */ true, /* finish= */ true);
  644. const std::string ping_message = "ping";
  645. const std::string ping_frame =
  646. EncodeFrame(ping_message, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  647. /* mask= */ true, /* finish= */ true);
  648. const std::string pong_frame =
  649. EncodeFrame(ping_message, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  650. /* mask= */ false, /* finish= */ true);
  651. // text_encoded_frame -> ping_frame -> continuation_encoded_frame
  652. client.Send(text_encoded_frame);
  653. client.Send(ping_frame);
  654. client.Send(continuation_encoded_frame);
  655. ASSERT_TRUE(client.Read(&response, pong_frame.length()));
  656. EXPECT_EQ(response, pong_frame);
  657. std::string received_message = GetMessage();
  658. EXPECT_EQ(received_message, "foobar");
  659. }
  660. TEST_F(WebSocketAcceptingTest, SendTextAndPingFrameWithMessage) {
  661. TestHttpClient client;
  662. CreateConnection(&client);
  663. std::string response;
  664. client.Send(
  665. "GET /test HTTP/1.1\r\n"
  666. "Upgrade: WebSocket\r\n"
  667. "Connection: SomethingElse, Upgrade\r\n"
  668. "Sec-WebSocket-Version: 8\r\n"
  669. "Sec-WebSocket-Key: key\r\n\r\n");
  670. WaitForRequest();
  671. ASSERT_TRUE(client.ReadResponse(&response));
  672. const std::string text_frame = "foo";
  673. const std::string continuation_frame = "bar";
  674. const std::string text_encoded_frame =
  675. EncodeFrame(text_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeText,
  676. /* mask= */ true,
  677. /* finish= */ false);
  678. const std::string continuation_encoded_frame = EncodeFrame(
  679. continuation_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeContinuation,
  680. /* mask= */ true, /* finish= */ true);
  681. const std::string ping_message = "hello";
  682. const std::string ping_frame =
  683. EncodeFrame(ping_message, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  684. /* mask= */ true, /* finish= */ true);
  685. const std::string pong_frame =
  686. EncodeFrame(ping_message, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  687. /* mask= */ false, /* finish= */ true);
  688. // text_encoded_frame -> ping_frame -> continuation_frame
  689. client.Send(text_encoded_frame);
  690. client.Send(ping_frame);
  691. client.Send(continuation_encoded_frame);
  692. ASSERT_TRUE(client.Read(&response, pong_frame.length()));
  693. EXPECT_EQ(response, pong_frame);
  694. std::string received_message = GetMessage();
  695. EXPECT_EQ(received_message, "foobar");
  696. }
  697. TEST_F(WebSocketAcceptingTest, SendTextAndPongFrame) {
  698. TestHttpClient client;
  699. CreateConnection(&client);
  700. std::string response;
  701. client.Send(
  702. "GET /test HTTP/1.1\r\n"
  703. "Upgrade: WebSocket\r\n"
  704. "Connection: SomethingElse, Upgrade\r\n"
  705. "Sec-WebSocket-Version: 8\r\n"
  706. "Sec-WebSocket-Key: key\r\n\r\n");
  707. WaitForRequest();
  708. ASSERT_TRUE(client.ReadResponse(&response));
  709. const std::string text_frame = "foo";
  710. const std::string continuation_frame = "bar";
  711. const std::string text_encoded_frame =
  712. EncodeFrame(text_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeText,
  713. /* mask= */ true,
  714. /* finish= */ false);
  715. const std::string continuation_encoded_frame = EncodeFrame(
  716. continuation_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeContinuation,
  717. /* mask= */ true, /* finish= */ true);
  718. const std::string pong_message = "pong";
  719. const std::string pong_frame =
  720. EncodeFrame(pong_message, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  721. /* mask= */ true, /* finish= */ true);
  722. // text_encoded_frame -> pong_frame -> continuation_encoded_frame
  723. client.Send(text_encoded_frame);
  724. client.Send(pong_frame);
  725. client.Send(continuation_encoded_frame);
  726. std::string received_message = GetMessage();
  727. EXPECT_EQ(received_message, "foobar");
  728. }
  729. TEST_F(WebSocketAcceptingTest, SendTextPingPongFrame) {
  730. TestHttpClient client;
  731. CreateConnection(&client);
  732. std::string response;
  733. client.Send(
  734. "GET /test HTTP/1.1\r\n"
  735. "Upgrade: WebSocket\r\n"
  736. "Connection: SomethingElse, Upgrade\r\n"
  737. "Sec-WebSocket-Version: 8\r\n"
  738. "Sec-WebSocket-Key: key\r\n\r\n");
  739. WaitForRequest();
  740. ASSERT_TRUE(client.ReadResponse(&response));
  741. const std::string text_frame = "foo";
  742. const std::string continuation_frame = "bar";
  743. const std::string text_encoded_frame =
  744. EncodeFrame(text_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeText,
  745. /* mask= */ true,
  746. /* finish= */ false);
  747. const std::string continuation_encoded_frame = EncodeFrame(
  748. continuation_frame, WebSocketFrameHeader::OpCodeEnum::kOpCodeContinuation,
  749. /* mask= */ true, /* finish= */ true);
  750. const std::string ping_message_first = "hello";
  751. const std::string ping_frame_first = EncodeFrame(
  752. ping_message_first, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  753. /* mask= */ true, /* finish= */ true);
  754. const std::string pong_frame_first = EncodeFrame(
  755. ping_message_first, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  756. /* mask= */ false, /* finish= */ true);
  757. const std::string ping_message_second = "HELLO";
  758. const std::string ping_frame_second = EncodeFrame(
  759. ping_message_second, WebSocketFrameHeader::OpCodeEnum::kOpCodePing,
  760. /* mask= */ true, /* finish= */ true);
  761. const std::string pong_frame_second = EncodeFrame(
  762. ping_message_second, WebSocketFrameHeader::OpCodeEnum::kOpCodePong,
  763. /* mask= */ false, /* finish= */ true);
  764. // text_encoded_frame -> ping_frame_first -> ping_frame_second ->
  765. // continuation_encoded_frame
  766. client.Send(text_encoded_frame);
  767. client.Send(ping_frame_first);
  768. ASSERT_TRUE(client.Read(&response, pong_frame_first.length()));
  769. EXPECT_EQ(response, pong_frame_first);
  770. client.Send(ping_frame_second);
  771. ASSERT_TRUE(client.Read(&response, pong_frame_second.length()));
  772. EXPECT_EQ(response, pong_frame_second);
  773. client.Send(continuation_encoded_frame);
  774. std::string received_message = GetMessage();
  775. EXPECT_EQ(received_message, "foobar");
  776. }
  777. TEST_F(HttpServerTest, RequestWithTooLargeBody) {
  778. TestHttpClient client;
  779. CreateConnection(&client);
  780. client.Send(
  781. "GET /test HTTP/1.1\r\n"
  782. "Content-Length: 1073741824\r\n\r\n");
  783. std::string response;
  784. ASSERT_TRUE(client.ReadResponse(&response));
  785. EXPECT_EQ(
  786. "HTTP/1.1 500 Internal Server Error\r\n"
  787. "Content-Length:42\r\n"
  788. "Content-Type:text/html\r\n\r\n"
  789. "request content-length too big or unknown.",
  790. response);
  791. }
  792. TEST_F(HttpServerTest, Send200) {
  793. TestHttpClient client;
  794. CreateConnection(&client);
  795. client.Send("GET /test HTTP/1.1\r\n\r\n");
  796. auto request = WaitForRequest();
  797. server_->Send200(request.connection_id, "Response!", "text/plain",
  798. TRAFFIC_ANNOTATION_FOR_TESTS);
  799. std::string response;
  800. ASSERT_TRUE(client.ReadResponse(&response));
  801. ASSERT_TRUE(base::StartsWith(response, "HTTP/1.1 200 OK",
  802. base::CompareCase::SENSITIVE));
  803. ASSERT_TRUE(
  804. base::EndsWith(response, "Response!", base::CompareCase::SENSITIVE));
  805. }
  806. TEST_F(HttpServerTest, SendRaw) {
  807. TestHttpClient client;
  808. CreateConnection(&client);
  809. client.Send("GET /test HTTP/1.1\r\n\r\n");
  810. auto request = WaitForRequest();
  811. server_->SendRaw(request.connection_id, "Raw Data ",
  812. TRAFFIC_ANNOTATION_FOR_TESTS);
  813. server_->SendRaw(request.connection_id, "More Data",
  814. TRAFFIC_ANNOTATION_FOR_TESTS);
  815. server_->SendRaw(request.connection_id, "Third Piece of Data",
  816. TRAFFIC_ANNOTATION_FOR_TESTS);
  817. const std::string expected_response("Raw Data More DataThird Piece of Data");
  818. std::string response;
  819. ASSERT_TRUE(client.Read(&response, expected_response.length()));
  820. ASSERT_EQ(expected_response, response);
  821. }
  822. TEST_F(HttpServerTest, WrongProtocolRequest) {
  823. const char* const kBadProtocolRequests[] = {
  824. "GET /test HTTP/1.0\r\n\r\n",
  825. "GET /test foo\r\n\r\n",
  826. "GET /test \r\n\r\n",
  827. };
  828. for (const char* bad_request : kBadProtocolRequests) {
  829. TestHttpClient client;
  830. CreateConnection(&client);
  831. client.Send(bad_request);
  832. client.ExpectUsedThenDisconnectedWithNoData();
  833. // Assert that the delegate was updated properly.
  834. ASSERT_EQ(1u, connection_map().size());
  835. ASSERT_FALSE(connection_map().begin()->second);
  836. EXPECT_FALSE(HasRequest());
  837. // Reset the state of the connection map.
  838. connection_map().clear();
  839. }
  840. }
  841. class MockStreamSocket : public StreamSocket {
  842. public:
  843. MockStreamSocket() = default;
  844. MockStreamSocket(const MockStreamSocket&) = delete;
  845. MockStreamSocket& operator=(const MockStreamSocket&) = delete;
  846. ~MockStreamSocket() override = default;
  847. // StreamSocket
  848. int Connect(CompletionOnceCallback callback) override {
  849. return ERR_NOT_IMPLEMENTED;
  850. }
  851. void Disconnect() override {
  852. connected_ = false;
  853. if (!read_callback_.is_null()) {
  854. read_buf_ = nullptr;
  855. read_buf_len_ = 0;
  856. std::move(read_callback_).Run(ERR_CONNECTION_CLOSED);
  857. }
  858. }
  859. bool IsConnected() const override { return connected_; }
  860. bool IsConnectedAndIdle() const override { return IsConnected(); }
  861. int GetPeerAddress(IPEndPoint* address) const override {
  862. return ERR_NOT_IMPLEMENTED;
  863. }
  864. int GetLocalAddress(IPEndPoint* address) const override {
  865. return ERR_NOT_IMPLEMENTED;
  866. }
  867. const NetLogWithSource& NetLog() const override { return net_log_; }
  868. bool WasEverUsed() const override { return true; }
  869. bool WasAlpnNegotiated() const override { return false; }
  870. NextProto GetNegotiatedProtocol() const override { return kProtoUnknown; }
  871. bool GetSSLInfo(SSLInfo* ssl_info) override { return false; }
  872. int64_t GetTotalReceivedBytes() const override {
  873. NOTIMPLEMENTED();
  874. return 0;
  875. }
  876. void ApplySocketTag(const SocketTag& tag) override {}
  877. // Socket
  878. int Read(IOBuffer* buf,
  879. int buf_len,
  880. CompletionOnceCallback callback) override {
  881. if (!connected_) {
  882. return ERR_SOCKET_NOT_CONNECTED;
  883. }
  884. if (pending_read_data_.empty()) {
  885. read_buf_ = buf;
  886. read_buf_len_ = buf_len;
  887. read_callback_ = std::move(callback);
  888. return ERR_IO_PENDING;
  889. }
  890. DCHECK_GT(buf_len, 0);
  891. int read_len =
  892. std::min(static_cast<int>(pending_read_data_.size()), buf_len);
  893. memcpy(buf->data(), pending_read_data_.data(), read_len);
  894. pending_read_data_.erase(0, read_len);
  895. return read_len;
  896. }
  897. int Write(IOBuffer* buf,
  898. int buf_len,
  899. CompletionOnceCallback callback,
  900. const NetworkTrafficAnnotationTag& traffic_annotation) override {
  901. return ERR_NOT_IMPLEMENTED;
  902. }
  903. int SetReceiveBufferSize(int32_t size) override {
  904. return ERR_NOT_IMPLEMENTED;
  905. }
  906. int SetSendBufferSize(int32_t size) override { return ERR_NOT_IMPLEMENTED; }
  907. void DidRead(const char* data, int data_len) {
  908. if (!read_buf_.get()) {
  909. pending_read_data_.append(data, data_len);
  910. return;
  911. }
  912. int read_len = std::min(data_len, read_buf_len_);
  913. memcpy(read_buf_->data(), data, read_len);
  914. pending_read_data_.assign(data + read_len, data_len - read_len);
  915. read_buf_ = nullptr;
  916. read_buf_len_ = 0;
  917. std::move(read_callback_).Run(read_len);
  918. }
  919. private:
  920. bool connected_ = true;
  921. scoped_refptr<IOBuffer> read_buf_;
  922. int read_buf_len_ = 0;
  923. CompletionOnceCallback read_callback_;
  924. std::string pending_read_data_;
  925. NetLogWithSource net_log_;
  926. };
  927. TEST_F(HttpServerTest, RequestWithBodySplitAcrossPackets) {
  928. auto socket = std::make_unique<MockStreamSocket>();
  929. auto* socket_ptr = socket.get();
  930. HandleAcceptResult(std::move(socket));
  931. std::string body("body");
  932. std::string request_text = base::StringPrintf(
  933. "GET /test HTTP/1.1\r\n"
  934. "SomeHeader: 1\r\n"
  935. "Content-Length: %" PRIuS "\r\n\r\n%s",
  936. body.length(), body.c_str());
  937. socket_ptr->DidRead(request_text.c_str(), request_text.length() - 2);
  938. ASSERT_FALSE(HasRequest());
  939. socket_ptr->DidRead(request_text.c_str() + request_text.length() - 2, 2);
  940. ASSERT_TRUE(HasRequest());
  941. ASSERT_EQ(body, WaitForRequest().info.data);
  942. }
  943. TEST_F(HttpServerTest, MultipleRequestsOnSameConnection) {
  944. // The idea behind this test is that requests with or without bodies should
  945. // not break parsing of the next request.
  946. TestHttpClient client;
  947. CreateConnection(&client);
  948. std::string body = "body";
  949. client.Send(
  950. base::StringPrintf("GET /test HTTP/1.1\r\n"
  951. "Content-Length: %" PRIuS "\r\n\r\n%s",
  952. body.length(), body.c_str()));
  953. auto first_request = WaitForRequest();
  954. ASSERT_EQ(body, first_request.info.data);
  955. int client_connection_id = first_request.connection_id;
  956. server_->Send200(client_connection_id, "Content for /test", "text/plain",
  957. TRAFFIC_ANNOTATION_FOR_TESTS);
  958. std::string response1;
  959. ASSERT_TRUE(client.ReadResponse(&response1));
  960. ASSERT_TRUE(base::StartsWith(response1, "HTTP/1.1 200 OK",
  961. base::CompareCase::SENSITIVE));
  962. ASSERT_TRUE(base::EndsWith(response1, "Content for /test",
  963. base::CompareCase::SENSITIVE));
  964. client.Send("GET /test2 HTTP/1.1\r\n\r\n");
  965. auto second_request = WaitForRequest();
  966. ASSERT_EQ("/test2", second_request.info.path);
  967. ASSERT_EQ(client_connection_id, second_request.connection_id);
  968. server_->Send404(client_connection_id, TRAFFIC_ANNOTATION_FOR_TESTS);
  969. std::string response2;
  970. ASSERT_TRUE(client.ReadResponse(&response2));
  971. ASSERT_TRUE(base::StartsWith(response2, "HTTP/1.1 404 Not Found",
  972. base::CompareCase::SENSITIVE));
  973. client.Send("GET /test3 HTTP/1.1\r\n\r\n");
  974. auto third_request = WaitForRequest();
  975. ASSERT_EQ("/test3", third_request.info.path);
  976. ASSERT_EQ(client_connection_id, third_request.connection_id);
  977. server_->Send200(client_connection_id, "Content for /test3", "text/plain",
  978. TRAFFIC_ANNOTATION_FOR_TESTS);
  979. std::string response3;
  980. ASSERT_TRUE(client.ReadResponse(&response3));
  981. ASSERT_TRUE(base::StartsWith(response3, "HTTP/1.1 200 OK",
  982. base::CompareCase::SENSITIVE));
  983. ASSERT_TRUE(base::EndsWith(response3, "Content for /test3",
  984. base::CompareCase::SENSITIVE));
  985. }
  986. class CloseOnConnectHttpServerTest : public HttpServerTest {
  987. public:
  988. void OnConnect(int connection_id) override {
  989. HttpServerTest::OnConnect(connection_id);
  990. connection_ids_.push_back(connection_id);
  991. server_->Close(connection_id);
  992. }
  993. protected:
  994. std::vector<int> connection_ids_;
  995. };
  996. TEST_F(CloseOnConnectHttpServerTest, ServerImmediatelyClosesConnection) {
  997. TestHttpClient client;
  998. CreateConnection(&client);
  999. client.Send("GET / HTTP/1.1\r\n\r\n");
  1000. // The server should close the socket without responding.
  1001. client.ExpectUsedThenDisconnectedWithNoData();
  1002. // Run any tasks the TestServer posted.
  1003. base::RunLoop().RunUntilIdle();
  1004. EXPECT_EQ(1ul, connection_ids_.size());
  1005. // OnHttpRequest() should never have been called, since the connection was
  1006. // closed without reading from it.
  1007. EXPECT_FALSE(HasRequest());
  1008. }
  1009. } // namespace
  1010. } // namespace net