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 3// found in the LICENSE file. 4 5#include "content/browser/loader/resource_scheduler.h" 6 7#include "base/memory/scoped_vector.h" 8#include "base/message_loop/message_loop.h" 9#include "base/run_loop.h" 10#include "base/strings/string_number_conversions.h" 11#include "base/timer/mock_timer.h" 12#include "base/timer/timer.h" 13#include "content/browser/browser_thread_impl.h" 14#include "content/browser/loader/resource_dispatcher_host_impl.h" 15#include "content/browser/loader/resource_message_filter.h" 16#include "content/browser/loader/resource_request_info_impl.h" 17#include "content/common/resource_messages.h" 18#include "content/public/browser/resource_context.h" 19#include "content/public/browser/resource_controller.h" 20#include "content/public/browser/resource_throttle.h" 21#include "content/public/common/process_type.h" 22#include "content/public/common/resource_type.h" 23#include "content/public/test/mock_render_process_host.h" 24#include "content/public/test/test_browser_context.h" 25#include "content/test/test_web_contents.h" 26#include "net/base/host_port_pair.h" 27#include "net/base/request_priority.h" 28#include "net/http/http_server_properties_impl.h" 29#include "net/url_request/url_request.h" 30#include "net/url_request/url_request_test_util.h" 31#include "testing/gtest/include/gtest/gtest.h" 32#include "ui/events/latency_info.h" 33 34namespace content { 35 36namespace { 37 38class TestRequestFactory; 39 40const int kChildId = 30; 41const int kRouteId = 75; 42const int kChildId2 = 43; 43const int kRouteId2 = 67; 44const int kBackgroundChildId = 35; 45const int kBackgroundRouteId = 43; 46const int kBackgroundChildId2 = 54; 47const int kBackgroundRouteId2 = 82; 48 49class TestRequest : public ResourceController { 50 public: 51 TestRequest(scoped_ptr<ResourceThrottle> throttle, 52 scoped_ptr<net::URLRequest> url_request) 53 : started_(false), 54 throttle_(throttle.Pass()), 55 url_request_(url_request.Pass()) { 56 throttle_->set_controller_for_testing(this); 57 } 58 virtual ~TestRequest() {} 59 60 bool started() const { return started_; } 61 62 void Start() { 63 bool deferred = false; 64 throttle_->WillStartRequest(&deferred); 65 started_ = !deferred; 66 } 67 68 virtual void Cancel() OVERRIDE { 69 // Alert the scheduler that the request can be deleted. 70 throttle_.reset(0); 71 } 72 73 const net::URLRequest* url_request() const { return url_request_.get(); } 74 75 protected: 76 // ResourceController interface: 77 virtual void CancelAndIgnore() OVERRIDE {} 78 virtual void CancelWithError(int error_code) OVERRIDE {} 79 virtual void Resume() OVERRIDE { started_ = true; } 80 81 private: 82 bool started_; 83 scoped_ptr<ResourceThrottle> throttle_; 84 scoped_ptr<net::URLRequest> url_request_; 85}; 86 87class CancelingTestRequest : public TestRequest { 88 public: 89 CancelingTestRequest(scoped_ptr<ResourceThrottle> throttle, 90 scoped_ptr<net::URLRequest> url_request) 91 : TestRequest(throttle.Pass(), url_request.Pass()) {} 92 93 void set_request_to_cancel(scoped_ptr<TestRequest> request_to_cancel) { 94 request_to_cancel_ = request_to_cancel.Pass(); 95 } 96 97 private: 98 virtual void Resume() OVERRIDE { 99 TestRequest::Resume(); 100 request_to_cancel_.reset(); 101 } 102 103 scoped_ptr<TestRequest> request_to_cancel_; 104}; 105 106class FakeResourceContext : public ResourceContext { 107 private: 108 virtual net::HostResolver* GetHostResolver() OVERRIDE { return NULL; } 109 virtual net::URLRequestContext* GetRequestContext() OVERRIDE { return NULL; } 110}; 111 112class FakeResourceMessageFilter : public ResourceMessageFilter { 113 public: 114 FakeResourceMessageFilter(int child_id) 115 : ResourceMessageFilter( 116 child_id, 117 PROCESS_TYPE_RENDERER, 118 NULL /* appcache_service */, 119 NULL /* blob_storage_context */, 120 NULL /* file_system_context */, 121 NULL /* service_worker_context */, 122 base::Bind(&FakeResourceMessageFilter::GetContexts, 123 base::Unretained(this))) { 124 } 125 126 private: 127 virtual ~FakeResourceMessageFilter() {} 128 129 void GetContexts(const ResourceHostMsg_Request& request, 130 ResourceContext** resource_context, 131 net::URLRequestContext** request_context) { 132 *resource_context = &context_; 133 *request_context = NULL; 134 } 135 136 FakeResourceContext context_; 137}; 138 139class ResourceSchedulerTest : public testing::Test { 140 protected: 141 ResourceSchedulerTest() 142 : next_request_id_(0), 143 ui_thread_(BrowserThread::UI, &message_loop_), 144 io_thread_(BrowserThread::IO, &message_loop_), 145 mock_timer_(new base::MockTimer(true, true)) { 146 scheduler_.set_timer_for_testing(scoped_ptr<base::Timer>(mock_timer_)); 147 148 // TODO(aiolos): Remove when throttling and coalescing have both landed. 149 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 150 false /* should_coalesce */); 151 152 scheduler_.OnClientCreated(kChildId, kRouteId, true); 153 scheduler_.OnClientCreated(kBackgroundChildId, kBackgroundRouteId, false); 154 context_.set_http_server_properties(http_server_properties_.GetWeakPtr()); 155 } 156 157 virtual ~ResourceSchedulerTest() { 158 scheduler_.OnClientDeleted(kChildId, kRouteId); 159 scheduler_.OnClientDeleted(kBackgroundChildId, kBackgroundRouteId); 160 } 161 162 scoped_ptr<net::URLRequest> NewURLRequestWithChildAndRoute( 163 const char* url, 164 net::RequestPriority priority, 165 int child_id, 166 int route_id, 167 bool is_async) { 168 scoped_ptr<net::URLRequest> url_request( 169 context_.CreateRequest(GURL(url), priority, NULL, NULL)); 170 ResourceRequestInfoImpl* info = new ResourceRequestInfoImpl( 171 PROCESS_TYPE_RENDERER, // process_type 172 child_id, // child_id 173 route_id, // route_id 174 0, // origin_pid 175 ++next_request_id_, // request_id 176 MSG_ROUTING_NONE, // render_frame_id 177 false, // is_main_frame 178 false, // parent_is_main_frame 179 0, // parent_render_frame_id 180 RESOURCE_TYPE_SUB_RESOURCE, // resource_type 181 ui::PAGE_TRANSITION_LINK, // transition_type 182 false, // should_replace_current_entry 183 false, // is_download 184 false, // is_stream 185 true, // allow_download 186 false, // has_user_gesture 187 false, // enable_load_timing 188 blink::WebReferrerPolicyDefault, // referrer_policy 189 blink::WebPageVisibilityStateVisible, // visibility_state 190 NULL, // context 191 base::WeakPtr<ResourceMessageFilter>(), // filter 192 is_async); // is_async 193 info->AssociateWithRequest(url_request.get()); 194 return url_request.Pass(); 195 } 196 197 scoped_ptr<net::URLRequest> NewURLRequest(const char* url, 198 net::RequestPriority priority) { 199 return NewURLRequestWithChildAndRoute( 200 url, priority, kChildId, kRouteId, true); 201 } 202 203 TestRequest* NewRequestWithRoute(const char* url, 204 net::RequestPriority priority, 205 int route_id) { 206 return NewRequestWithChildAndRoute(url, priority, route_id, kChildId); 207 } 208 209 TestRequest* NewRequestWithChildAndRoute(const char* url, 210 net::RequestPriority priority, 211 int child_id, 212 int route_id) { 213 return GetNewTestRequest(url, priority, child_id, route_id, true); 214 } 215 216 TestRequest* NewRequest(const char* url, net::RequestPriority priority) { 217 return NewRequestWithChildAndRoute(url, priority, kChildId, kRouteId); 218 } 219 220 TestRequest* NewBackgroundRequest(const char* url, 221 net::RequestPriority priority) { 222 return NewRequestWithChildAndRoute( 223 url, priority, kBackgroundChildId, kBackgroundRouteId); 224 } 225 226 TestRequest* NewSyncRequest(const char* url, net::RequestPriority priority) { 227 return NewSyncRequestWithChildAndRoute(url, priority, kChildId, kRouteId); 228 } 229 230 TestRequest* NewBackgroundSyncRequest(const char* url, 231 net::RequestPriority priority) { 232 return NewSyncRequestWithChildAndRoute( 233 url, priority, kBackgroundChildId, kBackgroundRouteId); 234 } 235 236 TestRequest* NewSyncRequestWithChildAndRoute(const char* url, 237 net::RequestPriority priority, 238 int child_id, 239 int route_id) { 240 return GetNewTestRequest(url, priority, child_id, route_id, false); 241 } 242 243 TestRequest* GetNewTestRequest(const char* url, 244 net::RequestPriority priority, 245 int child_id, 246 int route_id, 247 bool is_async) { 248 scoped_ptr<net::URLRequest> url_request(NewURLRequestWithChildAndRoute( 249 url, priority, child_id, route_id, is_async)); 250 scoped_ptr<ResourceThrottle> throttle( 251 scheduler_.ScheduleRequest(child_id, route_id, url_request.get())); 252 TestRequest* request = new TestRequest(throttle.Pass(), url_request.Pass()); 253 request->Start(); 254 return request; 255 } 256 257 258 void ChangeRequestPriority(TestRequest* request, 259 net::RequestPriority new_priority, 260 int intra_priority = 0) { 261 scoped_refptr<FakeResourceMessageFilter> filter( 262 new FakeResourceMessageFilter(kChildId)); 263 const ResourceRequestInfoImpl* info = ResourceRequestInfoImpl::ForRequest( 264 request->url_request()); 265 const GlobalRequestID& id = info->GetGlobalRequestID(); 266 ResourceHostMsg_DidChangePriority msg(id.request_id, new_priority, 267 intra_priority); 268 rdh_.OnMessageReceived(msg, filter.get()); 269 } 270 271 void FireCoalescingTimer() { 272 EXPECT_TRUE(mock_timer_->IsRunning()); 273 mock_timer_->Fire(); 274 } 275 276 int next_request_id_; 277 base::MessageLoopForIO message_loop_; 278 BrowserThreadImpl ui_thread_; 279 BrowserThreadImpl io_thread_; 280 ResourceDispatcherHostImpl rdh_; 281 ResourceScheduler scheduler_; 282 base::MockTimer* mock_timer_; 283 net::HttpServerPropertiesImpl http_server_properties_; 284 net::TestURLRequestContext context_; 285}; 286 287TEST_F(ResourceSchedulerTest, OneIsolatedLowRequest) { 288 scoped_ptr<TestRequest> request(NewRequest("http://host/1", net::LOWEST)); 289 EXPECT_TRUE(request->started()); 290} 291 292TEST_F(ResourceSchedulerTest, OneLowLoadsUntilIdle) { 293 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 294 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 295 scoped_ptr<TestRequest> low2(NewRequest("http://host/low", net::LOWEST)); 296 EXPECT_TRUE(high->started()); 297 EXPECT_TRUE(low->started()); 298 EXPECT_FALSE(low2->started()); 299 high.reset(); 300 EXPECT_TRUE(low2->started()); 301} 302 303TEST_F(ResourceSchedulerTest, OneLowLoadsUntilBodyInserted) { 304 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 305 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 306 scoped_ptr<TestRequest> low2(NewRequest("http://host/low", net::LOWEST)); 307 EXPECT_TRUE(high->started()); 308 EXPECT_TRUE(low->started()); 309 EXPECT_FALSE(low2->started()); 310 high.reset(); 311 scheduler_.OnWillInsertBody(kChildId, kRouteId); 312 EXPECT_TRUE(low2->started()); 313} 314 315TEST_F(ResourceSchedulerTest, OneLowLoadsUntilCriticalComplete) { 316 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 317 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 318 scoped_ptr<TestRequest> low2(NewRequest("http://host/low", net::LOWEST)); 319 EXPECT_TRUE(high->started()); 320 EXPECT_TRUE(low->started()); 321 EXPECT_FALSE(low2->started()); 322 scheduler_.OnWillInsertBody(kChildId, kRouteId); 323 EXPECT_FALSE(low2->started()); 324 high.reset(); 325 EXPECT_TRUE(low2->started()); 326} 327 328TEST_F(ResourceSchedulerTest, OneLowLoadsUntilBodyInsertedExceptSpdy) { 329 http_server_properties_.SetSupportsSpdy( 330 net::HostPortPair("spdyhost", 443), true); 331 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 332 scoped_ptr<TestRequest> low_spdy( 333 NewRequest("https://spdyhost/low", net::LOWEST)); 334 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 335 scoped_ptr<TestRequest> low2(NewRequest("http://host/low", net::LOWEST)); 336 EXPECT_TRUE(high->started()); 337 EXPECT_TRUE(low_spdy->started()); 338 EXPECT_TRUE(low->started()); 339 EXPECT_FALSE(low2->started()); 340 scheduler_.OnWillInsertBody(kChildId, kRouteId); 341 high.reset(); 342 EXPECT_TRUE(low2->started()); 343} 344 345TEST_F(ResourceSchedulerTest, NavigationResetsState) { 346 scheduler_.OnWillInsertBody(kChildId, kRouteId); 347 scheduler_.OnNavigate(kChildId, kRouteId); 348 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 349 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 350 scoped_ptr<TestRequest> low2(NewRequest("http://host/low", net::LOWEST)); 351 EXPECT_TRUE(high->started()); 352 EXPECT_TRUE(low->started()); 353 EXPECT_FALSE(low2->started()); 354} 355 356TEST_F(ResourceSchedulerTest, BackgroundRequestStartsImmediately) { 357 const int route_id = 0; // Indicates a background request. 358 scoped_ptr<TestRequest> request(NewRequestWithRoute("http://host/1", 359 net::LOWEST, route_id)); 360 EXPECT_TRUE(request->started()); 361} 362 363TEST_F(ResourceSchedulerTest, StartMultipleLowRequestsWhenIdle) { 364 scoped_ptr<TestRequest> high1(NewRequest("http://host/high1", net::HIGHEST)); 365 scoped_ptr<TestRequest> high2(NewRequest("http://host/high2", net::HIGHEST)); 366 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 367 scoped_ptr<TestRequest> low2(NewRequest("http://host/low", net::LOWEST)); 368 EXPECT_TRUE(high1->started()); 369 EXPECT_TRUE(high2->started()); 370 EXPECT_TRUE(low->started()); 371 EXPECT_FALSE(low2->started()); 372 high1.reset(); 373 EXPECT_FALSE(low2->started()); 374 high2.reset(); 375 EXPECT_TRUE(low2->started()); 376} 377 378TEST_F(ResourceSchedulerTest, CancelOtherRequestsWhileResuming) { 379 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 380 scoped_ptr<TestRequest> low1(NewRequest("http://host/low1", net::LOWEST)); 381 382 scoped_ptr<net::URLRequest> url_request( 383 NewURLRequest("http://host/low2", net::LOWEST)); 384 scoped_ptr<ResourceThrottle> throttle( 385 scheduler_.ScheduleRequest(kChildId, kRouteId, url_request.get())); 386 scoped_ptr<CancelingTestRequest> low2(new CancelingTestRequest( 387 throttle.Pass(), url_request.Pass())); 388 low2->Start(); 389 390 scoped_ptr<TestRequest> low3(NewRequest("http://host/low3", net::LOWEST)); 391 low2->set_request_to_cancel(low3.Pass()); 392 scoped_ptr<TestRequest> low4(NewRequest("http://host/low4", net::LOWEST)); 393 394 EXPECT_TRUE(high->started()); 395 EXPECT_FALSE(low2->started()); 396 high.reset(); 397 EXPECT_TRUE(low1->started()); 398 EXPECT_TRUE(low2->started()); 399 EXPECT_TRUE(low4->started()); 400} 401 402TEST_F(ResourceSchedulerTest, LimitedNumberOfDelayableRequestsInFlight) { 403 // We only load low priority resources if there's a body. 404 scheduler_.OnWillInsertBody(kChildId, kRouteId); 405 406 // Throw in one high priority request to make sure that's not a factor. 407 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 408 EXPECT_TRUE(high->started()); 409 410 const int kMaxNumDelayableRequestsPerClient = 10; // Should match the .cc. 411 const int kMaxNumDelayableRequestsPerHost = 6; 412 ScopedVector<TestRequest> lows_singlehost; 413 // Queue up to the per-host limit (we subtract the current high-pri request). 414 for (int i = 0; i < kMaxNumDelayableRequestsPerHost - 1; ++i) { 415 string url = "http://host/low" + base::IntToString(i); 416 lows_singlehost.push_back(NewRequest(url.c_str(), net::LOWEST)); 417 EXPECT_TRUE(lows_singlehost[i]->started()); 418 } 419 420 scoped_ptr<TestRequest> second_last_singlehost(NewRequest("http://host/last", 421 net::LOWEST)); 422 scoped_ptr<TestRequest> last_singlehost(NewRequest("http://host/s_last", 423 net::LOWEST)); 424 425 EXPECT_FALSE(second_last_singlehost->started()); 426 high.reset(); 427 EXPECT_TRUE(second_last_singlehost->started()); 428 EXPECT_FALSE(last_singlehost->started()); 429 lows_singlehost.erase(lows_singlehost.begin()); 430 EXPECT_TRUE(last_singlehost->started()); 431 432 // Queue more requests from different hosts until we reach the total limit. 433 int expected_slots_left = 434 kMaxNumDelayableRequestsPerClient - kMaxNumDelayableRequestsPerHost; 435 EXPECT_GT(expected_slots_left, 0); 436 ScopedVector<TestRequest> lows_differenthosts; 437 for (int i = 0; i < expected_slots_left; ++i) { 438 string url = "http://host" + base::IntToString(i) + "/low"; 439 lows_differenthosts.push_back(NewRequest(url.c_str(), net::LOWEST)); 440 EXPECT_TRUE(lows_differenthosts[i]->started()); 441 } 442 443 scoped_ptr<TestRequest> last_differenthost(NewRequest("http://host_new/last", 444 net::LOWEST)); 445 EXPECT_FALSE(last_differenthost->started()); 446} 447 448TEST_F(ResourceSchedulerTest, RaisePriorityAndStart) { 449 // Dummies to enforce scheduling. 450 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 451 scoped_ptr<TestRequest> low(NewRequest("http://host/req", net::LOWEST)); 452 453 scoped_ptr<TestRequest> request(NewRequest("http://host/req", net::LOWEST)); 454 EXPECT_FALSE(request->started()); 455 456 ChangeRequestPriority(request.get(), net::HIGHEST); 457 EXPECT_TRUE(request->started()); 458} 459 460TEST_F(ResourceSchedulerTest, RaisePriorityInQueue) { 461 // Dummies to enforce scheduling. 462 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 463 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 464 465 scoped_ptr<TestRequest> request(NewRequest("http://host/req", net::IDLE)); 466 scoped_ptr<TestRequest> idle(NewRequest("http://host/idle", net::IDLE)); 467 EXPECT_FALSE(request->started()); 468 EXPECT_FALSE(idle->started()); 469 470 ChangeRequestPriority(request.get(), net::LOWEST); 471 EXPECT_FALSE(request->started()); 472 EXPECT_FALSE(idle->started()); 473 474 const int kMaxNumDelayableRequestsPerClient = 10; // Should match the .cc. 475 ScopedVector<TestRequest> lows; 476 for (int i = 0; i < kMaxNumDelayableRequestsPerClient - 1; ++i) { 477 string url = "http://host/low" + base::IntToString(i); 478 lows.push_back(NewRequest(url.c_str(), net::LOWEST)); 479 } 480 481 scheduler_.OnWillInsertBody(kChildId, kRouteId); 482 high.reset(); 483 484 EXPECT_TRUE(request->started()); 485 EXPECT_FALSE(idle->started()); 486} 487 488TEST_F(ResourceSchedulerTest, LowerPriority) { 489 // Dummies to enforce scheduling. 490 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 491 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 492 493 scoped_ptr<TestRequest> request(NewRequest("http://host/req", net::LOWEST)); 494 scoped_ptr<TestRequest> idle(NewRequest("http://host/idle", net::IDLE)); 495 EXPECT_FALSE(request->started()); 496 EXPECT_FALSE(idle->started()); 497 498 ChangeRequestPriority(request.get(), net::IDLE); 499 EXPECT_FALSE(request->started()); 500 EXPECT_FALSE(idle->started()); 501 502 const int kMaxNumDelayableRequestsPerClient = 10; // Should match the .cc. 503 // 2 fewer filler requests: 1 for the "low" dummy at the start, and 1 for the 504 // one at the end, which will be tested. 505 const int kNumFillerRequests = kMaxNumDelayableRequestsPerClient - 2; 506 ScopedVector<TestRequest> lows; 507 for (int i = 0; i < kNumFillerRequests; ++i) { 508 string url = "http://host" + base::IntToString(i) + "/low"; 509 lows.push_back(NewRequest(url.c_str(), net::LOWEST)); 510 } 511 512 scheduler_.OnWillInsertBody(kChildId, kRouteId); 513 high.reset(); 514 515 EXPECT_FALSE(request->started()); 516 EXPECT_TRUE(idle->started()); 517} 518 519TEST_F(ResourceSchedulerTest, ReprioritizedRequestGoesToBackOfQueue) { 520 // Dummies to enforce scheduling. 521 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 522 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 523 524 scoped_ptr<TestRequest> request(NewRequest("http://host/req", net::LOWEST)); 525 scoped_ptr<TestRequest> idle(NewRequest("http://host/idle", net::IDLE)); 526 EXPECT_FALSE(request->started()); 527 EXPECT_FALSE(idle->started()); 528 529 const int kMaxNumDelayableRequestsPerClient = 10; // Should match the .cc. 530 ScopedVector<TestRequest> lows; 531 for (int i = 0; i < kMaxNumDelayableRequestsPerClient; ++i) { 532 string url = "http://host/low" + base::IntToString(i); 533 lows.push_back(NewRequest(url.c_str(), net::LOWEST)); 534 } 535 536 ChangeRequestPriority(request.get(), net::IDLE); 537 EXPECT_FALSE(request->started()); 538 EXPECT_FALSE(idle->started()); 539 540 ChangeRequestPriority(request.get(), net::LOWEST); 541 EXPECT_FALSE(request->started()); 542 EXPECT_FALSE(idle->started()); 543 544 scheduler_.OnWillInsertBody(kChildId, kRouteId); 545 EXPECT_FALSE(request->started()); 546 EXPECT_FALSE(idle->started()); 547} 548 549TEST_F(ResourceSchedulerTest, HigherIntraPriorityGoesToFrontOfQueue) { 550 // Dummies to enforce scheduling. 551 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 552 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 553 554 const int kMaxNumDelayableRequestsPerClient = 10; // Should match the .cc. 555 ScopedVector<TestRequest> lows; 556 for (int i = 0; i < kMaxNumDelayableRequestsPerClient; ++i) { 557 string url = "http://host/low" + base::IntToString(i); 558 lows.push_back(NewRequest(url.c_str(), net::IDLE)); 559 } 560 561 scoped_ptr<TestRequest> request(NewRequest("http://host/req", net::IDLE)); 562 EXPECT_FALSE(request->started()); 563 564 ChangeRequestPriority(request.get(), net::IDLE, 1); 565 EXPECT_FALSE(request->started()); 566 567 scheduler_.OnWillInsertBody(kChildId, kRouteId); 568 high.reset(); 569 EXPECT_TRUE(request->started()); 570} 571 572TEST_F(ResourceSchedulerTest, NonHTTPSchedulesImmediately) { 573 // Dummies to enforce scheduling. 574 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 575 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 576 577 scoped_ptr<TestRequest> request( 578 NewRequest("chrome-extension://req", net::LOWEST)); 579 EXPECT_TRUE(request->started()); 580} 581 582TEST_F(ResourceSchedulerTest, ActiveLoadingSyncSchedulesImmediately) { 583 // TODO(aiolos): remove when throttling and coalescing have both landed 584 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 585 false /* should_coalesce */); 586 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 587 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 588 // Dummies to enforce scheduling. 589 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 590 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 591 592 scoped_ptr<TestRequest> request( 593 NewSyncRequest("http://host/req", net::LOWEST)); 594 EXPECT_TRUE(request->started()); 595} 596 597TEST_F(ResourceSchedulerTest, UnthrottledSyncSchedulesImmediately) { 598 // TODO(aiolos): remove when throttling and coalescing have both landed 599 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 600 false /* should_coalesce */); 601 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 602 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 603 scheduler_.GetClientStateForTesting(kBackgroundChildId, 604 kBackgroundRouteId)); 605 // Dummies to enforce scheduling. 606 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 607 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 608 609 scoped_ptr<TestRequest> request( 610 NewBackgroundSyncRequest("http://host/req", net::LOWEST)); 611 EXPECT_TRUE(request->started()); 612} 613 614TEST_F(ResourceSchedulerTest, SpdyProxySchedulesImmediately) { 615 scoped_ptr<TestRequest> high(NewRequest("http://host/high", net::HIGHEST)); 616 scoped_ptr<TestRequest> low(NewRequest("http://host/low", net::LOWEST)); 617 618 scoped_ptr<TestRequest> request(NewRequest("http://host/req", net::IDLE)); 619 EXPECT_FALSE(request->started()); 620 621 scheduler_.OnReceivedSpdyProxiedHttpResponse(kChildId, kRouteId); 622 EXPECT_TRUE(request->started()); 623 624 scoped_ptr<TestRequest> after(NewRequest("http://host/after", net::IDLE)); 625 EXPECT_TRUE(after->started()); 626} 627 628TEST_F(ResourceSchedulerTest, NewSpdyHostInDelayableRequests) { 629 scheduler_.OnWillInsertBody(kChildId, kRouteId); 630 const int kMaxNumDelayableRequestsPerClient = 10; // Should match the .cc. 631 632 scoped_ptr<TestRequest> low1_spdy( 633 NewRequest("http://spdyhost1:8080/low", net::LOWEST)); 634 // Cancel a request after we learn the server supports SPDY. 635 ScopedVector<TestRequest> lows; 636 for (int i = 0; i < kMaxNumDelayableRequestsPerClient - 1; ++i) { 637 string url = "http://host" + base::IntToString(i) + "/low"; 638 lows.push_back(NewRequest(url.c_str(), net::LOWEST)); 639 } 640 scoped_ptr<TestRequest> low1(NewRequest("http://host/low", net::LOWEST)); 641 EXPECT_FALSE(low1->started()); 642 http_server_properties_.SetSupportsSpdy( 643 net::HostPortPair("spdyhost1", 8080), true); 644 low1_spdy.reset(); 645 EXPECT_TRUE(low1->started()); 646 647 low1.reset(); 648 scoped_ptr<TestRequest> low2_spdy( 649 NewRequest("http://spdyhost2:8080/low", net::IDLE)); 650 // Reprioritize a request after we learn the server supports SPDY. 651 EXPECT_TRUE(low2_spdy->started()); 652 http_server_properties_.SetSupportsSpdy( 653 net::HostPortPair("spdyhost2", 8080), true); 654 ChangeRequestPriority(low2_spdy.get(), net::LOWEST); 655 scoped_ptr<TestRequest> low2(NewRequest("http://host/low", net::LOWEST)); 656 EXPECT_TRUE(low2->started()); 657} 658 659TEST_F(ResourceSchedulerTest, ThrottledClientCreation) { 660 // TODO(aiolos): remove when throttling and coalescing have both landed 661 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 662 false /* should_coalesce */); 663 EXPECT_TRUE(scheduler_.should_throttle()); 664 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 665 666 EXPECT_EQ(ResourceScheduler::THROTTLED, 667 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 668 kBackgroundRouteId2)); 669 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 670} 671 672TEST_F(ResourceSchedulerTest, ActiveClientThrottleUpdateOnLoadingChange) { 673 // TODO(aiolos): remove when throttling and coalescing have both landed 674 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 675 false /* should_coalesce */); 676 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 677 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 678 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 679 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 680 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 681 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, false); 682 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 683 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 684} 685 686TEST_F(ResourceSchedulerTest, CoalesceBackgroundClientOnLoadCompletion) { 687 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 688 true /* should_coalesce */); 689 EXPECT_EQ(ResourceScheduler::THROTTLED, 690 scheduler_.GetClientStateForTesting(kBackgroundChildId, 691 kBackgroundRouteId)); 692 scheduler_.OnLoadingStateChanged( 693 kBackgroundChildId, kBackgroundRouteId, true); 694 EXPECT_EQ(ResourceScheduler::THROTTLED, 695 scheduler_.GetClientStateForTesting(kBackgroundChildId, 696 kBackgroundRouteId)); 697 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 698 EXPECT_EQ(ResourceScheduler::COALESCED, 699 scheduler_.GetClientStateForTesting(kBackgroundChildId, 700 kBackgroundRouteId)); 701} 702 703TEST_F(ResourceSchedulerTest, UnthrottleBackgroundClientOnLoadingStarted) { 704 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 705 true /* should_coalesce */); 706 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 707 scheduler_.OnLoadingStateChanged( 708 kBackgroundChildId, kBackgroundRouteId, true); 709 EXPECT_EQ(ResourceScheduler::COALESCED, 710 scheduler_.GetClientStateForTesting(kBackgroundChildId, 711 kBackgroundRouteId)); 712 713 scheduler_.OnLoadingStateChanged( 714 kBackgroundChildId, kBackgroundRouteId, false); 715 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 716 scheduler_.GetClientStateForTesting(kBackgroundChildId, 717 kBackgroundRouteId)); 718} 719 720TEST_F(ResourceSchedulerTest, OneRequestPerThrottledClient) { 721 // TODO(aiolos): remove when throttling and coalescing have both landed 722 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 723 false /* should_coalesce */); 724 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 725 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 726 EXPECT_EQ(ResourceScheduler::THROTTLED, 727 scheduler_.GetClientStateForTesting(kBackgroundChildId, 728 kBackgroundRouteId)); 729 scoped_ptr<TestRequest> high( 730 NewBackgroundRequest("http://host/high", net::HIGHEST)); 731 scoped_ptr<TestRequest> request( 732 NewBackgroundRequest("http://host/req", net::IDLE)); 733 734 EXPECT_TRUE(high->started()); 735 EXPECT_FALSE(request->started()); 736} 737 738TEST_F(ResourceSchedulerTest, UnthrottleNewlyVisibleClient) { 739 // TODO(aiolos): remove when throttling and coalescing have both landed 740 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 741 false /* should_coalesce */); 742 EXPECT_EQ(ResourceScheduler::THROTTLED, 743 scheduler_.GetClientStateForTesting(kBackgroundChildId, 744 kBackgroundRouteId)); 745 scoped_ptr<TestRequest> high( 746 NewBackgroundRequest("http://host/high", net::HIGHEST)); 747 scoped_ptr<TestRequest> request( 748 NewBackgroundRequest("http://host/req", net::IDLE)); 749 EXPECT_FALSE(request->started()); 750 751 scheduler_.OnVisibilityChanged(kBackgroundChildId, kBackgroundRouteId, true); 752 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 753 scheduler_.GetClientStateForTesting(kBackgroundChildId, 754 kBackgroundRouteId)); 755 EXPECT_TRUE(request->started()); 756} 757 758TEST_F(ResourceSchedulerTest, UnthrottleNewlyAudibleClient) { 759 // TODO(aiolos): remove when throttling and coalescing have both landed 760 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 761 false /* should_coalesce */); 762 EXPECT_EQ(ResourceScheduler::THROTTLED, 763 scheduler_.GetClientStateForTesting(kBackgroundChildId, 764 kBackgroundRouteId)); 765 scoped_ptr<TestRequest> high( 766 NewBackgroundRequest("http://host/high", net::HIGHEST)); 767 scoped_ptr<TestRequest> request( 768 NewBackgroundRequest("http://host/req", net::IDLE)); 769 EXPECT_FALSE(request->started()); 770 771 scheduler_.OnAudibilityChanged(kBackgroundChildId, kBackgroundRouteId, true); 772 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 773 scheduler_.GetClientStateForTesting(kBackgroundChildId, 774 kBackgroundRouteId)); 775 EXPECT_TRUE(request->started()); 776} 777 778TEST_F(ResourceSchedulerTest, VisibleClientStillUnthrottledOnAudabilityChange) { 779 // TODO(aiolos): remove when throttling and coalescing have both landed 780 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 781 false /* should_coalesce */); 782 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 783 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 784 EXPECT_EQ(ResourceScheduler::THROTTLED, 785 scheduler_.GetClientStateForTesting(kBackgroundChildId, 786 kBackgroundRouteId)); 787 788 scheduler_.OnAudibilityChanged(kChildId, kRouteId, true); 789 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 790 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 791 EXPECT_EQ(ResourceScheduler::THROTTLED, 792 scheduler_.GetClientStateForTesting(kBackgroundChildId, 793 kBackgroundRouteId)); 794 795 scheduler_.OnAudibilityChanged(kChildId, kRouteId, false); 796 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 797 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 798 EXPECT_EQ(ResourceScheduler::THROTTLED, 799 scheduler_.GetClientStateForTesting(kBackgroundChildId, 800 kBackgroundRouteId)); 801} 802 803TEST_F(ResourceSchedulerTest, AudibleClientStillUnthrottledOnVisabilityChange) { 804 // TODO(aiolos): remove when throttling and coalescing have both landed 805 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 806 false /* should_coalesce */); 807 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 808 scheduler_.OnAudibilityChanged(kChildId, kRouteId, true); 809 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 810 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 811 EXPECT_EQ(ResourceScheduler::THROTTLED, 812 scheduler_.GetClientStateForTesting(kBackgroundChildId, 813 kBackgroundRouteId)); 814 815 scheduler_.OnVisibilityChanged(kChildId, kRouteId, true); 816 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 817 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 818 EXPECT_EQ(ResourceScheduler::THROTTLED, 819 scheduler_.GetClientStateForTesting(kBackgroundChildId, 820 kBackgroundRouteId)); 821 822 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 823 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 824 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 825 EXPECT_EQ(ResourceScheduler::THROTTLED, 826 scheduler_.GetClientStateForTesting(kBackgroundChildId, 827 kBackgroundRouteId)); 828} 829 830TEST_F(ResourceSchedulerTest, ThrottledClientStartsNextHighestPriorityRequest) { 831 // TODO(aiolos): remove when throttling and coalescing have both landed 832 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 833 false /* should_coalesce */); 834 scoped_ptr<TestRequest> request( 835 NewBackgroundRequest("http://host/req", net::IDLE)); 836 // Lower priority request started first to test request prioritizaton. 837 scoped_ptr<TestRequest> low( 838 NewBackgroundRequest("http://host/high", net::IDLE)); 839 scoped_ptr<TestRequest> high( 840 NewBackgroundRequest("http://host/high", net::HIGHEST)); 841 842 EXPECT_FALSE(low->started()); 843 EXPECT_FALSE(high->started()); 844 845 // request->CancelRequest(); 846 request->Cancel(); 847 EXPECT_TRUE(high->started()); 848 EXPECT_FALSE(low->started()); 849} 850 851TEST_F(ResourceSchedulerTest, ThrottledSpdyProxySchedulesImmediately) { 852 // TODO(aiolos): remove when throttling and coalescing have both landed 853 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 854 false /* should_coalesce */); 855 EXPECT_EQ(ResourceScheduler::THROTTLED, 856 scheduler_.GetClientStateForTesting(kBackgroundChildId, 857 kBackgroundRouteId)); 858 scoped_ptr<TestRequest> high( 859 NewBackgroundRequest("http://host/high", net::HIGHEST)); 860 scoped_ptr<TestRequest> request( 861 NewBackgroundRequest("http://host/req", net::IDLE)); 862 863 EXPECT_FALSE(request->started()); 864 865 scheduler_.OnReceivedSpdyProxiedHttpResponse(kBackgroundChildId, 866 kBackgroundRouteId); 867 EXPECT_TRUE(request->started()); 868 869 scoped_ptr<TestRequest> after( 870 NewBackgroundRequest("http://host/after", net::IDLE)); 871 EXPECT_TRUE(after->started()); 872} 873 874TEST_F(ResourceSchedulerTest, CoalescedClientIssuesNoRequests) { 875 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 876 true /* should_coalesce */); 877 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 878 scheduler_.OnLoadingStateChanged( 879 kBackgroundChildId, kBackgroundRouteId, true); 880 EXPECT_EQ(ResourceScheduler::COALESCED, 881 scheduler_.GetClientStateForTesting(kBackgroundChildId, 882 kBackgroundRouteId)); 883 scoped_ptr<TestRequest> high( 884 NewBackgroundRequest("http://host/high", net::HIGHEST)); 885 scoped_ptr<TestRequest> request( 886 NewBackgroundRequest("http://host/req", net::IDLE)); 887 888 EXPECT_FALSE(high->started()); 889 EXPECT_FALSE(request->started()); 890 891 scheduler_.OnReceivedSpdyProxiedHttpResponse(kBackgroundChildId, 892 kBackgroundRouteId); 893 EXPECT_FALSE(high->started()); 894 895 scoped_ptr<TestRequest> after( 896 NewBackgroundRequest("http://host/after", net::HIGHEST)); 897 EXPECT_FALSE(after->started()); 898} 899 900TEST_F(ResourceSchedulerTest, CoalescedSpdyProxyWaits) { 901 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 902 true /* should_coalesce */); 903 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 904 scheduler_.OnLoadingStateChanged( 905 kBackgroundChildId, kBackgroundRouteId, true); 906 EXPECT_EQ(ResourceScheduler::COALESCED, 907 scheduler_.GetClientStateForTesting(kBackgroundChildId, 908 kBackgroundRouteId)); 909 scoped_ptr<TestRequest> high( 910 NewBackgroundRequest("http://host/high", net::HIGHEST)); 911 scoped_ptr<TestRequest> request( 912 NewBackgroundRequest("http://host/req", net::IDLE)); 913 914 EXPECT_FALSE(request->started()); 915 916 scheduler_.OnReceivedSpdyProxiedHttpResponse(kBackgroundChildId, 917 kBackgroundRouteId); 918 EXPECT_FALSE(request->started()); 919 920 scoped_ptr<TestRequest> after( 921 NewBackgroundRequest("http://host/after", net::IDLE)); 922 EXPECT_FALSE(after->started()); 923} 924 925TEST_F(ResourceSchedulerTest, ThrottledNonHTTPSchedulesImmediately) { 926 // TODO(aiolos): remove when throttling and coalescing have both landed 927 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 928 false /* should_coalesce */); 929 // Dummies to enforce scheduling. 930 scoped_ptr<TestRequest> high( 931 NewBackgroundRequest("http://host/high", net::HIGHEST)); 932 scoped_ptr<TestRequest> low( 933 NewBackgroundRequest("http://host/low", net::LOWEST)); 934 935 scoped_ptr<TestRequest> request( 936 NewBackgroundRequest("chrome-extension://req", net::LOWEST)); 937 EXPECT_TRUE(request->started()); 938 EXPECT_FALSE(low->started()); 939} 940 941TEST_F(ResourceSchedulerTest, CoalescedNonHTTPSchedulesImmediately) { 942 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 943 true /* should_coalesce */); 944 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 945 scheduler_.OnLoadingStateChanged( 946 kBackgroundChildId, kBackgroundRouteId, true); 947 EXPECT_EQ(ResourceScheduler::COALESCED, 948 scheduler_.GetClientStateForTesting(kBackgroundChildId, 949 kBackgroundRouteId)); 950 // Dummies to enforce scheduling. 951 scoped_ptr<TestRequest> high( 952 NewBackgroundRequest("http://host/high", net::HIGHEST)); 953 scoped_ptr<TestRequest> low( 954 NewBackgroundRequest("http://host/low", net::LOWEST)); 955 956 scoped_ptr<TestRequest> request( 957 NewBackgroundRequest("chrome-extension://req", net::LOWEST)); 958 EXPECT_TRUE(request->started()); 959 EXPECT_FALSE(low->started()); 960} 961 962TEST_F(ResourceSchedulerTest, ThrottledSyncSchedulesImmediately) { 963 // TODO(aiolos): remove when throttling and coalescing have both landed 964 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 965 false /* should_coalesce */); 966 // Dummies to enforce scheduling. 967 scoped_ptr<TestRequest> high( 968 NewBackgroundRequest("http://host/high", net::HIGHEST)); 969 scoped_ptr<TestRequest> low( 970 NewBackgroundRequest("http://host/low", net::LOWEST)); 971 972 scoped_ptr<TestRequest> request( 973 NewBackgroundSyncRequest("http://host/req", net::LOWEST)); 974 EXPECT_TRUE(request->started()); 975 EXPECT_FALSE(low->started()); 976} 977 978TEST_F(ResourceSchedulerTest, CoalescedSyncSchedulesImmediately) { 979 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 980 true /* should_coalesce */); 981 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 982 scheduler_.OnLoadingStateChanged( 983 kBackgroundChildId, kBackgroundRouteId, true); 984 EXPECT_EQ(ResourceScheduler::COALESCED, 985 scheduler_.GetClientStateForTesting(kBackgroundChildId, 986 kBackgroundRouteId)); 987 // Dummies to enforce scheduling. 988 scoped_ptr<TestRequest> high( 989 NewBackgroundRequest("http://host/high", net::HIGHEST)); 990 scoped_ptr<TestRequest> low( 991 NewBackgroundRequest("http://host/low", net::LOWEST)); 992 993 scoped_ptr<TestRequest> request( 994 NewBackgroundSyncRequest("http://host/req", net::LOWEST)); 995 EXPECT_TRUE(request->started()); 996 EXPECT_FALSE(low->started()); 997 EXPECT_FALSE(high->started()); 998} 999 1000TEST_F(ResourceSchedulerTest, AllBackgroundClientsUnthrottle) { 1001 // TODO(aiolos): remove when throttling and coalescing have both landed 1002 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1003 false /* should_coalesce */); 1004 EXPECT_EQ(ResourceScheduler::THROTTLED, 1005 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1006 kBackgroundRouteId)); 1007 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1008 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1009 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1010 1011 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1012 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1013 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1014 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1015 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1016 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1017 kBackgroundRouteId)); 1018 1019 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1020 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1021 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1022 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1023 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1024 kBackgroundRouteId)); 1025 1026 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, false); 1027 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1028 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1029 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1030 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1031 kBackgroundRouteId)); 1032 1033 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1034 scheduler_.OnLoadingStateChanged( 1035 kBackgroundChildId, kBackgroundRouteId, true); 1036 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1037 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1038 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1039 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1040 kBackgroundRouteId)); 1041} 1042 1043TEST_F(ResourceSchedulerTest, 1044 UnloadedClientVisibilityChangedCorrectlyUnthrottles) { 1045 // TODO(aiolos): remove when throttling and coalescing have both landed 1046 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1047 false /* should_coalesce */); 1048 scheduler_.OnClientCreated(kChildId2, kRouteId2, false); 1049 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1050 scheduler_.OnLoadingStateChanged(kChildId2, kRouteId2, true); 1051 scheduler_.OnLoadingStateChanged( 1052 kBackgroundChildId2, kBackgroundRouteId2, true); 1053 1054 // 1 visible, 3 hidden 1055 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1056 EXPECT_EQ(ResourceScheduler::THROTTLED, 1057 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1058 kBackgroundRouteId)); 1059 EXPECT_EQ(ResourceScheduler::THROTTLED, 1060 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1061 kBackgroundRouteId2)); 1062 EXPECT_EQ(ResourceScheduler::THROTTLED, 1063 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1064 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1065 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1066 1067 // 2 visible, 2 hidden 1068 scheduler_.OnVisibilityChanged(kChildId2, kRouteId2, true); 1069 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1070 EXPECT_EQ(ResourceScheduler::THROTTLED, 1071 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1072 kBackgroundRouteId)); 1073 EXPECT_EQ(ResourceScheduler::THROTTLED, 1074 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1075 kBackgroundRouteId2)); 1076 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1077 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1078 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1079 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1080 1081 // 1 visible, 3 hidden 1082 scheduler_.OnVisibilityChanged(kChildId2, kRouteId2, false); 1083 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1084 EXPECT_EQ(ResourceScheduler::THROTTLED, 1085 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1086 kBackgroundRouteId)); 1087 EXPECT_EQ(ResourceScheduler::THROTTLED, 1088 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1089 kBackgroundRouteId2)); 1090 EXPECT_EQ(ResourceScheduler::THROTTLED, 1091 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1092 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1093 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1094 1095 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1096 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1097} 1098 1099TEST_F(ResourceSchedulerTest, 1100 UnloadedClientAudibilityChangedCorrectlyUnthrottles) { 1101 // TODO(aiolos): remove when throttling and coalescing have both landed 1102 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1103 false /* should_coalesce */); 1104 scheduler_.OnClientCreated(kChildId2, kRouteId2, false); 1105 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1106 scheduler_.OnLoadingStateChanged( 1107 kBackgroundChildId2, kBackgroundRouteId2, true); 1108 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1109 scheduler_.OnAudibilityChanged(kChildId, kRouteId, true); 1110 1111 // 1 audible, 3 hidden 1112 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1113 EXPECT_EQ(ResourceScheduler::THROTTLED, 1114 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1115 kBackgroundRouteId)); 1116 EXPECT_EQ(ResourceScheduler::THROTTLED, 1117 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1118 kBackgroundRouteId2)); 1119 EXPECT_EQ(ResourceScheduler::THROTTLED, 1120 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1121 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1122 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1123 1124 // 2 audible, 2 hidden 1125 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, true); 1126 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1127 EXPECT_EQ(ResourceScheduler::THROTTLED, 1128 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1129 kBackgroundRouteId)); 1130 EXPECT_EQ(ResourceScheduler::THROTTLED, 1131 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1132 kBackgroundRouteId2)); 1133 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1134 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1135 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1136 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1137 1138 // 1 audible, 3 hidden 1139 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, false); 1140 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1141 EXPECT_EQ(ResourceScheduler::THROTTLED, 1142 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1143 kBackgroundRouteId)); 1144 EXPECT_EQ(ResourceScheduler::THROTTLED, 1145 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1146 kBackgroundRouteId2)); 1147 EXPECT_EQ(ResourceScheduler::THROTTLED, 1148 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1149 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1150 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1151 1152 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1153 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1154} 1155 1156TEST_F(ResourceSchedulerTest, 1157 LoadedClientVisibilityChangedCorrectlyUnthrottles) { 1158 // TODO(aiolos): remove when throttling and coalescing have both landed 1159 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1160 false /* should_coalesce */); 1161 scheduler_.OnClientCreated(kChildId2, kRouteId2, false); 1162 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1163 scheduler_.OnLoadingStateChanged(kChildId2, kRouteId2, true); 1164 scheduler_.OnLoadingStateChanged( 1165 kBackgroundChildId2, kBackgroundRouteId2, true); 1166 // 1 visible, 3 hidden 1167 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1168 EXPECT_EQ(ResourceScheduler::THROTTLED, 1169 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1170 kBackgroundRouteId)); 1171 EXPECT_EQ(ResourceScheduler::THROTTLED, 1172 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1173 kBackgroundRouteId2)); 1174 EXPECT_EQ(ResourceScheduler::THROTTLED, 1175 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1176 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1177 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1178 1179 // 2 visible, 2 hidden 1180 scheduler_.OnVisibilityChanged(kChildId2, kRouteId2, true); 1181 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1182 EXPECT_EQ(ResourceScheduler::THROTTLED, 1183 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1184 kBackgroundRouteId)); 1185 EXPECT_EQ(ResourceScheduler::THROTTLED, 1186 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1187 kBackgroundRouteId2)); 1188 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1189 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1190 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1191 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1192 1193 // 1 visible, 3 hidden 1194 scheduler_.OnVisibilityChanged(kChildId2, kRouteId2, false); 1195 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1196 EXPECT_EQ(ResourceScheduler::THROTTLED, 1197 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1198 kBackgroundRouteId)); 1199 EXPECT_EQ(ResourceScheduler::THROTTLED, 1200 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1201 kBackgroundRouteId2)); 1202 EXPECT_EQ(ResourceScheduler::THROTTLED, 1203 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1204 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1205 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1206 1207 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1208 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1209} 1210 1211TEST_F(ResourceSchedulerTest, 1212 LoadedClientAudibilityChangedCorrectlyUnthrottles) { 1213 // TODO(aiolos): remove when throttling and coalescing have both landed 1214 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1215 false /* should_coalesce */); 1216 scheduler_.OnClientCreated(kChildId2, kRouteId2, false); 1217 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1218 scheduler_.OnLoadingStateChanged(kChildId2, kRouteId2, true); 1219 scheduler_.OnLoadingStateChanged( 1220 kBackgroundChildId2, kBackgroundRouteId2, true); 1221 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1222 scheduler_.OnAudibilityChanged(kChildId, kRouteId, true); 1223 // 1 audible, 3 hidden 1224 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1225 EXPECT_EQ(ResourceScheduler::THROTTLED, 1226 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1227 kBackgroundRouteId)); 1228 EXPECT_EQ(ResourceScheduler::THROTTLED, 1229 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1230 kBackgroundRouteId2)); 1231 EXPECT_EQ(ResourceScheduler::THROTTLED, 1232 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1233 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1234 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1235 1236 // 2 audible, 2 hidden 1237 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, true); 1238 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1239 EXPECT_EQ(ResourceScheduler::THROTTLED, 1240 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1241 kBackgroundRouteId)); 1242 EXPECT_EQ(ResourceScheduler::THROTTLED, 1243 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1244 kBackgroundRouteId2)); 1245 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1246 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1247 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1248 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1249 1250 // 1 audible, 3 hidden 1251 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, false); 1252 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1253 EXPECT_EQ(ResourceScheduler::THROTTLED, 1254 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1255 kBackgroundRouteId)); 1256 EXPECT_EQ(ResourceScheduler::THROTTLED, 1257 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1258 kBackgroundRouteId2)); 1259 EXPECT_EQ(ResourceScheduler::THROTTLED, 1260 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1261 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1262 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1263 1264 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1265 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1266} 1267 1268TEST_F(ResourceSchedulerTest, UnloadedClientBecomesHiddenCorrectlyUnthrottles) { 1269 // TODO(aiolos): remove when throttling and coalescing have both landed 1270 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1271 false /* should_coalesce */); 1272 scheduler_.OnClientCreated(kChildId2, kRouteId2, true); 1273 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1274 scheduler_.OnLoadingStateChanged( 1275 kBackgroundChildId2, kBackgroundRouteId2, true); 1276 1277 // 2 visible, 2 hidden 1278 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1279 EXPECT_EQ(ResourceScheduler::THROTTLED, 1280 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1281 kBackgroundRouteId)); 1282 EXPECT_EQ(ResourceScheduler::THROTTLED, 1283 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1284 kBackgroundRouteId2)); 1285 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1286 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1287 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1288 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1289 1290 // 1 visible, 3 hidden 1291 scheduler_.OnVisibilityChanged(kChildId2, kRouteId2, false); 1292 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1293 EXPECT_EQ(ResourceScheduler::THROTTLED, 1294 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1295 kBackgroundRouteId)); 1296 EXPECT_EQ(ResourceScheduler::THROTTLED, 1297 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1298 kBackgroundRouteId2)); 1299 EXPECT_EQ(ResourceScheduler::THROTTLED, 1300 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1301 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1302 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1303 1304 // 0 visible, 4 hidden 1305 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1306 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1307 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1308 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1309 kBackgroundRouteId)); 1310 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1311 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1312 kBackgroundRouteId2)); 1313 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1314 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1315 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1316 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1317 1318 // 1 visible, 3 hidden 1319 scheduler_.OnVisibilityChanged(kChildId, kRouteId, true); 1320 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1321 EXPECT_EQ(ResourceScheduler::THROTTLED, 1322 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1323 kBackgroundRouteId)); 1324 EXPECT_EQ(ResourceScheduler::THROTTLED, 1325 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1326 kBackgroundRouteId2)); 1327 EXPECT_EQ(ResourceScheduler::THROTTLED, 1328 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1329 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1330 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1331 1332 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1333 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1334} 1335 1336TEST_F(ResourceSchedulerTest, UnloadedClientBecomesSilentCorrectlyUnthrottles) { 1337 // TODO(aiolos): remove when throttling and coalescing have both landed 1338 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1339 false /* should_coalesce */); 1340 scheduler_.OnClientCreated(kChildId2, kRouteId2, false); 1341 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1342 scheduler_.OnLoadingStateChanged( 1343 kBackgroundChildId2, kBackgroundRouteId2, true); 1344 scheduler_.OnAudibilityChanged(kChildId, kRouteId, true); 1345 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1346 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, true); 1347 // 2 audible, 2 hidden 1348 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1349 EXPECT_EQ(ResourceScheduler::THROTTLED, 1350 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1351 kBackgroundRouteId)); 1352 EXPECT_EQ(ResourceScheduler::THROTTLED, 1353 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1354 kBackgroundRouteId2)); 1355 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1356 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1357 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1358 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1359 1360 // 1 audible, 3 hidden 1361 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, false); 1362 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1363 EXPECT_EQ(ResourceScheduler::THROTTLED, 1364 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1365 kBackgroundRouteId)); 1366 EXPECT_EQ(ResourceScheduler::THROTTLED, 1367 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1368 kBackgroundRouteId2)); 1369 EXPECT_EQ(ResourceScheduler::THROTTLED, 1370 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1371 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1372 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1373 1374 // 0 audible, 4 hidden 1375 scheduler_.OnAudibilityChanged(kChildId, kRouteId, false); 1376 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1377 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1378 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1379 kBackgroundRouteId)); 1380 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1381 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1382 kBackgroundRouteId2)); 1383 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1384 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1385 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1386 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1387 1388 // 1 audible, 3 hidden 1389 scheduler_.OnAudibilityChanged(kChildId, kRouteId, true); 1390 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1391 EXPECT_EQ(ResourceScheduler::THROTTLED, 1392 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1393 kBackgroundRouteId)); 1394 EXPECT_EQ(ResourceScheduler::THROTTLED, 1395 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1396 kBackgroundRouteId2)); 1397 EXPECT_EQ(ResourceScheduler::THROTTLED, 1398 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1399 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1400 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1401 1402 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1403 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1404} 1405 1406TEST_F(ResourceSchedulerTest, LoadedClientBecomesHiddenCorrectlyThrottles) { 1407 // TODO(aiolos): remove when throttling and coalescing have both landed 1408 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1409 false /* should_coalesce */); 1410 scheduler_.OnClientCreated(kChildId2, kRouteId2, true); 1411 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1412 scheduler_.OnLoadingStateChanged( 1413 kBackgroundChildId2, kBackgroundRouteId2, true); 1414 scheduler_.OnLoadingStateChanged(kChildId2, kRouteId2, true); 1415 // 2 visible, 2 hidden 1416 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1417 EXPECT_EQ(ResourceScheduler::THROTTLED, 1418 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1419 kBackgroundRouteId)); 1420 EXPECT_EQ(ResourceScheduler::THROTTLED, 1421 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1422 kBackgroundRouteId2)); 1423 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1424 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1425 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1426 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1427 1428 // 1 visible, 3 hidden 1429 scheduler_.OnVisibilityChanged(kChildId2, kRouteId2, false); 1430 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1431 EXPECT_EQ(ResourceScheduler::THROTTLED, 1432 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1433 kBackgroundRouteId)); 1434 EXPECT_EQ(ResourceScheduler::THROTTLED, 1435 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1436 kBackgroundRouteId2)); 1437 EXPECT_EQ(ResourceScheduler::THROTTLED, 1438 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1439 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1440 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1441 1442 // 0 visible, 4 hidden 1443 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1444 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1445 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1446 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1447 kBackgroundRouteId)); 1448 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1449 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1450 kBackgroundRouteId2)); 1451 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1452 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1453 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1454 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1455 1456 // 1 visible, 3 hidden 1457 scheduler_.OnVisibilityChanged(kChildId2, kRouteId2, true); 1458 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1459 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1460 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1461 kBackgroundRouteId)); 1462 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1463 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1464 kBackgroundRouteId2)); 1465 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1466 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1467 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1468 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1469 1470 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1471 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1472} 1473 1474TEST_F(ResourceSchedulerTest, LoadedClientBecomesSilentCorrectlyThrottles) { 1475 // TODO(aiolos): remove when throttling and coalescing have both landed 1476 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1477 false /* should_coalesce */); 1478 scheduler_.OnClientCreated(kChildId2, kRouteId2, false); 1479 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1480 scheduler_.OnLoadingStateChanged( 1481 kBackgroundChildId2, kBackgroundRouteId2, true); 1482 scheduler_.OnLoadingStateChanged(kChildId2, kRouteId2, true); 1483 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1484 scheduler_.OnAudibilityChanged(kChildId, kRouteId, true); 1485 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, true); 1486 // 2 audible, 2 hidden 1487 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1488 EXPECT_EQ(ResourceScheduler::THROTTLED, 1489 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1490 kBackgroundRouteId)); 1491 EXPECT_EQ(ResourceScheduler::THROTTLED, 1492 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1493 kBackgroundRouteId2)); 1494 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1495 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1496 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1497 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1498 1499 // 1 audible, 3 hidden 1500 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, false); 1501 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1502 EXPECT_EQ(ResourceScheduler::THROTTLED, 1503 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1504 kBackgroundRouteId)); 1505 EXPECT_EQ(ResourceScheduler::THROTTLED, 1506 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1507 kBackgroundRouteId2)); 1508 EXPECT_EQ(ResourceScheduler::THROTTLED, 1509 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1510 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1511 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1512 1513 // 0 audible, 4 hidden 1514 scheduler_.OnAudibilityChanged(kChildId, kRouteId, false); 1515 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1516 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1517 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1518 kBackgroundRouteId)); 1519 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1520 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1521 kBackgroundRouteId2)); 1522 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1523 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1524 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1525 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1526 1527 // 1 audible, 3 hidden 1528 scheduler_.OnAudibilityChanged(kChildId2, kRouteId2, true); 1529 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1530 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1531 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1532 kBackgroundRouteId)); 1533 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1534 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1535 kBackgroundRouteId2)); 1536 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1537 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1538 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1539 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1540 1541 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1542 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1543} 1544 1545TEST_F(ResourceSchedulerTest, HiddenLoadedChangesCorrectlyStayThrottled) { 1546 // TODO(aiolos): remove when throttling and coalescing have both landed 1547 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1548 false /* should_coalesce */); 1549 scheduler_.OnClientCreated(kChildId2, kRouteId2, true); 1550 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1551 1552 // 1 visible and 2 hidden loading, 1 visible loaded 1553 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1554 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1555 EXPECT_EQ(ResourceScheduler::THROTTLED, 1556 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1557 kBackgroundRouteId)); 1558 EXPECT_EQ(ResourceScheduler::THROTTLED, 1559 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1560 kBackgroundRouteId2)); 1561 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1562 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1563 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1564 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1565 1566 // 1 visible and 1 hidden loading, 1 visible and 1 hidden loaded 1567 scheduler_.OnLoadingStateChanged( 1568 kBackgroundChildId2, kBackgroundRouteId2, true); 1569 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1570 EXPECT_EQ(ResourceScheduler::THROTTLED, 1571 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1572 kBackgroundRouteId)); 1573 EXPECT_EQ(ResourceScheduler::THROTTLED, 1574 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1575 kBackgroundRouteId2)); 1576 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1577 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1578 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1579 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1580 1581 // 1 visible loading, 1 visible and 2 hidden loaded 1582 scheduler_.OnLoadingStateChanged( 1583 kBackgroundChildId, kBackgroundRouteId, true); 1584 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1585 EXPECT_EQ(ResourceScheduler::THROTTLED, 1586 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1587 kBackgroundRouteId)); 1588 EXPECT_EQ(ResourceScheduler::THROTTLED, 1589 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1590 kBackgroundRouteId2)); 1591 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1592 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1593 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1594 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1595 1596 // 1 visible and 1 hidden loading, 1 visible and 1 hidden loaded 1597 scheduler_.OnLoadingStateChanged( 1598 kBackgroundChildId2, kBackgroundRouteId2, true); 1599 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1600 EXPECT_EQ(ResourceScheduler::THROTTLED, 1601 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1602 kBackgroundRouteId)); 1603 EXPECT_EQ(ResourceScheduler::THROTTLED, 1604 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1605 kBackgroundRouteId2)); 1606 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1607 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1608 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1609 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1610 1611 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1612 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1613} 1614 1615TEST_F(ResourceSchedulerTest, PartialVisibleClientLoadedDoesNotUnthrottle) { 1616 // TODO(aiolos): remove when throttling and coalescing have both landed 1617 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1618 false /* should_coalesce */); 1619 scheduler_.OnClientCreated(kChildId2, kRouteId2, true); 1620 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1621 1622 // 2 visible loading, 1 hidden loading, 1 hidden loaded 1623 scheduler_.OnLoadingStateChanged( 1624 kBackgroundChildId2, kBackgroundRouteId2, true); 1625 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1626 EXPECT_EQ(ResourceScheduler::THROTTLED, 1627 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1628 kBackgroundRouteId)); 1629 EXPECT_EQ(ResourceScheduler::THROTTLED, 1630 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1631 kBackgroundRouteId2)); 1632 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1633 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1634 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1635 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1636 1637 // 1 visible and 1 hidden loaded, 1 visible and 1 hidden loading 1638 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1639 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1640 EXPECT_EQ(ResourceScheduler::THROTTLED, 1641 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1642 kBackgroundRouteId)); 1643 EXPECT_EQ(ResourceScheduler::THROTTLED, 1644 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1645 kBackgroundRouteId2)); 1646 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1647 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1648 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1649 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1650 1651 // 2 visible loading, 1 hidden loading, 1 hidden loaded 1652 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, false); 1653 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1654 EXPECT_EQ(ResourceScheduler::THROTTLED, 1655 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1656 kBackgroundRouteId)); 1657 EXPECT_EQ(ResourceScheduler::THROTTLED, 1658 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1659 kBackgroundRouteId2)); 1660 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1661 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1662 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1663 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1664 1665 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1666 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1667} 1668 1669TEST_F(ResourceSchedulerTest, FullVisibleLoadedCorrectlyUnthrottle) { 1670 // TODO(aiolos): remove when throttling and coalescing have both landed 1671 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1672 false /* should_coalesce */); 1673 scheduler_.OnClientCreated(kChildId2, kRouteId2, true); 1674 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1675 1676 // 1 visible and 1 hidden loaded, 1 visible and 1 hidden loading 1677 scheduler_.OnLoadingStateChanged( 1678 kBackgroundChildId2, kBackgroundRouteId2, true); 1679 scheduler_.OnLoadingStateChanged(kChildId2, kRouteId2, true); 1680 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1681 EXPECT_EQ(ResourceScheduler::THROTTLED, 1682 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1683 kBackgroundRouteId)); 1684 EXPECT_EQ(ResourceScheduler::THROTTLED, 1685 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1686 kBackgroundRouteId2)); 1687 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1688 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1689 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1690 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1691 1692 scoped_ptr<TestRequest> high( 1693 NewBackgroundRequest("http://host/high", net::HIGHEST)); 1694 scoped_ptr<TestRequest> low( 1695 NewBackgroundRequest("http://host/low", net::LOWEST)); 1696 1697 EXPECT_TRUE(high->started()); 1698 EXPECT_FALSE(low->started()); 1699 1700 // 2 visible loaded, 1 hidden loading, 1 hidden loaded 1701 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1702 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1703 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1704 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1705 kBackgroundRouteId)); 1706 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1707 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1708 kBackgroundRouteId2)); 1709 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1710 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1711 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1712 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1713 // kBackgroundClientId unthrottling should unthrottle it's request. 1714 EXPECT_TRUE(low->started()); 1715 1716 // 1 visible and 1 hidden loaded, 1 visible and 1 hidden loading 1717 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, false); 1718 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1719 EXPECT_EQ(ResourceScheduler::THROTTLED, 1720 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1721 kBackgroundRouteId)); 1722 EXPECT_EQ(ResourceScheduler::THROTTLED, 1723 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1724 kBackgroundRouteId2)); 1725 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1726 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1727 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1728 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1729 1730 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1731 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1732} 1733 1734TEST_F(ResourceSchedulerTest, 1735 ActiveAndLoadingClientDeletedCorrectlyUnthrottle) { 1736 // TODO(aiolos): remove when throttling and coalescing have both landed 1737 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1738 false /* should_coalesce */); 1739 scheduler_.OnClientCreated(kChildId2, kRouteId2, true); 1740 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1741 1742 // 1 visible and 1 hidden loaded, 1 visible and 1 hidden loading 1743 scheduler_.OnLoadingStateChanged( 1744 kBackgroundChildId2, kBackgroundRouteId2, true); 1745 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1746 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1747 EXPECT_EQ(ResourceScheduler::THROTTLED, 1748 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1749 kBackgroundRouteId)); 1750 EXPECT_EQ(ResourceScheduler::THROTTLED, 1751 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1752 kBackgroundRouteId2)); 1753 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1754 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1755 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1756 scheduler_.GetClientStateForTesting(kChildId2, kRouteId2)); 1757 1758 // 1 visible loaded, 1 hidden loading, 1 hidden loaded 1759 scheduler_.OnClientDeleted(kChildId2, kRouteId2); 1760 EXPECT_TRUE(scheduler_.active_clients_loaded()); 1761 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1762 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1763 kBackgroundRouteId)); 1764 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1765 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1766 kBackgroundRouteId2)); 1767 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1768 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1769 1770 // 1 visible and 1 hidden loaded, 1 visible and 1 hidden loading 1771 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, false); 1772 EXPECT_FALSE(scheduler_.active_clients_loaded()); 1773 EXPECT_EQ(ResourceScheduler::THROTTLED, 1774 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1775 kBackgroundRouteId)); 1776 EXPECT_EQ(ResourceScheduler::THROTTLED, 1777 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1778 kBackgroundRouteId2)); 1779 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1780 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1781 1782 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1783} 1784 1785TEST_F(ResourceSchedulerTest, CoalescedClientCreationStartsTimer) { 1786 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1787 true /* should_coalesce */); 1788 EXPECT_FALSE(mock_timer_->IsRunning()); 1789 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1790 EXPECT_FALSE(mock_timer_->IsRunning()); 1791 scheduler_.OnLoadingStateChanged( 1792 kBackgroundChildId, kBackgroundRouteId, true); 1793 EXPECT_EQ(ResourceScheduler::COALESCED, 1794 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1795 kBackgroundRouteId)); 1796 EXPECT_TRUE(mock_timer_->IsRunning()); 1797} 1798 1799TEST_F(ResourceSchedulerTest, ActiveLoadingClientLoadedAndHiddenStartsTimer) { 1800 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1801 true /* should_coalesce */); 1802 EXPECT_FALSE(mock_timer_->IsRunning()); 1803 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1804 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1805 EXPECT_EQ(ResourceScheduler::THROTTLED, 1806 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1807 kBackgroundRouteId)); 1808 EXPECT_FALSE(mock_timer_->IsRunning()); 1809 1810 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1811 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1812 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1813 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1814 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1815 kBackgroundRouteId)); 1816 EXPECT_FALSE(mock_timer_->IsRunning()); 1817 1818 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1819 EXPECT_EQ(ResourceScheduler::COALESCED, 1820 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1821 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1822 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1823 kBackgroundRouteId)); 1824 EXPECT_TRUE(mock_timer_->IsRunning()); 1825} 1826 1827TEST_F(ResourceSchedulerTest, ActiveLoadingClientHiddenAndLoadedStartsTimer) { 1828 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1829 true /* should_coalesce */); 1830 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1831 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1832 EXPECT_EQ(ResourceScheduler::THROTTLED, 1833 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1834 kBackgroundRouteId)); 1835 EXPECT_FALSE(mock_timer_->IsRunning()); 1836 1837 scheduler_.OnVisibilityChanged(kChildId, kRouteId, false); 1838 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1839 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1840 EXPECT_FALSE(mock_timer_->IsRunning()); 1841 1842 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1843 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1844 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1845 kBackgroundRouteId)); 1846 EXPECT_EQ(ResourceScheduler::COALESCED, 1847 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); 1848 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1849 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1850 kBackgroundRouteId)); 1851 EXPECT_TRUE(mock_timer_->IsRunning()); 1852} 1853 1854TEST_F(ResourceSchedulerTest, CoalescedClientBecomesAudibleStopsTimer) { 1855 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1856 true /* should_coalesce */); 1857 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1858 EXPECT_FALSE(mock_timer_->IsRunning()); 1859 scheduler_.OnLoadingStateChanged( 1860 kBackgroundChildId, kBackgroundRouteId, true); 1861 EXPECT_EQ(ResourceScheduler::COALESCED, 1862 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1863 kBackgroundRouteId)); 1864 EXPECT_TRUE(mock_timer_->IsRunning()); 1865 1866 scheduler_.OnAudibilityChanged(kBackgroundChildId, kBackgroundRouteId, true); 1867 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1868 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1869 kBackgroundRouteId)); 1870 EXPECT_FALSE(mock_timer_->IsRunning()); 1871} 1872 1873TEST_F(ResourceSchedulerTest, LastCoalescedClientDeletionStopsTimer) { 1874 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1875 true /* should_coalesce */); 1876 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1877 EXPECT_FALSE(mock_timer_->IsRunning()); 1878 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1879 EXPECT_FALSE(mock_timer_->IsRunning()); 1880 scheduler_.OnLoadingStateChanged( 1881 kBackgroundChildId, kBackgroundRouteId, true); 1882 EXPECT_EQ(ResourceScheduler::COALESCED, 1883 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1884 kBackgroundRouteId)); 1885 scheduler_.OnLoadingStateChanged( 1886 kBackgroundChildId2, kBackgroundRouteId2, true); 1887 EXPECT_EQ(ResourceScheduler::COALESCED, 1888 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1889 kBackgroundRouteId2)); 1890 EXPECT_TRUE(mock_timer_->IsRunning()); 1891 1892 scheduler_.OnClientDeleted(kBackgroundChildId, kBackgroundRouteId); 1893 EXPECT_TRUE(mock_timer_->IsRunning()); 1894 1895 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1896 EXPECT_FALSE(mock_timer_->IsRunning()); 1897 1898 // To avoid errors on test tear down. 1899 scheduler_.OnClientCreated(kBackgroundChildId, kBackgroundRouteId, false); 1900} 1901 1902TEST_F(ResourceSchedulerTest, LastCoalescedClientStartsLoadingStopsTimer) { 1903 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1904 true /* should_coalesce */); 1905 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1906 EXPECT_FALSE(mock_timer_->IsRunning()); 1907 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1908 EXPECT_FALSE(mock_timer_->IsRunning()); 1909 scheduler_.OnLoadingStateChanged( 1910 kBackgroundChildId, kBackgroundRouteId, true); 1911 EXPECT_EQ(ResourceScheduler::COALESCED, 1912 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1913 kBackgroundRouteId)); 1914 scheduler_.OnLoadingStateChanged( 1915 kBackgroundChildId2, kBackgroundRouteId2, true); 1916 EXPECT_EQ(ResourceScheduler::COALESCED, 1917 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1918 kBackgroundRouteId2)); 1919 EXPECT_TRUE(mock_timer_->IsRunning()); 1920 1921 scheduler_.OnLoadingStateChanged( 1922 kBackgroundChildId, kBackgroundRouteId, false); 1923 EXPECT_TRUE(mock_timer_->IsRunning()); 1924 1925 scheduler_.OnLoadingStateChanged( 1926 kBackgroundChildId2, kBackgroundRouteId2, false); 1927 EXPECT_FALSE(mock_timer_->IsRunning()); 1928 1929 // This is needed to avoid errors on test tear down. 1930 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1931} 1932 1933TEST_F(ResourceSchedulerTest, LastCoalescedClientBecomesVisibleStopsTimer) { 1934 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1935 true /* should_coalesce */); 1936 scheduler_.OnClientCreated(kBackgroundChildId2, kBackgroundRouteId2, false); 1937 EXPECT_FALSE(mock_timer_->IsRunning()); 1938 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1939 EXPECT_FALSE(mock_timer_->IsRunning()); 1940 scheduler_.OnLoadingStateChanged( 1941 kBackgroundChildId, kBackgroundRouteId, true); 1942 EXPECT_EQ(ResourceScheduler::COALESCED, 1943 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1944 kBackgroundRouteId)); 1945 scheduler_.OnLoadingStateChanged( 1946 kBackgroundChildId2, kBackgroundRouteId2, true); 1947 EXPECT_EQ(ResourceScheduler::COALESCED, 1948 scheduler_.GetClientStateForTesting(kBackgroundChildId2, 1949 kBackgroundRouteId2)); 1950 EXPECT_TRUE(mock_timer_->IsRunning()); 1951 1952 scheduler_.OnVisibilityChanged(kBackgroundChildId, kBackgroundRouteId, true); 1953 EXPECT_TRUE(mock_timer_->IsRunning()); 1954 1955 scheduler_.OnVisibilityChanged( 1956 kBackgroundChildId2, kBackgroundRouteId2, true); 1957 EXPECT_FALSE(mock_timer_->IsRunning()); 1958 1959 // To avoid errors on test tear down. 1960 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); 1961} 1962 1963TEST_F(ResourceSchedulerTest, 1964 CoalescedClientBecomesLoadingAndVisibleStopsTimer) { 1965 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1966 true /* should_coalesce */); 1967 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1968 EXPECT_FALSE(mock_timer_->IsRunning()); 1969 scheduler_.OnLoadingStateChanged( 1970 kBackgroundChildId, kBackgroundRouteId, true); 1971 EXPECT_EQ(ResourceScheduler::COALESCED, 1972 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1973 kBackgroundRouteId)); 1974 EXPECT_TRUE(mock_timer_->IsRunning()); 1975 1976 scheduler_.OnLoadingStateChanged( 1977 kBackgroundChildId, kBackgroundRouteId, false); 1978 EXPECT_EQ(ResourceScheduler::UNTHROTTLED, 1979 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1980 kBackgroundRouteId)); 1981 EXPECT_FALSE(mock_timer_->IsRunning()); 1982 1983 scheduler_.OnVisibilityChanged(kBackgroundChildId, kBackgroundRouteId, true); 1984 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, 1985 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1986 kBackgroundRouteId)); 1987 EXPECT_FALSE(mock_timer_->IsRunning()); 1988} 1989 1990TEST_F(ResourceSchedulerTest, CoalescedRequestsIssueOnTimer) { 1991 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 1992 true /* should_coalesce */); 1993 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 1994 scheduler_.OnLoadingStateChanged( 1995 kBackgroundChildId, kBackgroundRouteId, true); 1996 EXPECT_EQ(ResourceScheduler::COALESCED, 1997 scheduler_.GetClientStateForTesting(kBackgroundChildId, 1998 kBackgroundRouteId)); 1999 EXPECT_TRUE(scheduler_.active_clients_loaded()); 2000 2001 scoped_ptr<TestRequest> high( 2002 NewBackgroundRequest("http://host/high", net::HIGHEST)); 2003 scoped_ptr<TestRequest> low( 2004 NewBackgroundRequest("http://host/low", net::LOWEST)); 2005 EXPECT_FALSE(high->started()); 2006 EXPECT_FALSE(low->started()); 2007 2008 FireCoalescingTimer(); 2009 2010 EXPECT_TRUE(high->started()); 2011 EXPECT_TRUE(low->started()); 2012} 2013 2014TEST_F(ResourceSchedulerTest, CoalescedRequestsUnthrottleCorrectlyOnTimer) { 2015 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 2016 true /* should_coalesce */); 2017 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 2018 scheduler_.OnLoadingStateChanged( 2019 kBackgroundChildId, kBackgroundRouteId, true); 2020 EXPECT_EQ(ResourceScheduler::COALESCED, 2021 scheduler_.GetClientStateForTesting(kBackgroundChildId, 2022 kBackgroundRouteId)); 2023 EXPECT_TRUE(scheduler_.active_clients_loaded()); 2024 2025 scoped_ptr<TestRequest> high( 2026 NewBackgroundRequest("http://host/high", net::HIGHEST)); 2027 scoped_ptr<TestRequest> high2( 2028 NewBackgroundRequest("http://host/high", net::HIGHEST)); 2029 scoped_ptr<TestRequest> high3( 2030 NewBackgroundRequest("http://host/high", net::HIGHEST)); 2031 scoped_ptr<TestRequest> high4( 2032 NewBackgroundRequest("http://host/high", net::HIGHEST)); 2033 scoped_ptr<TestRequest> low( 2034 NewBackgroundRequest("http://host/low", net::LOWEST)); 2035 scoped_ptr<TestRequest> low2( 2036 NewBackgroundRequest("http://host/low", net::LOWEST)); 2037 scoped_ptr<TestRequest> low3( 2038 NewBackgroundRequest("http://host/low", net::LOWEST)); 2039 scoped_ptr<TestRequest> low4( 2040 NewBackgroundRequest("http://host/low", net::LOWEST)); 2041 2042 http_server_properties_.SetSupportsSpdy(net::HostPortPair("spdyhost", 443), 2043 true); 2044 scoped_ptr<TestRequest> low_spdy( 2045 NewBackgroundRequest("https://spdyhost/low", net::LOW)); 2046 scoped_ptr<TestRequest> sync_request( 2047 NewBackgroundSyncRequest("http://host/req", net::LOW)); 2048 scoped_ptr<TestRequest> non_http_request( 2049 NewBackgroundRequest("chrome-extension://req", net::LOW)); 2050 2051 // Sync requests should issue immediately. 2052 EXPECT_TRUE(sync_request->started()); 2053 // Non-http(s) requests should issue immediately. 2054 EXPECT_TRUE(non_http_request->started()); 2055 // Nothing else should issue without a timer fire. 2056 EXPECT_FALSE(high->started()); 2057 EXPECT_FALSE(high2->started()); 2058 EXPECT_FALSE(high3->started()); 2059 EXPECT_FALSE(high4->started()); 2060 EXPECT_FALSE(low->started()); 2061 EXPECT_FALSE(low2->started()); 2062 EXPECT_FALSE(low3->started()); 2063 EXPECT_FALSE(low4->started()); 2064 EXPECT_FALSE(low_spdy->started()); 2065 2066 FireCoalescingTimer(); 2067 2068 // All high priority requests should issue. 2069 EXPECT_TRUE(high->started()); 2070 EXPECT_TRUE(high2->started()); 2071 EXPECT_TRUE(high3->started()); 2072 EXPECT_TRUE(high4->started()); 2073 // There should only be one net::LOWEST priority request issued with 2074 // non-delayable requests in flight. 2075 EXPECT_TRUE(low->started()); 2076 EXPECT_FALSE(low2->started()); 2077 EXPECT_FALSE(low3->started()); 2078 EXPECT_FALSE(low4->started()); 2079 // Spdy-Enable requests should issue regardless of priority. 2080 EXPECT_TRUE(low_spdy->started()); 2081} 2082 2083TEST_F(ResourceSchedulerTest, CoalescedRequestsWaitForNextTimer) { 2084 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, 2085 true /* should_coalesce */); 2086 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); 2087 scheduler_.OnLoadingStateChanged( 2088 kBackgroundChildId, kBackgroundRouteId, true); 2089 2090 EXPECT_EQ(ResourceScheduler::COALESCED, 2091 scheduler_.GetClientStateForTesting(kBackgroundChildId, 2092 kBackgroundRouteId)); 2093 EXPECT_TRUE(scheduler_.active_clients_loaded()); 2094 2095 scoped_ptr<TestRequest> high( 2096 NewBackgroundRequest("http://host/high", net::HIGHEST)); 2097 EXPECT_FALSE(high->started()); 2098 2099 FireCoalescingTimer(); 2100 2101 scoped_ptr<TestRequest> high2( 2102 NewBackgroundRequest("http://host/high2", net::HIGHEST)); 2103 scoped_ptr<TestRequest> low( 2104 NewBackgroundRequest("http://host/low", net::LOWEST)); 2105 2106 EXPECT_TRUE(high->started()); 2107 EXPECT_FALSE(high2->started()); 2108 EXPECT_FALSE(low->started()); 2109 2110 FireCoalescingTimer(); 2111 2112 EXPECT_TRUE(high->started()); 2113 EXPECT_TRUE(high2->started()); 2114 EXPECT_TRUE(low->started()); 2115} 2116 2117TEST_F(ResourceSchedulerTest, GetVisualSignalFromRenderViewHost) { 2118 scoped_ptr<MockRenderProcessHostFactory> render_process_host_factory; 2119 scoped_ptr<TestBrowserContext> browser_context; 2120 scoped_ptr<TestWebContents> web_contents_1; 2121 scoped_ptr<TestWebContents> web_contents_2; 2122 2123 render_process_host_factory.reset(new MockRenderProcessHostFactory()); 2124 browser_context.reset(new TestBrowserContext()); 2125 scoped_refptr<SiteInstance> site_instance_1 = 2126 SiteInstance::Create(browser_context.get()); 2127 scoped_refptr<SiteInstance> site_instance_2 = 2128 SiteInstance::Create(browser_context.get()); 2129 SiteInstanceImpl::set_render_process_host_factory( 2130 render_process_host_factory.get()); 2131 2132 web_contents_1.reset( 2133 TestWebContents::Create(browser_context.get(), site_instance_1.get())); 2134 web_contents_2.reset( 2135 TestWebContents::Create(browser_context.get(), site_instance_2.get())); 2136 base::RunLoop().RunUntilIdle(); 2137 2138 RenderViewHostImpl* rvh1 = web_contents_1->GetRenderViewHost(); 2139 RenderViewHostImpl* rvh2 = web_contents_2->GetRenderViewHost(); 2140 ResourceScheduler* scheduler = ResourceDispatcherHostImpl::Get()->scheduler(); 2141 2142 // Check initial visibility is set correctly. 2143 EXPECT_EQ(scheduler->IsClientVisibleForTesting(rvh1->GetProcess()->GetID(), 2144 rvh1->GetRoutingID()), 2145 !rvh1->is_hidden()); 2146 EXPECT_EQ(scheduler->IsClientVisibleForTesting(rvh2->GetProcess()->GetID(), 2147 rvh1->GetRoutingID()), 2148 !rvh2->is_hidden()); 2149 2150 // 1 visible, 1 hidden 2151 rvh1->WasShown(ui::LatencyInfo()); 2152 rvh2->WasHidden(); 2153 base::RunLoop().RunUntilIdle(); 2154 2155 EXPECT_TRUE(scheduler->IsClientVisibleForTesting(rvh1->GetProcess()->GetID(), 2156 rvh1->GetRoutingID())); 2157 EXPECT_FALSE(scheduler->IsClientVisibleForTesting(rvh2->GetProcess()->GetID(), 2158 rvh2->GetRoutingID())); 2159 2160 // Flip the visibility and check again. 2161 rvh1->WasHidden(); 2162 rvh2->WasShown(ui::LatencyInfo()); 2163 base::RunLoop().RunUntilIdle(); 2164 2165 EXPECT_FALSE(scheduler->IsClientVisibleForTesting(rvh1->GetProcess()->GetID(), 2166 rvh1->GetRoutingID())); 2167 EXPECT_TRUE(scheduler->IsClientVisibleForTesting(rvh2->GetProcess()->GetID(), 2168 rvh2->GetRoutingID())); 2169 // Clean up. 2170 web_contents_1.reset(); 2171 web_contents_2.reset(); 2172 base::RunLoop().RunUntilIdle(); 2173 2174 browser_context.reset(); 2175 render_process_host_factory.reset(); 2176} 2177 2178} // unnamed namespace 2179 2180} // namespace content 2181