OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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/base/network_quality_estimator.h" | 5 #include "net/base/network_quality_estimator.h" |
6 | 6 |
7 #include <stdint.h> | 7 #include <stdint.h> |
8 | 8 |
9 #include <limits> | 9 #include <limits> |
10 #include <map> | 10 #include <map> |
11 | 11 |
12 #include "base/basictypes.h" | 12 #include "base/basictypes.h" |
13 #include "base/files/file_path.h" | |
14 #include "base/logging.h" | 13 #include "base/logging.h" |
15 #include "base/memory/scoped_ptr.h" | 14 #include "base/memory/scoped_ptr.h" |
16 #include "base/metrics/histogram_samples.h" | 15 #include "base/metrics/histogram_samples.h" |
17 #include "base/run_loop.h" | 16 #include "base/run_loop.h" |
18 #include "base/strings/string_number_conversions.h" | 17 #include "base/strings/string_number_conversions.h" |
19 #include "base/test/histogram_tester.h" | 18 #include "base/test/histogram_tester.h" |
20 #include "base/time/time.h" | 19 #include "base/time/time.h" |
21 #include "build/build_config.h" | 20 #include "build/build_config.h" |
22 #include "net/base/external_estimate_provider.h" | 21 #include "net/base/external_estimate_provider.h" |
23 #include "net/base/load_flags.h" | 22 #include "net/base/load_flags.h" |
24 #include "net/base/network_change_notifier.h" | 23 #include "net/base/network_change_notifier.h" |
25 #include "net/http/http_status_code.h" | |
26 #include "net/test/embedded_test_server/embedded_test_server.h" | 24 #include "net/test/embedded_test_server/embedded_test_server.h" |
27 #include "net/test/embedded_test_server/http_request.h" | |
28 #include "net/test/embedded_test_server/http_response.h" | |
29 #include "net/url_request/url_request_test_util.h" | 25 #include "net/url_request/url_request_test_util.h" |
30 #include "testing/gtest/include/gtest/gtest.h" | 26 #include "testing/gtest/include/gtest/gtest.h" |
31 #include "url/gurl.h" | 27 #include "url/gurl.h" |
32 | 28 |
33 namespace { | 29 namespace { |
34 | 30 |
35 // Helps in setting the current network type and id. | 31 // Helps in setting the current network type and id. |
36 class TestNetworkQualityEstimator : public net::NetworkQualityEstimator { | 32 class TestNetworkQualityEstimator : public net::NetworkQualityEstimator { |
37 public: | 33 public: |
38 TestNetworkQualityEstimator( | 34 TestNetworkQualityEstimator( |
39 const std::map<std::string, std::string>& variation_params, | 35 const std::map<std::string, std::string>& variation_params) |
40 scoped_ptr<net::ExternalEstimateProvider> external_estimate_provider) | 36 : NetworkQualityEstimator(scoped_ptr<net::ExternalEstimateProvider>(), |
41 : NetworkQualityEstimator(external_estimate_provider.Pass(), | |
42 variation_params, | 37 variation_params, |
43 true, | 38 true, |
44 true) { | 39 true) {} |
45 // Set up embedded test server. | |
46 embedded_test_server_.ServeFilesFromDirectory( | |
47 base::FilePath(FILE_PATH_LITERAL("net/data/url_request_unittest"))); | |
48 DCHECK(embedded_test_server_.InitializeAndWaitUntilReady()); | |
49 embedded_test_server_.RegisterRequestHandler(base::Bind( | |
50 &TestNetworkQualityEstimator::HandleRequest, base::Unretained(this))); | |
51 } | |
52 | |
53 explicit TestNetworkQualityEstimator( | |
54 const std::map<std::string, std::string>& variation_params) | |
55 : TestNetworkQualityEstimator( | |
56 variation_params, | |
57 scoped_ptr<net::ExternalEstimateProvider>()) {} | |
58 | 40 |
59 ~TestNetworkQualityEstimator() override {} | 41 ~TestNetworkQualityEstimator() override {} |
60 | 42 |
61 // Overrides the current network type and id. | 43 // Overrides the current network type and id. |
62 // Notifies network quality estimator of change in connection. | 44 // Notifies network quality estimator of change in connection. |
63 void SimulateNetworkChangeTo(net::NetworkChangeNotifier::ConnectionType type, | 45 void SimulateNetworkChangeTo(net::NetworkChangeNotifier::ConnectionType type, |
64 std::string network_id) { | 46 std::string network_id) { |
65 current_network_type_ = type; | 47 current_network_type_ = type; |
66 current_network_id_ = network_id; | 48 current_network_id_ = network_id; |
67 OnConnectionTypeChanged(type); | 49 OnConnectionTypeChanged(type); |
68 } | 50 } |
69 | 51 |
70 // Called by embedded server when a HTTP request is received. | |
71 scoped_ptr<net::test_server::HttpResponse> HandleRequest( | |
72 const net::test_server::HttpRequest& request) { | |
73 scoped_ptr<net::test_server::BasicHttpResponse> http_response( | |
74 new net::test_server::BasicHttpResponse()); | |
75 http_response->set_code(net::HTTP_OK); | |
76 http_response->set_content("hello"); | |
77 http_response->set_content_type("text/plain"); | |
78 return http_response.Pass(); | |
79 } | |
80 | |
81 // Returns a GURL hosted at embedded test server. | |
82 const GURL GetEchoURL() const { | |
83 return embedded_test_server_.GetURL("/echo.html"); | |
84 } | |
85 | |
86 using NetworkQualityEstimator::ReadCachedNetworkQualityEstimate; | 52 using NetworkQualityEstimator::ReadCachedNetworkQualityEstimate; |
87 using NetworkQualityEstimator::OnConnectionTypeChanged; | 53 using NetworkQualityEstimator::OnConnectionTypeChanged; |
88 | 54 |
89 private: | 55 private: |
90 // NetworkQualityEstimator implementation that returns the overridden network | 56 // NetworkQualityEstimator implementation that returns the overridden network |
91 // id (instead of invoking platform APIs). | 57 // id (instead of invoking platform APIs). |
92 NetworkQualityEstimator::NetworkID GetCurrentNetworkID() const override { | 58 NetworkQualityEstimator::NetworkID GetCurrentNetworkID() const override { |
93 return NetworkQualityEstimator::NetworkID(current_network_type_, | 59 return NetworkQualityEstimator::NetworkID(current_network_type_, |
94 current_network_id_); | 60 current_network_id_); |
95 } | 61 } |
96 | 62 |
97 net::NetworkChangeNotifier::ConnectionType current_network_type_; | 63 net::NetworkChangeNotifier::ConnectionType current_network_type_; |
98 std::string current_network_id_; | 64 std::string current_network_id_; |
99 | |
100 // Embedded server used for testing. | |
101 net::test_server::EmbeddedTestServer embedded_test_server_; | |
102 | |
103 DISALLOW_COPY_AND_ASSIGN(TestNetworkQualityEstimator); | |
104 }; | 65 }; |
105 | 66 |
106 } // namespace | 67 } // namespace |
107 | 68 |
108 namespace net { | 69 namespace net { |
109 | 70 |
110 TEST(NetworkQualityEstimatorTest, TestKbpsRTTUpdates) { | 71 TEST(NetworkQualityEstimatorTest, TestKbpsRTTUpdates) { |
| 72 net::test_server::EmbeddedTestServer embedded_test_server; |
| 73 embedded_test_server.ServeFilesFromDirectory( |
| 74 base::FilePath(FILE_PATH_LITERAL("net/data/url_request_unittest"))); |
| 75 ASSERT_TRUE(embedded_test_server.InitializeAndWaitUntilReady()); |
| 76 |
111 base::HistogramTester histogram_tester; | 77 base::HistogramTester histogram_tester; |
112 // Enable requests to local host to be used for network quality estimation. | 78 // Enable requests to local host to be used for network quality estimation. |
113 std::map<std::string, std::string> variation_params; | 79 std::map<std::string, std::string> variation_params; |
114 TestNetworkQualityEstimator estimator(variation_params); | 80 TestNetworkQualityEstimator estimator(variation_params); |
115 | 81 |
116 EXPECT_EQ(NetworkQualityEstimator::InvalidRTT(), | 82 EXPECT_EQ(NetworkQualityEstimator::InvalidRTT(), |
117 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); | 83 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); |
118 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, | 84 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, |
119 estimator.GetDownlinkThroughputKbpsEstimateInternal( | 85 estimator.GetDownlinkThroughputKbpsEstimateInternal( |
120 base::TimeTicks(), 100)); | 86 base::TimeTicks(), 100)); |
121 | 87 |
122 TestDelegate test_delegate; | 88 TestDelegate test_delegate; |
123 TestURLRequestContext context(true); | 89 TestURLRequestContext context(false); |
124 context.set_network_quality_estimator(&estimator); | |
125 context.Init(); | |
126 | 90 |
127 scoped_ptr<URLRequest> request(context.CreateRequest( | 91 scoped_ptr<URLRequest> request( |
128 estimator.GetEchoURL(), DEFAULT_PRIORITY, &test_delegate)); | 92 context.CreateRequest(embedded_test_server.GetURL("/echo.html"), |
| 93 DEFAULT_PRIORITY, &test_delegate)); |
129 request->SetLoadFlags(request->load_flags() | LOAD_MAIN_FRAME); | 94 request->SetLoadFlags(request->load_flags() | LOAD_MAIN_FRAME); |
130 request->Start(); | 95 request->Start(); |
| 96 |
131 base::RunLoop().Run(); | 97 base::RunLoop().Run(); |
132 | 98 |
133 // Both RTT and downstream throughput should be updated. | 99 // Both RTT and downstream throughput should be updated. |
| 100 estimator.NotifyHeadersReceived(*request); |
| 101 estimator.NotifyRequestCompleted(*request); |
134 EXPECT_NE(NetworkQualityEstimator::InvalidRTT(), | 102 EXPECT_NE(NetworkQualityEstimator::InvalidRTT(), |
135 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); | 103 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); |
136 EXPECT_NE(NetworkQualityEstimator::kInvalidThroughput, | 104 EXPECT_NE(NetworkQualityEstimator::kInvalidThroughput, |
137 estimator.GetDownlinkThroughputKbpsEstimateInternal( | 105 estimator.GetDownlinkThroughputKbpsEstimateInternal( |
138 base::TimeTicks(), 100)); | 106 base::TimeTicks(), 100)); |
139 | 107 |
140 base::TimeDelta rtt = NetworkQualityEstimator::InvalidRTT(); | 108 base::TimeDelta rtt = NetworkQualityEstimator::InvalidRTT(); |
141 int32_t kbps = NetworkQualityEstimator::kInvalidThroughput; | 109 int32_t kbps = NetworkQualityEstimator::kInvalidThroughput; |
142 EXPECT_TRUE(estimator.GetRTTEstimate(&rtt)); | 110 EXPECT_TRUE(estimator.GetRTTEstimate(&rtt)); |
143 EXPECT_TRUE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); | 111 EXPECT_TRUE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); |
144 EXPECT_NE(NetworkQualityEstimator::InvalidRTT(), rtt); | 112 EXPECT_NE(NetworkQualityEstimator::InvalidRTT(), rtt); |
145 EXPECT_NE(NetworkQualityEstimator::kInvalidThroughput, kbps); | 113 EXPECT_NE(NetworkQualityEstimator::kInvalidThroughput, kbps); |
146 | 114 |
147 EXPECT_NEAR( | 115 EXPECT_NEAR( |
148 rtt.InMilliseconds(), | 116 rtt.InMilliseconds(), |
149 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100).InMilliseconds(), | 117 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100).InMilliseconds(), |
150 1); | 118 1); |
151 | 119 |
152 // Check UMA histograms. | 120 // Check UMA histograms. |
153 histogram_tester.ExpectTotalCount("NQE.PeakKbps.Unknown", 0); | 121 histogram_tester.ExpectTotalCount("NQE.PeakKbps.Unknown", 0); |
154 histogram_tester.ExpectTotalCount("NQE.FastestRTT.Unknown", 0); | 122 histogram_tester.ExpectTotalCount("NQE.FastestRTT.Unknown", 0); |
155 | 123 |
156 histogram_tester.ExpectTotalCount("NQE.RatioEstimatedToActualRTT.Unknown", 0); | 124 histogram_tester.ExpectTotalCount("NQE.RatioEstimatedToActualRTT.Unknown", 0); |
157 | 125 |
158 scoped_ptr<URLRequest> request2(context.CreateRequest( | 126 estimator.NotifyHeadersReceived(*request); |
159 estimator.GetEchoURL(), DEFAULT_PRIORITY, &test_delegate)); | 127 estimator.NotifyRequestCompleted(*request); |
160 request2->SetLoadFlags(request2->load_flags() | LOAD_MAIN_FRAME); | |
161 request2->Start(); | |
162 base::RunLoop().Run(); | |
163 | |
164 histogram_tester.ExpectTotalCount("NQE.RTTObservations.Unknown", 1); | 128 histogram_tester.ExpectTotalCount("NQE.RTTObservations.Unknown", 1); |
165 estimator.SimulateNetworkChangeTo( | 129 estimator.SimulateNetworkChangeTo( |
166 NetworkChangeNotifier::ConnectionType::CONNECTION_WIFI, "test-1"); | 130 NetworkChangeNotifier::ConnectionType::CONNECTION_WIFI, "test-1"); |
167 histogram_tester.ExpectTotalCount("NQE.PeakKbps.Unknown", 1); | 131 histogram_tester.ExpectTotalCount("NQE.PeakKbps.Unknown", 1); |
168 histogram_tester.ExpectTotalCount("NQE.FastestRTT.Unknown", 1); | 132 histogram_tester.ExpectTotalCount("NQE.FastestRTT.Unknown", 1); |
169 | 133 |
170 histogram_tester.ExpectTotalCount("NQE.RatioMedianRTT.WiFi", 0); | 134 histogram_tester.ExpectTotalCount("NQE.RatioMedianRTT.WiFi", 0); |
171 | 135 |
172 histogram_tester.ExpectTotalCount("NQE.RTT.Percentile0.Unknown", 1); | 136 histogram_tester.ExpectTotalCount("NQE.RTT.Percentile0.Unknown", 1); |
173 histogram_tester.ExpectTotalCount("NQE.RTT.Percentile10.Unknown", 1); | 137 histogram_tester.ExpectTotalCount("NQE.RTT.Percentile10.Unknown", 1); |
(...skipping 21 matching lines...) Expand all Loading... |
195 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); | 159 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); |
196 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, | 160 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, |
197 estimator.GetDownlinkThroughputKbpsEstimateInternal( | 161 estimator.GetDownlinkThroughputKbpsEstimateInternal( |
198 base::TimeTicks(), 100)); | 162 base::TimeTicks(), 100)); |
199 | 163 |
200 EXPECT_FALSE(estimator.GetRTTEstimate(&rtt)); | 164 EXPECT_FALSE(estimator.GetRTTEstimate(&rtt)); |
201 EXPECT_FALSE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); | 165 EXPECT_FALSE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); |
202 } | 166 } |
203 | 167 |
204 TEST(NetworkQualityEstimatorTest, StoreObservations) { | 168 TEST(NetworkQualityEstimatorTest, StoreObservations) { |
| 169 net::test_server::EmbeddedTestServer embedded_test_server; |
| 170 embedded_test_server.ServeFilesFromDirectory( |
| 171 base::FilePath(FILE_PATH_LITERAL("net/data/url_request_unittest"))); |
| 172 ASSERT_TRUE(embedded_test_server.InitializeAndWaitUntilReady()); |
| 173 |
205 std::map<std::string, std::string> variation_params; | 174 std::map<std::string, std::string> variation_params; |
206 TestNetworkQualityEstimator estimator(variation_params); | 175 TestNetworkQualityEstimator estimator(variation_params); |
207 | |
208 TestDelegate test_delegate; | 176 TestDelegate test_delegate; |
209 TestURLRequestContext context(true); | 177 TestURLRequestContext context(false); |
210 context.set_network_quality_estimator(&estimator); | |
211 context.Init(); | |
212 | 178 |
213 // Push 10 more observations than the maximum buffer size. | 179 // Push 10 more observations than the maximum buffer size. |
214 for (size_t i = 0; i < estimator.kMaximumObservationsBufferSize + 10U; ++i) { | 180 for (size_t i = 0; i < estimator.kMaximumObservationsBufferSize + 10U; ++i) { |
215 scoped_ptr<URLRequest> request(context.CreateRequest( | 181 scoped_ptr<URLRequest> request( |
216 estimator.GetEchoURL(), DEFAULT_PRIORITY, &test_delegate)); | 182 context.CreateRequest(embedded_test_server.GetURL("/echo.html"), |
| 183 DEFAULT_PRIORITY, &test_delegate)); |
217 request->Start(); | 184 request->Start(); |
218 base::RunLoop().Run(); | 185 base::RunLoop().Run(); |
| 186 |
| 187 estimator.NotifyHeadersReceived(*request); |
| 188 estimator.NotifyRequestCompleted(*request); |
219 } | 189 } |
220 | 190 |
221 EXPECT_EQ(static_cast<size_t>( | 191 EXPECT_EQ(static_cast<size_t>( |
222 NetworkQualityEstimator::kMaximumObservationsBufferSize), | 192 NetworkQualityEstimator::kMaximumObservationsBufferSize), |
223 estimator.downstream_throughput_kbps_observations_.Size()); | 193 estimator.downstream_throughput_kbps_observations_.Size()); |
224 EXPECT_EQ(static_cast<size_t>( | 194 EXPECT_EQ(static_cast<size_t>( |
225 NetworkQualityEstimator::kMaximumObservationsBufferSize), | 195 NetworkQualityEstimator::kMaximumObservationsBufferSize), |
226 estimator.rtt_msec_observations_.Size()); | 196 estimator.rtt_msec_observations_.Size()); |
227 | 197 |
228 // Verify that the stored observations are cleared on network change. | 198 // Verify that the stored observations are cleared on network change. |
229 estimator.SimulateNetworkChangeTo( | 199 estimator.SimulateNetworkChangeTo( |
230 NetworkChangeNotifier::ConnectionType::CONNECTION_WIFI, "test-2"); | 200 NetworkChangeNotifier::ConnectionType::CONNECTION_WIFI, "test-2"); |
231 EXPECT_EQ(0U, estimator.downstream_throughput_kbps_observations_.Size()); | 201 EXPECT_EQ(0U, estimator.downstream_throughput_kbps_observations_.Size()); |
232 EXPECT_EQ(0U, estimator.rtt_msec_observations_.Size()); | 202 EXPECT_EQ(0U, estimator.rtt_msec_observations_.Size()); |
| 203 |
| 204 scoped_ptr<URLRequest> request( |
| 205 context.CreateRequest(embedded_test_server.GetURL("/echo.html"), |
| 206 DEFAULT_PRIORITY, &test_delegate)); |
233 } | 207 } |
234 | 208 |
235 // Verifies that the percentiles are correctly computed. All observations have | 209 // Verifies that the percentiles are correctly computed. All observations have |
236 // the same timestamp. Kbps percentiles must be in decreasing order. RTT | 210 // the same timestamp. Kbps percentiles must be in decreasing order. RTT |
237 // percentiles must be in increasing order. | 211 // percentiles must be in increasing order. |
238 TEST(NetworkQualityEstimatorTest, PercentileSameTimestamps) { | 212 TEST(NetworkQualityEstimatorTest, PercentileSameTimestamps) { |
239 std::map<std::string, std::string> variation_params; | 213 std::map<std::string, std::string> variation_params; |
240 TestNetworkQualityEstimator estimator(variation_params); | 214 TestNetworkQualityEstimator estimator(variation_params); |
241 base::TimeTicks now = base::TimeTicks::Now(); | 215 base::TimeTicks now = base::TimeTicks::Now(); |
242 | 216 |
(...skipping 92 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
335 base::TimeTicks::Now() + base::TimeDelta::FromMinutes(10), 50)); | 309 base::TimeTicks::Now() + base::TimeDelta::FromMinutes(10), 50)); |
336 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, | 310 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, |
337 estimator.GetDownlinkThroughputKbpsEstimateInternal( | 311 estimator.GetDownlinkThroughputKbpsEstimateInternal( |
338 base::TimeTicks::Now() + base::TimeDelta::FromMinutes(10), 50)); | 312 base::TimeTicks::Now() + base::TimeDelta::FromMinutes(10), 50)); |
339 } | 313 } |
340 | 314 |
341 // This test notifies NetworkQualityEstimator of received data. Next, | 315 // This test notifies NetworkQualityEstimator of received data. Next, |
342 // throughput and RTT percentiles are checked for correctness by doing simple | 316 // throughput and RTT percentiles are checked for correctness by doing simple |
343 // verifications. | 317 // verifications. |
344 TEST(NetworkQualityEstimatorTest, ComputedPercentiles) { | 318 TEST(NetworkQualityEstimatorTest, ComputedPercentiles) { |
| 319 net::test_server::EmbeddedTestServer embedded_test_server; |
| 320 embedded_test_server.ServeFilesFromDirectory( |
| 321 base::FilePath(FILE_PATH_LITERAL("net/data/url_request_unittest"))); |
| 322 ASSERT_TRUE(embedded_test_server.InitializeAndWaitUntilReady()); |
| 323 |
345 std::map<std::string, std::string> variation_params; | 324 std::map<std::string, std::string> variation_params; |
346 TestNetworkQualityEstimator estimator(variation_params); | 325 TestNetworkQualityEstimator estimator(variation_params); |
347 | 326 |
348 EXPECT_EQ(NetworkQualityEstimator::InvalidRTT(), | 327 EXPECT_EQ(NetworkQualityEstimator::InvalidRTT(), |
349 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); | 328 estimator.GetRTTEstimateInternal(base::TimeTicks(), 100)); |
350 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, | 329 EXPECT_EQ(NetworkQualityEstimator::kInvalidThroughput, |
351 estimator.GetDownlinkThroughputKbpsEstimateInternal( | 330 estimator.GetDownlinkThroughputKbpsEstimateInternal( |
352 base::TimeTicks(), 100)); | 331 base::TimeTicks(), 100)); |
353 | 332 |
354 TestDelegate test_delegate; | 333 TestDelegate test_delegate; |
355 TestURLRequestContext context(true); | 334 TestURLRequestContext context(false); |
356 context.set_network_quality_estimator(&estimator); | |
357 context.Init(); | |
358 | 335 |
359 // Number of observations are more than the maximum buffer size. | 336 // Number of observations are more than the maximum buffer size. |
360 for (size_t i = 0; i < estimator.kMaximumObservationsBufferSize + 100U; ++i) { | 337 for (size_t i = 0; i < estimator.kMaximumObservationsBufferSize + 100U; ++i) { |
361 scoped_ptr<URLRequest> request(context.CreateRequest( | 338 scoped_ptr<URLRequest> request( |
362 estimator.GetEchoURL(), DEFAULT_PRIORITY, &test_delegate)); | 339 context.CreateRequest(embedded_test_server.GetURL("/echo.html"), |
| 340 DEFAULT_PRIORITY, &test_delegate)); |
363 request->Start(); | 341 request->Start(); |
364 base::RunLoop().Run(); | 342 base::RunLoop().Run(); |
| 343 |
| 344 // Use different number of bytes to create variation. |
| 345 estimator.NotifyHeadersReceived(*request); |
| 346 estimator.NotifyRequestCompleted(*request); |
365 } | 347 } |
366 | 348 |
367 // Verify the percentiles through simple tests. | 349 // Verify the percentiles through simple tests. |
368 for (int i = 0; i <= 100; ++i) { | 350 for (int i = 0; i <= 100; ++i) { |
369 EXPECT_GT(estimator.GetDownlinkThroughputKbpsEstimateInternal( | 351 EXPECT_GT(estimator.GetDownlinkThroughputKbpsEstimateInternal( |
370 base::TimeTicks(), i), | 352 base::TimeTicks(), i), |
371 0); | 353 0); |
372 EXPECT_LT(estimator.GetRTTEstimateInternal(base::TimeTicks(), i), | 354 EXPECT_LT(estimator.GetRTTEstimateInternal(base::TimeTicks(), i), |
373 base::TimeDelta::Max()); | 355 base::TimeDelta::Max()); |
374 | 356 |
(...skipping 290 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
665 EXPECT_EQ(100, rtt.InMilliseconds()); | 647 EXPECT_EQ(100, rtt.InMilliseconds()); |
666 | 648 |
667 int32_t downstream_throughput_kbps; | 649 int32_t downstream_throughput_kbps; |
668 EXPECT_FALSE(estimator.GetRecentMedianDownlinkThroughputKbps( | 650 EXPECT_FALSE(estimator.GetRecentMedianDownlinkThroughputKbps( |
669 now + base::TimeDelta::FromSeconds(10), &downstream_throughput_kbps)); | 651 now + base::TimeDelta::FromSeconds(10), &downstream_throughput_kbps)); |
670 EXPECT_TRUE(estimator.GetRecentMedianDownlinkThroughputKbps( | 652 EXPECT_TRUE(estimator.GetRecentMedianDownlinkThroughputKbps( |
671 now, &downstream_throughput_kbps)); | 653 now, &downstream_throughput_kbps)); |
672 EXPECT_EQ(100, downstream_throughput_kbps); | 654 EXPECT_EQ(100, downstream_throughput_kbps); |
673 } | 655 } |
674 | 656 |
675 // An external estimate provider that does not have a valid RTT or throughput | |
676 // estimate. | |
677 class InvalidExternalEstimateProvider : public ExternalEstimateProvider { | |
678 public: | |
679 InvalidExternalEstimateProvider() : get_rtt_count_(0) {} | |
680 ~InvalidExternalEstimateProvider() override {} | |
681 | |
682 // ExternalEstimateProvider implementation: | |
683 bool GetRTT(base::TimeDelta* rtt) const override { | |
684 DCHECK(rtt); | |
685 get_rtt_count_++; | |
686 return false; | |
687 } | |
688 | |
689 // ExternalEstimateProvider implementation: | |
690 bool GetDownstreamThroughputKbps( | |
691 int32_t* downstream_throughput_kbps) const override { | |
692 DCHECK(downstream_throughput_kbps); | |
693 return false; | |
694 } | |
695 | |
696 // ExternalEstimateProvider implementation: | |
697 bool GetUpstreamThroughputKbps( | |
698 int32_t* upstream_throughput_kbps) const override { | |
699 // NetworkQualityEstimator does not support upstream throughput. | |
700 ADD_FAILURE(); | |
701 return false; | |
702 } | |
703 | |
704 // ExternalEstimateProvider implementation: | |
705 bool GetTimeSinceLastUpdate( | |
706 base::TimeDelta* time_since_last_update) const override { | |
707 *time_since_last_update = base::TimeDelta::FromMilliseconds(1); | |
708 return true; | |
709 } | |
710 | |
711 // ExternalEstimateProvider implementation: | |
712 void SetUpdatedEstimateDelegate(UpdatedEstimateDelegate* delegate) override {} | |
713 | |
714 // ExternalEstimateProvider implementation: | |
715 void Update() const override {} | |
716 | |
717 size_t get_rtt_count() const { return get_rtt_count_; } | |
718 | |
719 private: | |
720 // Keeps track of number of times different functions were called. | |
721 mutable size_t get_rtt_count_; | |
722 | |
723 DISALLOW_COPY_AND_ASSIGN(InvalidExternalEstimateProvider); | |
724 }; | |
725 | |
726 // Tests if the RTT value from external estimate provider is discarded if the | |
727 // external estimate provider is invalid. | |
728 TEST(NetworkQualityEstimatorTest, InvalidExternalEstimateProvider) { | |
729 InvalidExternalEstimateProvider* invalid_external_estimate_provider = | |
730 new InvalidExternalEstimateProvider(); | |
731 scoped_ptr<ExternalEstimateProvider> external_estimate_provider( | |
732 invalid_external_estimate_provider); | |
733 | |
734 TestNetworkQualityEstimator estimator(std::map<std::string, std::string>(), | |
735 external_estimate_provider.Pass()); | |
736 | |
737 base::TimeDelta rtt; | |
738 int32_t kbps; | |
739 EXPECT_EQ(1U, invalid_external_estimate_provider->get_rtt_count()); | |
740 EXPECT_FALSE(estimator.GetRTTEstimate(&rtt)); | |
741 EXPECT_FALSE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); | |
742 } | |
743 | |
744 class TestExternalEstimateProvider : public ExternalEstimateProvider { | |
745 public: | |
746 TestExternalEstimateProvider(base::TimeDelta rtt, | |
747 int32_t downstream_throughput_kbps) | |
748 : rtt_(rtt), | |
749 downstream_throughput_kbps_(downstream_throughput_kbps), | |
750 time_since_last_update_(base::TimeDelta::FromSeconds(1)), | |
751 get_time_since_last_update_count_(0), | |
752 get_rtt_count_(0), | |
753 get_downstream_throughput_kbps_count_(0), | |
754 update_count_(0) {} | |
755 ~TestExternalEstimateProvider() override {} | |
756 | |
757 // ExternalEstimateProvider implementation: | |
758 bool GetRTT(base::TimeDelta* rtt) const override { | |
759 *rtt = rtt_; | |
760 get_rtt_count_++; | |
761 return true; | |
762 } | |
763 | |
764 // ExternalEstimateProvider implementation: | |
765 bool GetDownstreamThroughputKbps( | |
766 int32_t* downstream_throughput_kbps) const override { | |
767 *downstream_throughput_kbps = downstream_throughput_kbps_; | |
768 get_downstream_throughput_kbps_count_++; | |
769 return true; | |
770 } | |
771 | |
772 // ExternalEstimateProvider implementation: | |
773 bool GetUpstreamThroughputKbps( | |
774 int32_t* upstream_throughput_kbps) const override { | |
775 // NetworkQualityEstimator does not support upstream throughput. | |
776 ADD_FAILURE(); | |
777 return false; | |
778 } | |
779 | |
780 // ExternalEstimateProvider implementation: | |
781 bool GetTimeSinceLastUpdate( | |
782 base::TimeDelta* time_since_last_update) const override { | |
783 *time_since_last_update = time_since_last_update_; | |
784 get_time_since_last_update_count_++; | |
785 return true; | |
786 } | |
787 | |
788 // ExternalEstimateProvider implementation: | |
789 void SetUpdatedEstimateDelegate(UpdatedEstimateDelegate* delegate) override {} | |
790 | |
791 // ExternalEstimateProvider implementation: | |
792 void Update() const override { update_count_++; } | |
793 | |
794 void set_time_since_last_update(base::TimeDelta time_since_last_update) { | |
795 time_since_last_update_ = time_since_last_update; | |
796 } | |
797 | |
798 size_t get_time_since_last_update_count() const { | |
799 return get_time_since_last_update_count_; | |
800 } | |
801 size_t get_rtt_count() const { return get_rtt_count_; } | |
802 size_t get_downstream_throughput_kbps_count() const { | |
803 return get_downstream_throughput_kbps_count_; | |
804 } | |
805 size_t update_count() const { return update_count_; } | |
806 | |
807 private: | |
808 // RTT and downstream throughput estimates. | |
809 const base::TimeDelta rtt_; | |
810 const int32_t downstream_throughput_kbps_; | |
811 | |
812 base::TimeDelta time_since_last_update_; | |
813 | |
814 // Keeps track of number of times different functions were called. | |
815 mutable size_t get_time_since_last_update_count_; | |
816 mutable size_t get_rtt_count_; | |
817 mutable size_t get_downstream_throughput_kbps_count_; | |
818 mutable size_t update_count_; | |
819 | |
820 DISALLOW_COPY_AND_ASSIGN(TestExternalEstimateProvider); | |
821 }; | |
822 | |
823 // Tests if the external estimate provider is called in the constructor and | |
824 // on network change notification. | |
825 TEST(NetworkQualityEstimatorTest, TestExternalEstimateProvider) { | |
826 TestExternalEstimateProvider* test_external_estimate_provider = | |
827 new TestExternalEstimateProvider(base::TimeDelta::FromMilliseconds(1), | |
828 100); | |
829 scoped_ptr<ExternalEstimateProvider> external_estimate_provider( | |
830 test_external_estimate_provider); | |
831 std::map<std::string, std::string> variation_params; | |
832 TestNetworkQualityEstimator estimator(variation_params, | |
833 external_estimate_provider.Pass()); | |
834 | |
835 base::TimeDelta rtt; | |
836 int32_t kbps; | |
837 EXPECT_TRUE(estimator.GetRTTEstimate(&rtt)); | |
838 EXPECT_TRUE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); | |
839 | |
840 EXPECT_EQ( | |
841 1U, test_external_estimate_provider->get_time_since_last_update_count()); | |
842 EXPECT_EQ(1U, test_external_estimate_provider->get_rtt_count()); | |
843 EXPECT_EQ( | |
844 1U, | |
845 test_external_estimate_provider->get_downstream_throughput_kbps_count()); | |
846 | |
847 // Change network type to WiFi. Number of queries to External estimate | |
848 // provider must increment. | |
849 estimator.SimulateNetworkChangeTo( | |
850 NetworkChangeNotifier::ConnectionType::CONNECTION_WIFI, "test-1"); | |
851 EXPECT_TRUE(estimator.GetRTTEstimate(&rtt)); | |
852 EXPECT_TRUE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); | |
853 EXPECT_EQ( | |
854 2U, test_external_estimate_provider->get_time_since_last_update_count()); | |
855 EXPECT_EQ(2U, test_external_estimate_provider->get_rtt_count()); | |
856 EXPECT_EQ( | |
857 2U, | |
858 test_external_estimate_provider->get_downstream_throughput_kbps_count()); | |
859 | |
860 // Change network type to 2G. Number of queries to External estimate provider | |
861 // must increment. | |
862 estimator.SimulateNetworkChangeTo( | |
863 NetworkChangeNotifier::ConnectionType::CONNECTION_2G, "test-1"); | |
864 EXPECT_EQ( | |
865 3U, test_external_estimate_provider->get_time_since_last_update_count()); | |
866 EXPECT_EQ(3U, test_external_estimate_provider->get_rtt_count()); | |
867 EXPECT_EQ( | |
868 3U, | |
869 test_external_estimate_provider->get_downstream_throughput_kbps_count()); | |
870 | |
871 // Set the external estimate as old. Network Quality estimator should request | |
872 // an update on connection type change. | |
873 EXPECT_EQ(0U, test_external_estimate_provider->update_count()); | |
874 test_external_estimate_provider->set_time_since_last_update( | |
875 base::TimeDelta::Max()); | |
876 | |
877 estimator.SimulateNetworkChangeTo( | |
878 NetworkChangeNotifier::ConnectionType::CONNECTION_2G, "test-2"); | |
879 EXPECT_EQ( | |
880 4U, test_external_estimate_provider->get_time_since_last_update_count()); | |
881 EXPECT_EQ(3U, test_external_estimate_provider->get_rtt_count()); | |
882 EXPECT_EQ( | |
883 3U, | |
884 test_external_estimate_provider->get_downstream_throughput_kbps_count()); | |
885 EXPECT_EQ(1U, test_external_estimate_provider->update_count()); | |
886 | |
887 // Estimates are unavailable because external estimate provider never | |
888 // notifies network quality estimator of the updated estimates. | |
889 EXPECT_FALSE(estimator.GetRTTEstimate(&rtt)); | |
890 EXPECT_FALSE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); | |
891 } | |
892 | |
893 // Tests if the estimate from the external estimate provider is merged with the | |
894 // observations collected from the HTTP requests. | |
895 TEST(NetworkQualityEstimatorTest, TestExternalEstimateProviderMergeEstimates) { | |
896 const base::TimeDelta external_estimate_provider_rtt = | |
897 base::TimeDelta::FromMilliseconds(1); | |
898 const int32_t external_estimate_provider_downstream_throughput = 100; | |
899 TestExternalEstimateProvider* test_external_estimate_provider = | |
900 new TestExternalEstimateProvider( | |
901 external_estimate_provider_rtt, | |
902 external_estimate_provider_downstream_throughput); | |
903 scoped_ptr<ExternalEstimateProvider> external_estimate_provider( | |
904 test_external_estimate_provider); | |
905 | |
906 std::map<std::string, std::string> variation_params; | |
907 TestNetworkQualityEstimator estimator(variation_params, | |
908 external_estimate_provider.Pass()); | |
909 | |
910 base::TimeDelta rtt; | |
911 // Estimate provided by network quality estimator should match the estimate | |
912 // provided by external estimate provider. | |
913 EXPECT_TRUE(estimator.GetRTTEstimate(&rtt)); | |
914 EXPECT_EQ(external_estimate_provider_rtt, rtt); | |
915 | |
916 int32_t kbps; | |
917 EXPECT_TRUE(estimator.GetDownlinkThroughputKbpsEstimate(&kbps)); | |
918 EXPECT_EQ(external_estimate_provider_downstream_throughput, kbps); | |
919 | |
920 EXPECT_EQ(1U, estimator.rtt_msec_observations_.Size()); | |
921 EXPECT_EQ(1U, estimator.downstream_throughput_kbps_observations_.Size()); | |
922 | |
923 TestDelegate test_delegate; | |
924 TestURLRequestContext context(true); | |
925 context.set_network_quality_estimator(&estimator); | |
926 context.Init(); | |
927 | |
928 scoped_ptr<URLRequest> request(context.CreateRequest( | |
929 estimator.GetEchoURL(), DEFAULT_PRIORITY, &test_delegate)); | |
930 request->Start(); | |
931 base::RunLoop().Run(); | |
932 | |
933 EXPECT_EQ(2U, estimator.rtt_msec_observations_.Size()); | |
934 EXPECT_EQ(2U, estimator.downstream_throughput_kbps_observations_.Size()); | |
935 } | |
936 | |
937 } // namespace net | 657 } // namespace net |
OLD | NEW |