| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 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/url_request/url_request_throttler_manager.h" | 5 #include "net/url_request/url_request_throttler_manager.h" |
| 6 | 6 |
| 7 #include "base/memory/scoped_ptr.h" | 7 #include "base/memory/scoped_ptr.h" |
| 8 #include "base/metrics/histogram_samples.h" | 8 #include "base/metrics/histogram_samples.h" |
| 9 #include "base/pickle.h" | 9 #include "base/pickle.h" |
| 10 #include "base/stl_util.h" | 10 #include "base/stl_util.h" |
| 11 #include "base/strings/string_number_conversions.h" | 11 #include "base/strings/string_number_conversions.h" |
| 12 #include "base/strings/stringprintf.h" | 12 #include "base/strings/stringprintf.h" |
| 13 #include "base/test/histogram_tester.h" | 13 #include "base/test/histogram_tester.h" |
| 14 #include "base/time/time.h" | 14 #include "base/time/time.h" |
| 15 #include "net/base/load_flags.h" | 15 #include "net/base/load_flags.h" |
| 16 #include "net/base/request_priority.h" | 16 #include "net/base/request_priority.h" |
| 17 #include "net/base/test_completion_callback.h" | 17 #include "net/base/test_completion_callback.h" |
| 18 #include "net/url_request/url_request.h" |
| 18 #include "net/url_request/url_request_context.h" | 19 #include "net/url_request/url_request_context.h" |
| 19 #include "net/url_request/url_request_test_util.h" | 20 #include "net/url_request/url_request_test_util.h" |
| 20 #include "net/url_request/url_request_throttler_header_interface.h" | 21 #include "net/url_request/url_request_throttler_header_interface.h" |
| 21 #include "net/url_request/url_request_throttler_test_support.h" | 22 #include "net/url_request/url_request_throttler_test_support.h" |
| 22 #include "testing/gtest/include/gtest/gtest.h" | 23 #include "testing/gtest/include/gtest/gtest.h" |
| 23 | 24 |
| 24 using base::TimeDelta; | 25 using base::TimeDelta; |
| 25 using base::TimeTicks; | 26 using base::TimeTicks; |
| 26 | 27 |
| 27 namespace net { | 28 namespace net { |
| (...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 163 GURL url; | 164 GURL url; |
| 164 std::string result; | 165 std::string result; |
| 165 int line; | 166 int line; |
| 166 }; | 167 }; |
| 167 | 168 |
| 168 } // namespace | 169 } // namespace |
| 169 | 170 |
| 170 class URLRequestThrottlerEntryTest : public testing::Test { | 171 class URLRequestThrottlerEntryTest : public testing::Test { |
| 171 protected: | 172 protected: |
| 172 URLRequestThrottlerEntryTest() | 173 URLRequestThrottlerEntryTest() |
| 173 : request_(GURL(), DEFAULT_PRIORITY, NULL, &context_) {} | 174 : request_(context_.CreateRequest(GURL(), DEFAULT_PRIORITY, NULL, NULL)) { |
| 175 } |
| 174 | 176 |
| 175 virtual void SetUp(); | 177 virtual void SetUp(); |
| 176 | 178 |
| 177 TimeTicks now_; | 179 TimeTicks now_; |
| 178 MockURLRequestThrottlerManager manager_; // Dummy object, not used. | 180 MockURLRequestThrottlerManager manager_; // Dummy object, not used. |
| 179 scoped_refptr<MockURLRequestThrottlerEntry> entry_; | 181 scoped_refptr<MockURLRequestThrottlerEntry> entry_; |
| 180 | 182 |
| 181 TestURLRequestContext context_; | 183 TestURLRequestContext context_; |
| 182 TestURLRequest request_; | 184 scoped_ptr<URLRequest> request_; |
| 183 }; | 185 }; |
| 184 | 186 |
| 185 void URLRequestThrottlerEntryTest::SetUp() { | 187 void URLRequestThrottlerEntryTest::SetUp() { |
| 186 request_.SetLoadFlags(0); | 188 request_->SetLoadFlags(0); |
| 187 | 189 |
| 188 now_ = TimeTicks::Now(); | 190 now_ = TimeTicks::Now(); |
| 189 entry_ = new MockURLRequestThrottlerEntry(&manager_); | 191 entry_ = new MockURLRequestThrottlerEntry(&manager_); |
| 190 entry_->ResetToBlank(now_); | 192 entry_->ResetToBlank(now_); |
| 191 } | 193 } |
| 192 | 194 |
| 193 std::ostream& operator<<(std::ostream& out, const base::TimeTicks& time) { | 195 std::ostream& operator<<(std::ostream& out, const base::TimeTicks& time) { |
| 194 return out << time.ToInternalValue(); | 196 return out << time.ToInternalValue(); |
| 195 } | 197 } |
| 196 | 198 |
| 197 TEST_F(URLRequestThrottlerEntryTest, CanThrottleRequest) { | 199 TEST_F(URLRequestThrottlerEntryTest, CanThrottleRequest) { |
| 198 TestNetworkDelegate d; | 200 TestNetworkDelegate d; |
| 199 context_.set_network_delegate(&d); | 201 context_.set_network_delegate(&d); |
| 200 entry_->set_exponential_backoff_release_time( | 202 entry_->set_exponential_backoff_release_time( |
| 201 entry_->fake_time_now_ + TimeDelta::FromMilliseconds(1)); | 203 entry_->fake_time_now_ + TimeDelta::FromMilliseconds(1)); |
| 202 | 204 |
| 203 d.set_can_throttle_requests(false); | 205 d.set_can_throttle_requests(false); |
| 204 EXPECT_FALSE(entry_->ShouldRejectRequest(request_, | 206 EXPECT_FALSE(entry_->ShouldRejectRequest(*request_, |
| 205 context_.network_delegate())); | 207 context_.network_delegate())); |
| 206 d.set_can_throttle_requests(true); | 208 d.set_can_throttle_requests(true); |
| 207 EXPECT_TRUE(entry_->ShouldRejectRequest(request_, | 209 EXPECT_TRUE(entry_->ShouldRejectRequest(*request_, |
| 208 context_.network_delegate())); | 210 context_.network_delegate())); |
| 209 } | 211 } |
| 210 | 212 |
| 211 TEST_F(URLRequestThrottlerEntryTest, InterfaceDuringExponentialBackoff) { | 213 TEST_F(URLRequestThrottlerEntryTest, InterfaceDuringExponentialBackoff) { |
| 212 base::HistogramTester histogram_tester; | 214 base::HistogramTester histogram_tester; |
| 213 entry_->set_exponential_backoff_release_time( | 215 entry_->set_exponential_backoff_release_time( |
| 214 entry_->fake_time_now_ + TimeDelta::FromMilliseconds(1)); | 216 entry_->fake_time_now_ + TimeDelta::FromMilliseconds(1)); |
| 215 EXPECT_TRUE(entry_->ShouldRejectRequest(request_, | 217 EXPECT_TRUE(entry_->ShouldRejectRequest(*request_, |
| 216 context_.network_delegate())); | 218 context_.network_delegate())); |
| 217 | 219 |
| 218 // Also end-to-end test the load flags exceptions. | 220 // Also end-to-end test the load flags exceptions. |
| 219 request_.SetLoadFlags(LOAD_MAYBE_USER_GESTURE); | 221 request_->SetLoadFlags(LOAD_MAYBE_USER_GESTURE); |
| 220 EXPECT_FALSE(entry_->ShouldRejectRequest(request_, | 222 EXPECT_FALSE(entry_->ShouldRejectRequest(*request_, |
| 221 context_.network_delegate())); | 223 context_.network_delegate())); |
| 222 | 224 |
| 223 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 0, 1); | 225 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 0, 1); |
| 224 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 1, 1); | 226 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 1, 1); |
| 225 } | 227 } |
| 226 | 228 |
| 227 TEST_F(URLRequestThrottlerEntryTest, InterfaceNotDuringExponentialBackoff) { | 229 TEST_F(URLRequestThrottlerEntryTest, InterfaceNotDuringExponentialBackoff) { |
| 228 base::HistogramTester histogram_tester; | 230 base::HistogramTester histogram_tester; |
| 229 entry_->set_exponential_backoff_release_time(entry_->fake_time_now_); | 231 entry_->set_exponential_backoff_release_time(entry_->fake_time_now_); |
| 230 EXPECT_FALSE(entry_->ShouldRejectRequest(request_, | 232 EXPECT_FALSE(entry_->ShouldRejectRequest(*request_, |
| 231 context_.network_delegate())); | 233 context_.network_delegate())); |
| 232 entry_->set_exponential_backoff_release_time( | 234 entry_->set_exponential_backoff_release_time( |
| 233 entry_->fake_time_now_ - TimeDelta::FromMilliseconds(1)); | 235 entry_->fake_time_now_ - TimeDelta::FromMilliseconds(1)); |
| 234 EXPECT_FALSE(entry_->ShouldRejectRequest(request_, | 236 EXPECT_FALSE(entry_->ShouldRejectRequest(*request_, |
| 235 context_.network_delegate())); | 237 context_.network_delegate())); |
| 236 | 238 |
| 237 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 0, 2); | 239 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 0, 2); |
| 238 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 1, 0); | 240 histogram_tester.ExpectBucketCount(kRequestThrottledHistogramName, 1, 0); |
| 239 } | 241 } |
| 240 | 242 |
| 241 TEST_F(URLRequestThrottlerEntryTest, InterfaceUpdateFailure) { | 243 TEST_F(URLRequestThrottlerEntryTest, InterfaceUpdateFailure) { |
| 242 MockURLRequestThrottlerHeaderAdapter failure_response(503); | 244 MockURLRequestThrottlerHeaderAdapter failure_response(503); |
| 243 entry_->UpdateWithResponse(std::string(), &failure_response); | 245 entry_->UpdateWithResponse(std::string(), &failure_response); |
| 244 EXPECT_GT(entry_->GetExponentialBackoffReleaseTime(), entry_->fake_time_now_) | 246 EXPECT_GT(entry_->GetExponentialBackoffReleaseTime(), entry_->fake_time_now_) |
| (...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 345 ASSERT_FALSE(MockURLRequestThrottlerEntry::ExplicitUserRequest(0)); | 347 ASSERT_FALSE(MockURLRequestThrottlerEntry::ExplicitUserRequest(0)); |
| 346 ASSERT_TRUE(MockURLRequestThrottlerEntry::ExplicitUserRequest( | 348 ASSERT_TRUE(MockURLRequestThrottlerEntry::ExplicitUserRequest( |
| 347 LOAD_MAYBE_USER_GESTURE)); | 349 LOAD_MAYBE_USER_GESTURE)); |
| 348 ASSERT_FALSE(MockURLRequestThrottlerEntry::ExplicitUserRequest( | 350 ASSERT_FALSE(MockURLRequestThrottlerEntry::ExplicitUserRequest( |
| 349 ~LOAD_MAYBE_USER_GESTURE)); | 351 ~LOAD_MAYBE_USER_GESTURE)); |
| 350 } | 352 } |
| 351 | 353 |
| 352 class URLRequestThrottlerManagerTest : public testing::Test { | 354 class URLRequestThrottlerManagerTest : public testing::Test { |
| 353 protected: | 355 protected: |
| 354 URLRequestThrottlerManagerTest() | 356 URLRequestThrottlerManagerTest() |
| 355 : request_(GURL(), DEFAULT_PRIORITY, NULL, &context_) {} | 357 : request_(context_.CreateRequest(GURL(), DEFAULT_PRIORITY, NULL, NULL)) { |
| 358 } |
| 356 | 359 |
| 357 virtual void SetUp() { | 360 virtual void SetUp() { |
| 358 request_.SetLoadFlags(0); | 361 request_->SetLoadFlags(0); |
| 359 } | 362 } |
| 360 | 363 |
| 361 void ExpectEntryAllowsAllOnErrorIfOptedOut( | 364 void ExpectEntryAllowsAllOnErrorIfOptedOut( |
| 362 URLRequestThrottlerEntryInterface* entry, | 365 URLRequestThrottlerEntryInterface* entry, |
| 363 bool opted_out, | 366 bool opted_out, |
| 364 const URLRequest& request) { | 367 const URLRequest& request) { |
| 365 EXPECT_FALSE(entry->ShouldRejectRequest(request, | 368 EXPECT_FALSE(entry->ShouldRejectRequest(request, |
| 366 context_.network_delegate())); | 369 context_.network_delegate())); |
| 367 MockURLRequestThrottlerHeaderAdapter failure_adapter(503); | 370 MockURLRequestThrottlerHeaderAdapter failure_adapter(503); |
| 368 for (int i = 0; i < 10; ++i) { | 371 for (int i = 0; i < 10; ++i) { |
| (...skipping 12 matching lines...) Expand all Loading... |
| 381 entry->GetExponentialBackoffReleaseTime()); | 384 entry->GetExponentialBackoffReleaseTime()); |
| 382 } else { | 385 } else { |
| 383 // As above, add 100 ms. | 386 // As above, add 100 ms. |
| 384 EXPECT_LT(TimeTicks::Now() + TimeDelta::FromMilliseconds(100), | 387 EXPECT_LT(TimeTicks::Now() + TimeDelta::FromMilliseconds(100), |
| 385 entry->GetExponentialBackoffReleaseTime()); | 388 entry->GetExponentialBackoffReleaseTime()); |
| 386 } | 389 } |
| 387 } | 390 } |
| 388 | 391 |
| 389 // context_ must be declared before request_. | 392 // context_ must be declared before request_. |
| 390 TestURLRequestContext context_; | 393 TestURLRequestContext context_; |
| 391 TestURLRequest request_; | 394 scoped_ptr<URLRequest> request_; |
| 392 }; | 395 }; |
| 393 | 396 |
| 394 TEST_F(URLRequestThrottlerManagerTest, IsUrlStandardised) { | 397 TEST_F(URLRequestThrottlerManagerTest, IsUrlStandardised) { |
| 395 MockURLRequestThrottlerManager manager; | 398 MockURLRequestThrottlerManager manager; |
| 396 GurlAndString test_values[] = { | 399 GurlAndString test_values[] = { |
| 397 GurlAndString(GURL("http://www.example.com"), | 400 GurlAndString(GURL("http://www.example.com"), |
| 398 std::string("http://www.example.com/"), | 401 std::string("http://www.example.com/"), |
| 399 __LINE__), | 402 __LINE__), |
| 400 GurlAndString(GURL("http://www.Example.com"), | 403 GurlAndString(GURL("http://www.Example.com"), |
| 401 std::string("http://www.example.com/"), | 404 std::string("http://www.example.com/"), |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 461 manager.RegisterRequestUrl(GURL("http://www.google.com/yodude")); | 464 manager.RegisterRequestUrl(GURL("http://www.google.com/yodude")); |
| 462 | 465 |
| 463 // Fake a response with the opt-out header. | 466 // Fake a response with the opt-out header. |
| 464 MockURLRequestThrottlerHeaderAdapter response_adapter( | 467 MockURLRequestThrottlerHeaderAdapter response_adapter( |
| 465 std::string(), | 468 std::string(), |
| 466 MockURLRequestThrottlerEntry::kExponentialThrottlingDisableValue, | 469 MockURLRequestThrottlerEntry::kExponentialThrottlingDisableValue, |
| 467 200); | 470 200); |
| 468 entry->UpdateWithResponse("www.google.com", &response_adapter); | 471 entry->UpdateWithResponse("www.google.com", &response_adapter); |
| 469 | 472 |
| 470 // Ensure that the same entry on error always allows everything. | 473 // Ensure that the same entry on error always allows everything. |
| 471 ExpectEntryAllowsAllOnErrorIfOptedOut(entry.get(), true, request_); | 474 ExpectEntryAllowsAllOnErrorIfOptedOut(entry.get(), true, *request_); |
| 472 | 475 |
| 473 // Ensure that a freshly created entry (for a different URL on an | 476 // Ensure that a freshly created entry (for a different URL on an |
| 474 // already opted-out host) also gets "always allow" behavior. | 477 // already opted-out host) also gets "always allow" behavior. |
| 475 scoped_refptr<URLRequestThrottlerEntryInterface> other_entry = | 478 scoped_refptr<URLRequestThrottlerEntryInterface> other_entry = |
| 476 manager.RegisterRequestUrl(GURL("http://www.google.com/bingobob")); | 479 manager.RegisterRequestUrl(GURL("http://www.google.com/bingobob")); |
| 477 ExpectEntryAllowsAllOnErrorIfOptedOut(other_entry.get(), true, request_); | 480 ExpectEntryAllowsAllOnErrorIfOptedOut(other_entry.get(), true, *request_); |
| 478 | 481 |
| 479 // Fake a response with the opt-out header incorrectly specified. | 482 // Fake a response with the opt-out header incorrectly specified. |
| 480 scoped_refptr<URLRequestThrottlerEntryInterface> no_opt_out_entry = | 483 scoped_refptr<URLRequestThrottlerEntryInterface> no_opt_out_entry = |
| 481 manager.RegisterRequestUrl(GURL("http://www.nike.com/justdoit")); | 484 manager.RegisterRequestUrl(GURL("http://www.nike.com/justdoit")); |
| 482 MockURLRequestThrottlerHeaderAdapter wrong_adapter( | 485 MockURLRequestThrottlerHeaderAdapter wrong_adapter( |
| 483 std::string(), "yesplease", 200); | 486 std::string(), "yesplease", 200); |
| 484 no_opt_out_entry->UpdateWithResponse("www.nike.com", &wrong_adapter); | 487 no_opt_out_entry->UpdateWithResponse("www.nike.com", &wrong_adapter); |
| 485 ExpectEntryAllowsAllOnErrorIfOptedOut( | 488 ExpectEntryAllowsAllOnErrorIfOptedOut( |
| 486 no_opt_out_entry.get(), false, request_); | 489 no_opt_out_entry.get(), false, *request_); |
| 487 | 490 |
| 488 // A localhost entry should always be opted out. | 491 // A localhost entry should always be opted out. |
| 489 scoped_refptr<URLRequestThrottlerEntryInterface> localhost_entry = | 492 scoped_refptr<URLRequestThrottlerEntryInterface> localhost_entry = |
| 490 manager.RegisterRequestUrl(GURL("http://localhost/hello")); | 493 manager.RegisterRequestUrl(GURL("http://localhost/hello")); |
| 491 ExpectEntryAllowsAllOnErrorIfOptedOut(localhost_entry.get(), true, request_); | 494 ExpectEntryAllowsAllOnErrorIfOptedOut(localhost_entry.get(), true, *request_); |
| 492 } | 495 } |
| 493 | 496 |
| 494 TEST_F(URLRequestThrottlerManagerTest, ClearOnNetworkChange) { | 497 TEST_F(URLRequestThrottlerManagerTest, ClearOnNetworkChange) { |
| 495 for (int i = 0; i < 3; ++i) { | 498 for (int i = 0; i < 3; ++i) { |
| 496 MockURLRequestThrottlerManager manager; | 499 MockURLRequestThrottlerManager manager; |
| 497 scoped_refptr<URLRequestThrottlerEntryInterface> entry_before = | 500 scoped_refptr<URLRequestThrottlerEntryInterface> entry_before = |
| 498 manager.RegisterRequestUrl(GURL("http://www.example.com/")); | 501 manager.RegisterRequestUrl(GURL("http://www.example.com/")); |
| 499 MockURLRequestThrottlerHeaderAdapter failure_adapter(503); | 502 MockURLRequestThrottlerHeaderAdapter failure_adapter(503); |
| 500 for (int j = 0; j < 10; ++j) { | 503 for (int j = 0; j < 10; ++j) { |
| 501 // Host doesn't really matter in this scenario so we skip it. | 504 // Host doesn't really matter in this scenario so we skip it. |
| 502 entry_before->UpdateWithResponse(std::string(), &failure_adapter); | 505 entry_before->UpdateWithResponse(std::string(), &failure_adapter); |
| 503 } | 506 } |
| 504 EXPECT_TRUE(entry_before->ShouldRejectRequest(request_, | 507 EXPECT_TRUE(entry_before->ShouldRejectRequest(*request_, |
| 505 context_.network_delegate())); | 508 context_.network_delegate())); |
| 506 | 509 |
| 507 switch (i) { | 510 switch (i) { |
| 508 case 0: | 511 case 0: |
| 509 manager.OnIPAddressChanged(); | 512 manager.OnIPAddressChanged(); |
| 510 break; | 513 break; |
| 511 case 1: | 514 case 1: |
| 512 manager.OnConnectionTypeChanged( | 515 manager.OnConnectionTypeChanged( |
| 513 NetworkChangeNotifier::CONNECTION_UNKNOWN); | 516 NetworkChangeNotifier::CONNECTION_UNKNOWN); |
| 514 break; | 517 break; |
| 515 case 2: | 518 case 2: |
| 516 manager.OnConnectionTypeChanged(NetworkChangeNotifier::CONNECTION_NONE); | 519 manager.OnConnectionTypeChanged(NetworkChangeNotifier::CONNECTION_NONE); |
| 517 break; | 520 break; |
| 518 default: | 521 default: |
| 519 FAIL(); | 522 FAIL(); |
| 520 } | 523 } |
| 521 | 524 |
| 522 scoped_refptr<URLRequestThrottlerEntryInterface> entry_after = | 525 scoped_refptr<URLRequestThrottlerEntryInterface> entry_after = |
| 523 manager.RegisterRequestUrl(GURL("http://www.example.com/")); | 526 manager.RegisterRequestUrl(GURL("http://www.example.com/")); |
| 524 EXPECT_FALSE(entry_after->ShouldRejectRequest( | 527 EXPECT_FALSE(entry_after->ShouldRejectRequest( |
| 525 request_, context_.network_delegate())); | 528 *request_, context_.network_delegate())); |
| 526 } | 529 } |
| 527 } | 530 } |
| 528 | 531 |
| 529 } // namespace net | 532 } // namespace net |
| OLD | NEW |