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

Side by Side Diff: net/spdy/bidirectional_stream_spdy_impl_unittest.cc

Issue 2356463002: Implements BidirectionalStreamSpdyImpl::GetLoadTimingInfo (Closed)
Patch Set: Rebased Created 4 years, 3 months 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
« no previous file with comments | « net/spdy/bidirectional_stream_spdy_impl.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "net/spdy/bidirectional_stream_spdy_impl.h" 5 #include "net/spdy/bidirectional_stream_spdy_impl.h"
6 6
7 #include <memory> 7 #include <memory>
8 #include <string> 8 #include <string>
9 9
10 #include "base/macros.h" 10 #include "base/macros.h"
11 #include "base/memory/ptr_util.h" 11 #include "base/memory/ptr_util.h"
12 #include "base/run_loop.h" 12 #include "base/run_loop.h"
13 #include "base/strings/string_number_conversions.h" 13 #include "base/strings/string_number_conversions.h"
14 #include "base/strings/string_piece.h" 14 #include "base/strings/string_piece.h"
15 #include "base/time/time.h" 15 #include "base/time/time.h"
16 #include "base/timer/mock_timer.h" 16 #include "base/timer/mock_timer.h"
17 #include "net/base/load_timing_info.h"
18 #include "net/base/load_timing_info_test_util.h"
17 #include "net/base/net_errors.h" 19 #include "net/base/net_errors.h"
18 #include "net/http/http_request_info.h" 20 #include "net/http/http_request_info.h"
19 #include "net/http/http_response_headers.h" 21 #include "net/http/http_response_headers.h"
20 #include "net/http/http_response_info.h" 22 #include "net/http/http_response_info.h"
21 #include "net/log/net_log.h" 23 #include "net/log/net_log.h"
22 #include "net/log/test_net_log.h" 24 #include "net/log/test_net_log.h"
23 #include "net/socket/socket_test_util.h" 25 #include "net/socket/socket_test_util.h"
24 #include "net/spdy/spdy_session.h" 26 #include "net/spdy/spdy_session.h"
25 #include "net/spdy/spdy_test_util_common.h" 27 #include "net/spdy/spdy_test_util_common.h"
26 #include "net/test/cert_test_util.h" 28 #include "net/test/cert_test_util.h"
27 #include "net/test/gtest_util.h" 29 #include "net/test/gtest_util.h"
28 #include "net/test/test_data_directory.h" 30 #include "net/test/test_data_directory.h"
29 #include "testing/gmock/include/gmock/gmock.h" 31 #include "testing/gmock/include/gmock/gmock.h"
30 #include "testing/gtest/include/gtest/gtest.h" 32 #include "testing/gtest/include/gtest/gtest.h"
31 33
32 using net::test::IsError; 34 using net::test::IsError;
33 using net::test::IsOk; 35 using net::test::IsOk;
34 36
35 namespace net { 37 namespace net {
36 38
37 namespace { 39 namespace {
38 40
39 const char kBodyData[] = "Body data"; 41 const char kBodyData[] = "Body data";
40 const size_t kBodyDataSize = arraysize(kBodyData); 42 const size_t kBodyDataSize = arraysize(kBodyData);
41 // Size of the buffer to be allocated for each read. 43 // Size of the buffer to be allocated for each read.
42 const size_t kReadBufferSize = 4096; 44 const size_t kReadBufferSize = 4096;
43 45
46 // Tests the load timing of a stream that's connected and is not the first
47 // request sent on a connection.
48 void TestLoadTimingReused(const LoadTimingInfo& load_timing_info) {
49 EXPECT_TRUE(load_timing_info.socket_reused);
50 EXPECT_NE(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
51
52 ExpectConnectTimingHasNoTimes(load_timing_info.connect_timing);
53 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
54 }
55
56 // Tests the load timing of a stream that's connected and using a fresh
57 // connection.
58 void TestLoadTimingNotReused(const LoadTimingInfo& load_timing_info) {
59 EXPECT_FALSE(load_timing_info.socket_reused);
60 EXPECT_NE(NetLog::Source::kInvalidId, load_timing_info.socket_log_id);
61
62 ExpectConnectTimingHasTimes(
63 load_timing_info.connect_timing,
64 CONNECT_TIMING_HAS_SSL_TIMES | CONNECT_TIMING_HAS_DNS_TIMES);
65 ExpectLoadTimingHasOnlyConnectionTimes(load_timing_info);
66 }
67
44 class TestDelegateBase : public BidirectionalStreamImpl::Delegate { 68 class TestDelegateBase : public BidirectionalStreamImpl::Delegate {
45 public: 69 public:
46 TestDelegateBase(base::WeakPtr<SpdySession> session, 70 TestDelegateBase(base::WeakPtr<SpdySession> session,
47 IOBuffer* read_buf, 71 IOBuffer* read_buf,
48 int read_buf_len) 72 int read_buf_len)
49 : stream_(new BidirectionalStreamSpdyImpl(session)), 73 : stream_(new BidirectionalStreamSpdyImpl(session)),
50 read_buf_(read_buf), 74 read_buf_(read_buf),
51 read_buf_len_(read_buf_len), 75 read_buf_len_(read_buf_len),
52 loop_(nullptr), 76 loop_(nullptr),
53 received_bytes_(0),
54 sent_bytes_(0),
55 error_(OK), 77 error_(OK),
56 bytes_read_(0), 78 bytes_read_(0),
57 on_data_read_count_(0), 79 on_data_read_count_(0),
58 on_data_sent_count_(0), 80 on_data_sent_count_(0),
59 do_not_start_read_(false), 81 do_not_start_read_(false),
60 run_until_completion_(false), 82 run_until_completion_(false),
61 not_expect_callback_(false), 83 not_expect_callback_(false),
62 on_failed_called_(false) {} 84 on_failed_called_(false) {}
63 85
64 ~TestDelegateBase() override {} 86 ~TestDelegateBase() override {}
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after
130 stream_->SendvData(data, length, end_of_stream); 152 stream_->SendvData(data, length, end_of_stream);
131 not_expect_callback_ = false; 153 not_expect_callback_ = false;
132 } 154 }
133 155
134 // Sets whether the delegate should wait until the completion of the stream. 156 // Sets whether the delegate should wait until the completion of the stream.
135 void SetRunUntilCompletion(bool run_until_completion) { 157 void SetRunUntilCompletion(bool run_until_completion) {
136 run_until_completion_ = run_until_completion; 158 run_until_completion_ = run_until_completion;
137 loop_.reset(new base::RunLoop); 159 loop_.reset(new base::RunLoop);
138 } 160 }
139 161
162 // Wait until the stream reaches completion.
163 void WaitUntilCompletion() { loop_->Run(); }
164
140 // Starts or continues read data from |stream_| until there is no more 165 // Starts or continues read data from |stream_| until there is no more
141 // byte can be read synchronously. 166 // byte can be read synchronously.
142 void StartOrContinueReading() { 167 void StartOrContinueReading() {
143 int rv = ReadData(); 168 int rv = ReadData();
144 while (rv > 0) { 169 while (rv > 0) {
145 rv = ReadData(); 170 rv = ReadData();
146 } 171 }
147 if (run_until_completion_ && rv == 0) 172 if (run_until_completion_ && rv == 0)
148 loop_->Quit(); 173 loop_->Quit();
149 } 174 }
150 175
151 // Calls ReadData on the |stream_| and updates internal states. 176 // Calls ReadData on the |stream_| and updates internal states.
152 int ReadData() { 177 int ReadData() {
153 int rv = stream_->ReadData(read_buf_.get(), read_buf_len_); 178 int rv = stream_->ReadData(read_buf_.get(), read_buf_len_);
154 if (rv > 0) { 179 if (rv > 0) {
155 data_received_.append(read_buf_->data(), rv); 180 data_received_.append(read_buf_->data(), rv);
156 bytes_read_ += rv; 181 bytes_read_ += rv;
157 } 182 }
158 return rv; 183 return rv;
159 } 184 }
160 185
161 NextProto GetProtocol() const { return stream_->GetProtocol(); } 186 NextProto GetProtocol() const { return stream_->GetProtocol(); }
162 187
163 int64_t GetTotalReceivedBytes() const { 188 int64_t GetTotalReceivedBytes() const {
164 if (stream_)
165 return stream_->GetTotalReceivedBytes(); 189 return stream_->GetTotalReceivedBytes();
166 return received_bytes_;
167 } 190 }
168 191
169 int64_t GetTotalSentBytes() const { 192 int64_t GetTotalSentBytes() const {
170 if (stream_)
171 return stream_->GetTotalSentBytes(); 193 return stream_->GetTotalSentBytes();
172 return sent_bytes_; 194 }
195
196 bool GetLoadTimingInfo(LoadTimingInfo* load_timing_info) const {
197 return stream_->GetLoadTimingInfo(load_timing_info);
173 } 198 }
174 199
175 // Const getters for internal states. 200 // Const getters for internal states.
176 const std::string& data_received() const { return data_received_; } 201 const std::string& data_received() const { return data_received_; }
177 int bytes_read() const { return bytes_read_; } 202 int bytes_read() const { return bytes_read_; }
178 int error() const { return error_; } 203 int error() const { return error_; }
179 const SpdyHeaderBlock& response_headers() const { return response_headers_; } 204 const SpdyHeaderBlock& response_headers() const { return response_headers_; }
180 const SpdyHeaderBlock& trailers() const { return trailers_; } 205 const SpdyHeaderBlock& trailers() const { return trailers_; }
181 int on_data_read_count() const { return on_data_read_count_; } 206 int on_data_read_count() const { return on_data_read_count_; }
182 int on_data_sent_count() const { return on_data_sent_count_; } 207 int on_data_sent_count() const { return on_data_sent_count_; }
183 bool on_failed_called() const { return on_failed_called_; } 208 bool on_failed_called() const { return on_failed_called_; }
184 209
185 // Sets whether the delegate should automatically start reading. 210 // Sets whether the delegate should automatically start reading.
186 void set_do_not_start_read(bool do_not_start_read) { 211 void set_do_not_start_read(bool do_not_start_read) {
187 do_not_start_read_ = do_not_start_read; 212 do_not_start_read_ = do_not_start_read;
188 } 213 }
189 214
190 void DeleteStream() { stream_.reset(); }
191
192 private: 215 private:
193 std::unique_ptr<BidirectionalStreamSpdyImpl> stream_; 216 std::unique_ptr<BidirectionalStreamSpdyImpl> stream_;
194 scoped_refptr<IOBuffer> read_buf_; 217 scoped_refptr<IOBuffer> read_buf_;
195 int read_buf_len_; 218 int read_buf_len_;
196 std::string data_received_; 219 std::string data_received_;
197 std::unique_ptr<base::RunLoop> loop_; 220 std::unique_ptr<base::RunLoop> loop_;
198 SpdyHeaderBlock response_headers_; 221 SpdyHeaderBlock response_headers_;
199 SpdyHeaderBlock trailers_; 222 SpdyHeaderBlock trailers_;
200 int64_t received_bytes_;
201 int64_t sent_bytes_;
202 int error_; 223 int error_;
203 int bytes_read_; 224 int bytes_read_;
204 int on_data_read_count_; 225 int on_data_read_count_;
205 int on_data_sent_count_; 226 int on_data_sent_count_;
206 bool do_not_start_read_; 227 bool do_not_start_read_;
207 bool run_until_completion_; 228 bool run_until_completion_;
208 bool not_expect_callback_; 229 bool not_expect_callback_;
209 bool on_failed_called_; 230 bool on_failed_called_;
210 231
211 DISALLOW_COPY_AND_ASSIGN(TestDelegateBase); 232 DISALLOW_COPY_AND_ASSIGN(TestDelegateBase);
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
255 const HostPortPair host_port_pair_; 276 const HostPortPair host_port_pair_;
256 const SpdySessionKey key_; 277 const SpdySessionKey key_;
257 std::unique_ptr<SequencedSocketData> sequenced_data_; 278 std::unique_ptr<SequencedSocketData> sequenced_data_;
258 std::unique_ptr<HttpNetworkSession> http_session_; 279 std::unique_ptr<HttpNetworkSession> http_session_;
259 base::WeakPtr<SpdySession> session_; 280 base::WeakPtr<SpdySession> session_;
260 281
261 private: 282 private:
262 SSLSocketDataProvider ssl_data_; 283 SSLSocketDataProvider ssl_data_;
263 }; 284 };
264 285
286 TEST_F(BidirectionalStreamSpdyImplTest, SimplePostRequest) {
287 SpdySerializedFrame req(spdy_util_.ConstructSpdyPost(
288 kDefaultUrl, 1, kBodyDataSize, LOW, nullptr, 0));
289 SpdySerializedFrame data_frame(spdy_util_.ConstructSpdyDataFrame(
290 1, kBodyData, kBodyDataSize, /*fin=*/true));
291 MockWrite writes[] = {
292 CreateMockWrite(req, 0), CreateMockWrite(data_frame, 3),
293 };
294 SpdySerializedFrame resp(spdy_util_.ConstructSpdyPostReply(nullptr, 0));
295 SpdySerializedFrame response_body_frame(
296 spdy_util_.ConstructSpdyDataFrame(1, /*fin=*/true));
297 MockRead reads[] = {
298 CreateMockRead(resp, 1),
299 MockRead(ASYNC, ERR_IO_PENDING, 2), // Force a pause.
300 CreateMockRead(response_body_frame, 4), MockRead(ASYNC, 0, 5),
301 };
302 InitSession(reads, arraysize(reads), writes, arraysize(writes));
303
304 BidirectionalStreamRequestInfo request_info;
305 request_info.method = "POST";
306 request_info.url = default_url_;
307 request_info.extra_headers.SetHeader(net::HttpRequestHeaders::kContentLength,
308 base::SizeTToString(kBodyDataSize));
309
310 scoped_refptr<IOBuffer> read_buffer(new IOBuffer(kReadBufferSize));
311 std::unique_ptr<TestDelegateBase> delegate(
312 new TestDelegateBase(session_, read_buffer.get(), kReadBufferSize));
313 delegate->SetRunUntilCompletion(true);
314 delegate->Start(&request_info, net_log_.bound());
315 sequenced_data_->RunUntilPaused();
316
317 scoped_refptr<StringIOBuffer> write_buffer(
318 new StringIOBuffer(std::string(kBodyData, kBodyDataSize)));
319 delegate->SendData(write_buffer.get(), write_buffer->size(), true);
320 sequenced_data_->Resume();
321 base::RunLoop().RunUntilIdle();
322 delegate->WaitUntilCompletion();
323 LoadTimingInfo load_timing_info;
324 EXPECT_TRUE(delegate->GetLoadTimingInfo(&load_timing_info));
325 TestLoadTimingNotReused(load_timing_info);
326
327 EXPECT_EQ(1, delegate->on_data_read_count());
328 EXPECT_EQ(1, delegate->on_data_sent_count());
329 EXPECT_EQ(kProtoHTTP2, delegate->GetProtocol());
330 EXPECT_EQ(CountWriteBytes(writes, arraysize(writes)),
331 delegate->GetTotalSentBytes());
332 EXPECT_EQ(CountReadBytes(reads, arraysize(reads)),
333 delegate->GetTotalReceivedBytes());
334 }
335
336 TEST_F(BidirectionalStreamSpdyImplTest, LoadTimingTwoRequests) {
337 SpdySerializedFrame req(
338 spdy_util_.ConstructSpdyGet(nullptr, 0, /*stream_id=*/1, LOW, true));
339 SpdySerializedFrame req2(
340 spdy_util_.ConstructSpdyGet(nullptr, 0, /*stream_id=*/3, LOW, true));
341 MockWrite writes[] = {
342 CreateMockWrite(req, 0), CreateMockWrite(req2, 2),
343 };
344 SpdySerializedFrame resp(
345 spdy_util_.ConstructSpdyGetReply(nullptr, 0, /*stream_id=*/1));
346 SpdySerializedFrame resp2(
347 spdy_util_.ConstructSpdyGetReply(nullptr, 0, /*stream_id=*/3));
348 SpdySerializedFrame resp_body(
349 spdy_util_.ConstructSpdyDataFrame(/*stream_id=*/1, /*fin=*/true));
350 SpdySerializedFrame resp_body2(
351 spdy_util_.ConstructSpdyDataFrame(/*stream_id=*/3, /*fin=*/true));
352 MockRead reads[] = {CreateMockRead(resp, 1), CreateMockRead(resp_body, 3),
353 CreateMockRead(resp2, 4), CreateMockRead(resp_body2, 5),
354 MockRead(ASYNC, 0, 6)};
355 InitSession(reads, arraysize(reads), writes, arraysize(writes));
356
357 BidirectionalStreamRequestInfo request_info;
358 request_info.method = "GET";
359 request_info.url = default_url_;
360 request_info.end_stream_on_headers = true;
361
362 scoped_refptr<IOBuffer> read_buffer(new IOBuffer(kReadBufferSize));
363 scoped_refptr<IOBuffer> read_buffer2(new IOBuffer(kReadBufferSize));
364 std::unique_ptr<TestDelegateBase> delegate(
365 new TestDelegateBase(session_, read_buffer.get(), kReadBufferSize));
366 std::unique_ptr<TestDelegateBase> delegate2(
367 new TestDelegateBase(session_, read_buffer2.get(), kReadBufferSize));
368 delegate->SetRunUntilCompletion(true);
369 delegate2->SetRunUntilCompletion(true);
370 delegate->Start(&request_info, net_log_.bound());
371 delegate2->Start(&request_info, net_log_.bound());
372
373 base::RunLoop().RunUntilIdle();
374 delegate->WaitUntilCompletion();
375 delegate2->WaitUntilCompletion();
376 LoadTimingInfo load_timing_info;
377 EXPECT_TRUE(delegate->GetLoadTimingInfo(&load_timing_info));
378 TestLoadTimingNotReused(load_timing_info);
379 LoadTimingInfo load_timing_info2;
380 EXPECT_TRUE(delegate2->GetLoadTimingInfo(&load_timing_info2));
381 TestLoadTimingReused(load_timing_info2);
382 }
383
265 TEST_F(BidirectionalStreamSpdyImplTest, SendDataAfterStreamFailed) { 384 TEST_F(BidirectionalStreamSpdyImplTest, SendDataAfterStreamFailed) {
266 SpdySerializedFrame req(spdy_util_.ConstructSpdyPost( 385 SpdySerializedFrame req(spdy_util_.ConstructSpdyPost(
267 kDefaultUrl, 1, kBodyDataSize * 3, LOW, nullptr, 0)); 386 kDefaultUrl, 1, kBodyDataSize * 3, LOW, nullptr, 0));
268 SpdySerializedFrame rst( 387 SpdySerializedFrame rst(
269 spdy_util_.ConstructSpdyRstStream(1, RST_STREAM_PROTOCOL_ERROR)); 388 spdy_util_.ConstructSpdyRstStream(1, RST_STREAM_PROTOCOL_ERROR));
270 389
271 MockWrite writes[] = { 390 MockWrite writes[] = {
272 CreateMockWrite(req, 0), CreateMockWrite(rst, 2), 391 CreateMockWrite(req, 0), CreateMockWrite(rst, 2),
273 }; 392 };
274 393
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
307 EXPECT_EQ(0, delegate->on_data_sent_count()); 426 EXPECT_EQ(0, delegate->on_data_sent_count());
308 EXPECT_EQ(kProtoHTTP2, delegate->GetProtocol()); 427 EXPECT_EQ(kProtoHTTP2, delegate->GetProtocol());
309 // BidirectionalStreamSpdyStreamJob does not count the bytes sent for |rst| 428 // BidirectionalStreamSpdyStreamJob does not count the bytes sent for |rst|
310 // because it is sent after SpdyStream::Delegate::OnClose is called. 429 // because it is sent after SpdyStream::Delegate::OnClose is called.
311 EXPECT_EQ(CountWriteBytes(writes, 1), delegate->GetTotalSentBytes()); 430 EXPECT_EQ(CountWriteBytes(writes, 1), delegate->GetTotalSentBytes());
312 EXPECT_EQ(CountReadBytes(reads, arraysize(reads)), 431 EXPECT_EQ(CountReadBytes(reads, arraysize(reads)),
313 delegate->GetTotalReceivedBytes()); 432 delegate->GetTotalReceivedBytes());
314 } 433 }
315 434
316 } // namespace net 435 } // namespace net
OLDNEW
« no previous file with comments | « net/spdy/bidirectional_stream_spdy_impl.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698