Chromium Code Reviews| Index: components/offline_pages/background/request_coordinator_unittest.cc |
| diff --git a/components/offline_pages/background/request_coordinator_unittest.cc b/components/offline_pages/background/request_coordinator_unittest.cc |
| index 0b8c1614af8e378aeef3e0ee23cfb9f884e1d148..b30badb6e2751afdbae78248da0d1c85ad9fe844 100644 |
| --- a/components/offline_pages/background/request_coordinator_unittest.cc |
| +++ b/components/offline_pages/background/request_coordinator_unittest.cc |
| @@ -63,10 +63,13 @@ class SchedulerStub : public Scheduler { |
| class OfflinerStub : public Offliner { |
| public: |
| - OfflinerStub() : skip_callback_(false) {} |
| + OfflinerStub() : request_(kRequestId, kUrl, kClientId, base::Time::Now()), |
| + skip_callback_(false) {} |
| bool LoadAndSave(const SavePageRequest& request, |
| const CompletionCallback& callback) override { |
| + callback_ = callback; |
| + request_ = request; |
| // Post the callback on the run loop. |
| if (!skip_callback_) { |
| base::ThreadTaskRunnerHandle::Get()->PostTask( |
| @@ -76,19 +79,30 @@ class OfflinerStub : public Offliner { |
| return true; |
| } |
| + // Clears the currently processing request, if any. Must have called |
| + // LoadAndSave first to set the callback and request. |
| // Clears the currently processing request, if any. |
| - void Cancel() override {} |
| + void Cancel() override { |
| + base::ThreadTaskRunnerHandle::Get()->PostTask( |
| + FROM_HERE, |
| + base::Bind(callback_, request_, Offliner::RequestStatus::CANCELED)); |
| + } |
| void set_skip_callback(bool skip) { |
| skip_callback_ = skip; |
| } |
| private: |
| + CompletionCallback callback_; |
| + SavePageRequest request_; |
| bool skip_callback_; |
| }; |
| class OfflinerFactoryStub : public OfflinerFactory { |
| public: |
| + |
| + OfflinerFactoryStub() : offliner_(nullptr) {} |
| + |
| Offliner* GetOffliner(const OfflinerPolicy* policy) override { |
| if (offliner_.get() == nullptr) { |
| offliner_.reset(new OfflinerStub()); |
| @@ -97,7 +111,7 @@ class OfflinerFactoryStub : public OfflinerFactory { |
| } |
| private: |
| - std::unique_ptr<Offliner> offliner_; |
| + std::unique_ptr<OfflinerStub> offliner_; |
| }; |
| class RequestCoordinatorTest |
| @@ -145,10 +159,14 @@ class RequestCoordinatorTest |
| return last_requests_; |
| } |
| - void skip_offliner_callback() { |
| + void SkipOfflinerCallback() { |
|
dougarnett
2016/06/23 17:19:17
consider whether changing to stub to not auto call
Pete Williamson
2016/06/23 17:54:54
Changed to EnableOfflinerCallback(bool enable); An
|
| offliner_->set_skip_callback(true); |
| } |
| + Offliner::RequestStatus last_offlining_status() const { |
| + return coordinator_->last_offlining_status_; |
| + } |
| + |
| private: |
| RequestQueue::GetRequestsResult last_get_requests_result_; |
| std::vector<SavePageRequest> last_requests_; |
| @@ -169,6 +187,7 @@ RequestCoordinatorTest::~RequestCoordinatorTest() {} |
| void RequestCoordinatorTest::SetUp() { |
| std::unique_ptr<OfflinerPolicy> policy(new OfflinerPolicy()); |
| std::unique_ptr<OfflinerFactory> factory(new OfflinerFactoryStub()); |
| + // Save the offliner for use by the tests. |
| offliner_ = |
| reinterpret_cast<OfflinerStub*>(factory->GetOffliner(policy.get())); |
| std::unique_ptr<RequestQueueInMemoryStore> |
| @@ -191,7 +210,6 @@ void RequestCoordinatorTest::GetRequestsDone( |
| last_requests_ = requests; |
| } |
| - |
| void RequestCoordinatorTest::AddRequestDone( |
| RequestQueue::AddRequestResult result, |
| const SavePageRequest& request) {} |
| @@ -202,7 +220,6 @@ void RequestCoordinatorTest::SendOfflinerDoneCallback( |
| coordinator_->OfflinerDoneCallback(request, status); |
| } |
| - |
| TEST_F(RequestCoordinatorTest, StartProcessingWithNoRequests) { |
| DeviceConditions device_conditions(false, 75, |
| net::NetworkChangeNotifier::CONNECTION_3G); |
| @@ -226,7 +243,7 @@ TEST_F(RequestCoordinatorTest, StartProcessingWithRequestInProgress) { |
| // Ensure that the forthcoming request does not finish - we simulate it being |
| // in progress by asking it to skip making the completion callback. |
| - skip_offliner_callback(); |
| + SkipOfflinerCallback(); |
| // Sending the request to the offliner should make it busy. |
| EXPECT_TRUE(coordinator()->StartProcessing(device_conditions, callback)); |
| @@ -330,4 +347,71 @@ TEST_F(RequestCoordinatorTest, OfflinerDoneRequestFailed) { |
| // TODO(dougarnett): Verify retry count gets incremented. |
| } |
| +// This tests a StopProcessing call before we have actually started the |
| +// prerenderer. |
| +TEST_F(RequestCoordinatorTest, StartProcessingThenStopProcessingImmediately) { |
| + // Add a request to the queue, wait for callbacks to finish. |
| + offline_pages::SavePageRequest request( |
| + kRequestId, kUrl, kClientId, base::Time::Now()); |
| + coordinator()->queue()->AddRequest( |
| + request, |
| + base::Bind(&RequestCoordinatorTest::AddRequestDone, |
| + base::Unretained(this))); |
| + PumpLoop(); |
| + |
| + DeviceConditions device_conditions(false, 75, |
| + net::NetworkChangeNotifier::CONNECTION_3G); |
| + base::Callback<void(bool)> callback = |
| + base::Bind( |
| + &RequestCoordinatorTest::EmptyCallbackFunction, |
| + base::Unretained(this)); |
| + EXPECT_TRUE(coordinator()->StartProcessing(device_conditions, callback)); |
| + |
| + // Now, quick, before it can do much (we haven't called PumpLoop), cancel it. |
| + coordinator()->StopProcessing(); |
| + |
| + // Let the async callbacks in the request coordinator run. |
| + PumpLoop(); |
| + |
| + // OfflinerDoneCallback will not end up getting called with status SAVED, |
| + // Since we cancelled the event before it called offliner_->LoadAndSave(). |
| + EXPECT_NE(Offliner::RequestStatus::SAVED, last_offlining_status()); |
| +} |
| + |
| +// This tests a StopProcessing call after the prerenderer has been started. |
| +TEST_F(RequestCoordinatorTest, StartProcessingThenStopProcessingLater) { |
| + // Add a request to the queue, wait for callbacks to finish. |
| + offline_pages::SavePageRequest request( |
| + kRequestId, kUrl, kClientId, base::Time::Now()); |
| + coordinator()->queue()->AddRequest( |
| + request, |
| + base::Bind(&RequestCoordinatorTest::AddRequestDone, |
| + base::Unretained(this))); |
| + PumpLoop(); |
| + |
| + // Ensure the start processing request stops before the completion callback. |
| + SkipOfflinerCallback(); |
| + |
| + DeviceConditions device_conditions(false, 75, |
| + net::NetworkChangeNotifier::CONNECTION_3G); |
| + base::Callback<void(bool)> callback = |
| + base::Bind( |
| + &RequestCoordinatorTest::EmptyCallbackFunction, |
| + base::Unretained(this)); |
| + EXPECT_TRUE(coordinator()->StartProcessing(device_conditions, callback)); |
| + |
| + // Let all the async parts of the start processing pipeline run to completion. |
| + PumpLoop(); |
| + |
| + // Now we cancel it while the prerenderer is busy. |
| + coordinator()->StopProcessing(); |
| + |
| + // Let the async callbacks in the cancel run. |
| + PumpLoop(); |
| + |
| + // OfflinerDoneCallback will not end up getting called with status SAVED, |
| + // Since we cancelled the event before it called offliner_->LoadAndSave(). |
| + EXPECT_EQ(Offliner::RequestStatus::CANCELED, last_offlining_status()); |
| +} |
| + |
| } // namespace offline_pages |