| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "content/browser/loader/resource_scheduler.h" | 5 #include "content/browser/loader/resource_scheduler.h" |
| 6 | 6 |
| 7 #include "base/memory/scoped_vector.h" | 7 #include "base/memory/scoped_vector.h" |
| 8 #include "base/message_loop/message_loop.h" | 8 #include "base/message_loop/message_loop.h" |
| 9 #include "base/strings/string_number_conversions.h" | 9 #include "base/strings/string_number_conversions.h" |
| 10 #include "base/timer/mock_timer.h" |
| 11 #include "base/timer/timer.h" |
| 10 #include "content/browser/browser_thread_impl.h" | 12 #include "content/browser/browser_thread_impl.h" |
| 11 #include "content/browser/loader/resource_dispatcher_host_impl.h" | 13 #include "content/browser/loader/resource_dispatcher_host_impl.h" |
| 12 #include "content/browser/loader/resource_message_filter.h" | 14 #include "content/browser/loader/resource_message_filter.h" |
| 13 #include "content/browser/loader/resource_request_info_impl.h" | 15 #include "content/browser/loader/resource_request_info_impl.h" |
| 14 #include "content/common/resource_messages.h" | 16 #include "content/common/resource_messages.h" |
| 15 #include "content/public/browser/resource_context.h" | 17 #include "content/public/browser/resource_context.h" |
| 16 #include "content/public/browser/resource_controller.h" | 18 #include "content/public/browser/resource_controller.h" |
| 17 #include "content/public/browser/resource_throttle.h" | 19 #include "content/public/browser/resource_throttle.h" |
| 18 #include "content/public/common/process_type.h" | 20 #include "content/public/common/process_type.h" |
| 19 #include "content/public/common/resource_type.h" | 21 #include "content/public/common/resource_type.h" |
| (...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 130 | 132 |
| 131 FakeResourceContext context_; | 133 FakeResourceContext context_; |
| 132 }; | 134 }; |
| 133 | 135 |
| 134 class ResourceSchedulerTest : public testing::Test { | 136 class ResourceSchedulerTest : public testing::Test { |
| 135 protected: | 137 protected: |
| 136 ResourceSchedulerTest() | 138 ResourceSchedulerTest() |
| 137 : next_request_id_(0), | 139 : next_request_id_(0), |
| 138 ui_thread_(BrowserThread::UI, &message_loop_), | 140 ui_thread_(BrowserThread::UI, &message_loop_), |
| 139 io_thread_(BrowserThread::IO, &message_loop_) { | 141 io_thread_(BrowserThread::IO, &message_loop_) { |
| 142 mock_timer_ = new base::MockTimer(true, true); |
| 143 scheduler_.set_timer_for_testing(scoped_ptr<base::Timer>(mock_timer_)); |
| 144 |
| 140 // TODO(aiolos): remove when throttling and coalescing have both landed | 145 // TODO(aiolos): remove when throttling and coalescing have both landed |
| 141 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, | 146 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, |
| 142 false /* should_coalesce */); | 147 false /* should_coalesce */); |
| 143 | 148 |
| 144 scheduler_.OnClientCreated(kChildId, kRouteId); | 149 scheduler_.OnClientCreated(kChildId, kRouteId); |
| 145 scheduler_.OnVisibilityChanged(kChildId, kRouteId, true); | 150 scheduler_.OnVisibilityChanged(kChildId, kRouteId, true); |
| 146 scheduler_.OnClientCreated(kBackgroundChildId, kBackgroundRouteId); | 151 scheduler_.OnClientCreated(kBackgroundChildId, kBackgroundRouteId); |
| 147 context_.set_http_server_properties(http_server_properties_.GetWeakPtr()); | 152 context_.set_http_server_properties(http_server_properties_.GetWeakPtr()); |
| 148 } | 153 } |
| 149 | 154 |
| (...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 253 scoped_refptr<FakeResourceMessageFilter> filter( | 258 scoped_refptr<FakeResourceMessageFilter> filter( |
| 254 new FakeResourceMessageFilter(kChildId)); | 259 new FakeResourceMessageFilter(kChildId)); |
| 255 const ResourceRequestInfoImpl* info = ResourceRequestInfoImpl::ForRequest( | 260 const ResourceRequestInfoImpl* info = ResourceRequestInfoImpl::ForRequest( |
| 256 request->url_request()); | 261 request->url_request()); |
| 257 const GlobalRequestID& id = info->GetGlobalRequestID(); | 262 const GlobalRequestID& id = info->GetGlobalRequestID(); |
| 258 ResourceHostMsg_DidChangePriority msg(id.request_id, new_priority, | 263 ResourceHostMsg_DidChangePriority msg(id.request_id, new_priority, |
| 259 intra_priority); | 264 intra_priority); |
| 260 rdh_.OnMessageReceived(msg, filter.get()); | 265 rdh_.OnMessageReceived(msg, filter.get()); |
| 261 } | 266 } |
| 262 | 267 |
| 268 void FireCoalescingTimer() { |
| 269 EXPECT_TRUE(mock_timer_->IsRunning()); |
| 270 mock_timer_->Fire(); |
| 271 } |
| 272 |
| 263 int next_request_id_; | 273 int next_request_id_; |
| 264 base::MessageLoopForIO message_loop_; | 274 base::MessageLoopForIO message_loop_; |
| 265 BrowserThreadImpl ui_thread_; | 275 BrowserThreadImpl ui_thread_; |
| 266 BrowserThreadImpl io_thread_; | 276 BrowserThreadImpl io_thread_; |
| 267 ResourceDispatcherHostImpl rdh_; | 277 ResourceDispatcherHostImpl rdh_; |
| 268 ResourceScheduler scheduler_; | 278 ResourceScheduler scheduler_; |
| 279 base::MockTimer* mock_timer_; |
| 269 net::HttpServerPropertiesImpl http_server_properties_; | 280 net::HttpServerPropertiesImpl http_server_properties_; |
| 270 net::TestURLRequestContext context_; | 281 net::TestURLRequestContext context_; |
| 271 }; | 282 }; |
| 272 | 283 |
| 273 TEST_F(ResourceSchedulerTest, OneIsolatedLowRequest) { | 284 TEST_F(ResourceSchedulerTest, OneIsolatedLowRequest) { |
| 274 scoped_ptr<TestRequest> request(NewRequest("http://host/1", net::LOWEST)); | 285 scoped_ptr<TestRequest> request(NewRequest("http://host/1", net::LOWEST)); |
| 275 EXPECT_TRUE(request->started()); | 286 EXPECT_TRUE(request->started()); |
| 276 } | 287 } |
| 277 | 288 |
| 278 TEST_F(ResourceSchedulerTest, OneLowLoadsUntilIdle) { | 289 TEST_F(ResourceSchedulerTest, OneLowLoadsUntilIdle) { |
| (...skipping 1390 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1669 kBackgroundRouteId)); | 1680 kBackgroundRouteId)); |
| 1670 EXPECT_EQ(ResourceScheduler::THROTTLED, | 1681 EXPECT_EQ(ResourceScheduler::THROTTLED, |
| 1671 scheduler_.GetClientStateForTesting(kBackgroundChildId2, | 1682 scheduler_.GetClientStateForTesting(kBackgroundChildId2, |
| 1672 kBackgroundRouteId2)); | 1683 kBackgroundRouteId2)); |
| 1673 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, | 1684 EXPECT_EQ(ResourceScheduler::ACTIVE_AND_LOADING, |
| 1674 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); | 1685 scheduler_.GetClientStateForTesting(kChildId, kRouteId)); |
| 1675 | 1686 |
| 1676 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); | 1687 scheduler_.OnClientDeleted(kBackgroundChildId2, kBackgroundRouteId2); |
| 1677 } | 1688 } |
| 1678 | 1689 |
| 1690 TEST_F(ResourceSchedulerTest, CoalescedRequestsIssueOnTimer) { |
| 1691 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, |
| 1692 true /* should_coalesce */); |
| 1693 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); |
| 1694 scheduler_.OnLoadingStateChanged( |
| 1695 kBackgroundChildId, kBackgroundRouteId, true); |
| 1696 EXPECT_EQ(ResourceScheduler::COALESCED, |
| 1697 scheduler_.GetClientStateForTesting(kBackgroundChildId, |
| 1698 kBackgroundRouteId)); |
| 1699 EXPECT_TRUE(scheduler_.active_clients_loaded()); |
| 1700 |
| 1701 scoped_ptr<TestRequest> high( |
| 1702 NewBackgroundRequest("http://host/high", net::HIGHEST)); |
| 1703 scoped_ptr<TestRequest> low( |
| 1704 NewBackgroundRequest("http://host/low", net::LOWEST)); |
| 1705 EXPECT_FALSE(high->started()); |
| 1706 EXPECT_FALSE(low->started()); |
| 1707 |
| 1708 FireCoalescingTimer(); |
| 1709 |
| 1710 EXPECT_TRUE(high->started()); |
| 1711 EXPECT_TRUE(low->started()); |
| 1712 } |
| 1713 |
| 1714 TEST_F(ResourceSchedulerTest, CoalescedRequestsUnthrottleCorrectlyOnTimer) { |
| 1715 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, |
| 1716 true /* should_coalesce */); |
| 1717 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); |
| 1718 scheduler_.OnLoadingStateChanged( |
| 1719 kBackgroundChildId, kBackgroundRouteId, true); |
| 1720 EXPECT_EQ(ResourceScheduler::COALESCED, |
| 1721 scheduler_.GetClientStateForTesting(kBackgroundChildId, |
| 1722 kBackgroundRouteId)); |
| 1723 EXPECT_TRUE(scheduler_.active_clients_loaded()); |
| 1724 |
| 1725 scoped_ptr<TestRequest> high( |
| 1726 NewBackgroundRequest("http://host/high", net::HIGHEST)); |
| 1727 scoped_ptr<TestRequest> high2( |
| 1728 NewBackgroundRequest("http://host/high", net::HIGHEST)); |
| 1729 scoped_ptr<TestRequest> high3( |
| 1730 NewBackgroundRequest("http://host/high", net::HIGHEST)); |
| 1731 scoped_ptr<TestRequest> high4( |
| 1732 NewBackgroundRequest("http://host/high", net::HIGHEST)); |
| 1733 scoped_ptr<TestRequest> low( |
| 1734 NewBackgroundRequest("http://host/low", net::LOWEST)); |
| 1735 scoped_ptr<TestRequest> low2( |
| 1736 NewBackgroundRequest("http://host/low", net::LOWEST)); |
| 1737 scoped_ptr<TestRequest> low3( |
| 1738 NewBackgroundRequest("http://host/low", net::LOWEST)); |
| 1739 scoped_ptr<TestRequest> low4( |
| 1740 NewBackgroundRequest("http://host/low", net::LOWEST)); |
| 1741 |
| 1742 http_server_properties_.SetSupportsSpdy(net::HostPortPair("spdyhost", 443), |
| 1743 true); |
| 1744 scoped_ptr<TestRequest> low_spdy( |
| 1745 NewBackgroundRequest("https://spdyhost/low", net::LOW)); |
| 1746 scoped_ptr<TestRequest> sync_request( |
| 1747 NewBackgroundSyncRequest("http://host/req", net::LOW)); |
| 1748 scoped_ptr<TestRequest> non_http_request( |
| 1749 NewBackgroundRequest("chrome-extension://req", net::LOW)); |
| 1750 |
| 1751 // Sync requests should issue immediately. |
| 1752 EXPECT_TRUE(sync_request->started()); |
| 1753 // Non-http(s) requests should issue immediately. |
| 1754 EXPECT_TRUE(non_http_request->started()); |
| 1755 // Nothing else should issue without a timer fire. |
| 1756 EXPECT_FALSE(high->started()); |
| 1757 EXPECT_FALSE(high2->started()); |
| 1758 EXPECT_FALSE(high3->started()); |
| 1759 EXPECT_FALSE(high4->started()); |
| 1760 EXPECT_FALSE(low->started()); |
| 1761 EXPECT_FALSE(low2->started()); |
| 1762 EXPECT_FALSE(low3->started()); |
| 1763 EXPECT_FALSE(low4->started()); |
| 1764 EXPECT_FALSE(low_spdy->started()); |
| 1765 |
| 1766 FireCoalescingTimer(); |
| 1767 |
| 1768 // All high priority requests should issue. |
| 1769 EXPECT_TRUE(high->started()); |
| 1770 EXPECT_TRUE(high2->started()); |
| 1771 EXPECT_TRUE(high3->started()); |
| 1772 EXPECT_TRUE(high4->started()); |
| 1773 // There should only be one net::LOWEST priority request issued with |
| 1774 // non-delayable requests in flight. |
| 1775 EXPECT_TRUE(low->started()); |
| 1776 EXPECT_FALSE(low2->started()); |
| 1777 EXPECT_FALSE(low3->started()); |
| 1778 EXPECT_FALSE(low4->started()); |
| 1779 // Spdy-Enable requests should issue regardless of priority. |
| 1780 EXPECT_TRUE(low_spdy->started()); |
| 1781 } |
| 1782 |
| 1783 TEST_F(ResourceSchedulerTest, CoalescedRequestsWaitForNextTimer) { |
| 1784 scheduler_.SetThrottleOptionsForTesting(true /* should_throttle */, |
| 1785 true /* should_coalesce */); |
| 1786 scheduler_.OnLoadingStateChanged(kChildId, kRouteId, true); |
| 1787 scheduler_.OnLoadingStateChanged( |
| 1788 kBackgroundChildId, kBackgroundRouteId, true); |
| 1789 |
| 1790 EXPECT_EQ(ResourceScheduler::COALESCED, |
| 1791 scheduler_.GetClientStateForTesting(kBackgroundChildId, |
| 1792 kBackgroundRouteId)); |
| 1793 EXPECT_TRUE(scheduler_.active_clients_loaded()); |
| 1794 |
| 1795 scoped_ptr<TestRequest> high( |
| 1796 NewBackgroundRequest("http://host/high", net::HIGHEST)); |
| 1797 EXPECT_FALSE(high->started()); |
| 1798 |
| 1799 FireCoalescingTimer(); |
| 1800 |
| 1801 scoped_ptr<TestRequest> high2( |
| 1802 NewBackgroundRequest("http://host/high2", net::HIGHEST)); |
| 1803 scoped_ptr<TestRequest> low( |
| 1804 NewBackgroundRequest("http://host/low", net::LOWEST)); |
| 1805 |
| 1806 EXPECT_TRUE(high->started()); |
| 1807 EXPECT_FALSE(high2->started()); |
| 1808 EXPECT_FALSE(low->started()); |
| 1809 |
| 1810 FireCoalescingTimer(); |
| 1811 |
| 1812 EXPECT_TRUE(high->started()); |
| 1813 EXPECT_TRUE(high2->started()); |
| 1814 EXPECT_TRUE(low->started()); |
| 1815 } |
| 1816 |
| 1679 } // unnamed namespace | 1817 } // unnamed namespace |
| 1680 | 1818 |
| 1681 } // namespace content | 1819 } // namespace content |
| OLD | NEW |