Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(280)

Side by Side Diff: components/offline_pages/downloads/download_ui_adapter_unittest.cc

Issue 2489443002: Move all components/offline_pages/ files into component/offline_pages/core (Closed)
Patch Set: rebase Created 4 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2016 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 "components/offline_pages/downloads/download_ui_adapter.h"
6
7 #include <stdint.h>
8
9 #include <map>
10 #include <memory>
11 #include <string>
12 #include <vector>
13
14 #include "base/bind.h"
15 #include "base/callback.h"
16 #include "base/files/file_path.h"
17 #include "base/run_loop.h"
18 #include "base/single_thread_task_runner.h"
19 #include "base/strings/utf_string_conversions.h"
20 #include "base/test/test_mock_time_task_runner.h"
21 #include "base/threading/thread_task_runner_handle.h"
22 #include "base/time/time.h"
23 #include "components/offline_pages/client_namespace_constants.h"
24 #include "components/offline_pages/client_policy_controller.h"
25 #include "components/offline_pages/stub_offline_page_model.h"
26 #include "testing/gtest/include/gtest/gtest.h"
27
28 namespace offline_pages {
29
30 namespace {
31 // Constants for a test OfflinePageItem.
32 static const int kTestOfflineId1 = 1;
33 static const int kTestOfflineId2 = 2;
34 static const int kTestOfflineId3 = 3;
35 static const char kTestUrl[] = "http://foo.com/bar.mhtml";
36 static const char kTestGuid1[] = "cccccccc-cccc-4ccc-0ccc-ccccccccccc1";
37 static const char kTestGuid2[] = "cccccccc-cccc-4ccc-0ccc-ccccccccccc2";
38 static const char kTestBadGuid[] = "ccccccc-cccc-0ccc-0ccc-ccccccccccc0";
39 static const ClientId kTestClientIdOtherNamespace(kLastNNamespace, kTestGuid1);
40 static const ClientId kTestClientIdOtherGuid(kLastNNamespace, kTestBadGuid);
41 static const ClientId kTestClientId1(kAsyncNamespace, kTestGuid1);
42 static const ClientId kTestClientId2(kAsyncNamespace, kTestGuid2);
43 static const base::FilePath kTestFilePath =
44 base::FilePath(FILE_PATH_LITERAL("foo/bar.mhtml"));
45 static const int kFileSize = 1000;
46 static const base::Time kTestCreationTime = base::Time::Now();
47 static const base::string16 kTestTitle = base::ASCIIToUTF16("test title");
48 } // namespace
49
50 // Mock OfflinePageModel for testing the SavePage calls.
51 class MockOfflinePageModel : public StubOfflinePageModel {
52 public:
53 MockOfflinePageModel(base::TestMockTimeTaskRunner* task_runner)
54 : observer_(nullptr),
55 task_runner_(task_runner),
56 policy_controller_(new ClientPolicyController()) {
57 adapter.reset(new DownloadUIAdapter(this));
58 // Add one page.
59 OfflinePageItem page(GURL(kTestUrl),
60 kTestOfflineId1,
61 kTestClientId1,
62 kTestFilePath,
63 kFileSize,
64 kTestCreationTime);
65 page.title = kTestTitle;
66 pages[kTestOfflineId1] = page;
67 }
68
69 ~MockOfflinePageModel() override {}
70
71 // OfflinePageModel overrides.
72 void AddObserver(Observer* observer) override {
73 EXPECT_TRUE(observer != nullptr);
74 observer_ = observer;
75 }
76
77 void RemoveObserver(Observer* observer) override {
78 EXPECT_TRUE(observer != nullptr);
79 EXPECT_EQ(observer, observer_);
80 observer_ = nullptr;
81 }
82
83 // PostTask instead of just running callback to simpulate the real class.
84 void GetAllPages(const MultipleOfflinePageItemCallback& callback) override {
85 task_runner_->PostTask(
86 FROM_HERE, base::Bind(&MockOfflinePageModel::GetAllPagesImpl,
87 base::Unretained(this), callback));
88 }
89
90 void GetAllPagesImpl(const MultipleOfflinePageItemCallback& callback) {
91 std::vector<OfflinePageItem> result;
92 for (const auto& page : pages)
93 result.push_back(page.second);
94 callback.Run(result);
95 }
96
97 void DeletePageAndNotifyAdapter(const std::string& guid) {
98 for(const auto& page : pages) {
99 if (page.second.client_id.id == guid) {
100 observer_->OfflinePageDeleted(page.second.offline_id,
101 page.second.client_id);
102 pages.erase(page.first);
103 return;
104 }
105 }
106 }
107
108 void AddPageAndNotifyAdapter(const OfflinePageItem& page) {
109 EXPECT_EQ(pages.end(), pages.find(page.offline_id));
110 pages[page.offline_id] = page;
111 observer_->OfflinePageModelChanged(this);
112 }
113
114 ClientPolicyController* GetPolicyController() override {
115 return policy_controller_.get();
116 }
117
118 // Normally, OfflinePageModel owns this adapter, so lets test it this way.
119 std::unique_ptr<DownloadUIAdapter> adapter;
120
121 std::map<int64_t, OfflinePageItem> pages;
122
123 private:
124 OfflinePageModel::Observer* observer_;
125 base::TestMockTimeTaskRunner* task_runner_;
126 // Normally owned by OfflinePageModel.
127 std::unique_ptr<ClientPolicyController> policy_controller_;
128
129 DISALLOW_COPY_AND_ASSIGN(MockOfflinePageModel);
130 };
131
132 class DownloadUIAdapterTest
133 : public testing::Test,
134 public DownloadUIAdapter::Observer {
135 public:
136 DownloadUIAdapterTest();
137 ~DownloadUIAdapterTest() override;
138
139 // testing::Test
140 void SetUp() override;
141
142 // DownloadUIAdapter::Observer
143 void ItemsLoaded() override;
144 void ItemAdded(const DownloadUIItem& item) override;
145 void ItemUpdated(const DownloadUIItem& item) override;
146 void ItemDeleted(const std::string& guid) override;
147
148 // Runs until all of the tasks that are not delayed are gone from the task
149 // queue.
150 void PumpLoop();
151
152 bool items_loaded;
153 std::vector<std::string> added_guids, updated_guids, deleted_guids;
154 std::unique_ptr<MockOfflinePageModel> model;
155
156 private:
157 scoped_refptr<base::TestMockTimeTaskRunner> task_runner_;
158 };
159
160 DownloadUIAdapterTest::DownloadUIAdapterTest()
161 : items_loaded(false),
162 task_runner_(new base::TestMockTimeTaskRunner) {
163 }
164
165 DownloadUIAdapterTest::~DownloadUIAdapterTest() {
166 }
167
168 void DownloadUIAdapterTest::SetUp() {
169 model.reset(new MockOfflinePageModel(task_runner_.get()));
170 model->adapter->AddObserver(this);
171 }
172
173 void DownloadUIAdapterTest::ItemsLoaded() {
174 items_loaded = true;
175 }
176
177 void DownloadUIAdapterTest::ItemAdded(const DownloadUIItem& item) {
178 added_guids.push_back(item.guid);
179 }
180
181 void DownloadUIAdapterTest::ItemUpdated(const DownloadUIItem& item) {
182 updated_guids.push_back(item.guid);
183 }
184
185 void DownloadUIAdapterTest::ItemDeleted(const std::string& guid) {
186 deleted_guids.push_back(guid);
187 }
188
189 void DownloadUIAdapterTest::PumpLoop() {
190 task_runner_->RunUntilIdle();
191 }
192
193 TEST_F(DownloadUIAdapterTest, InitialLoad) {
194 EXPECT_NE(nullptr, model->adapter);
195 EXPECT_FALSE(items_loaded);
196 PumpLoop();
197 EXPECT_TRUE(items_loaded);
198 const DownloadUIItem* item = model->adapter->GetItem(kTestGuid1);
199 EXPECT_NE(nullptr, item);
200 }
201
202 TEST_F(DownloadUIAdapterTest, InitialItemConversion) {
203 EXPECT_EQ(1UL, model->pages.size());
204 EXPECT_EQ(kTestGuid1, model->pages[kTestOfflineId1].client_id.id);
205 PumpLoop();
206 const DownloadUIItem* item = model->adapter->GetItem(kTestGuid1);
207 EXPECT_EQ(kTestGuid1, item->guid);
208 EXPECT_EQ(kTestUrl, item->url.spec());
209 EXPECT_EQ(kTestFilePath, item->target_path);
210 EXPECT_EQ(kTestCreationTime, item->start_time);
211 EXPECT_EQ(kFileSize, item->total_bytes);
212 EXPECT_EQ(kTestTitle, item->title);
213 }
214
215 TEST_F(DownloadUIAdapterTest, ItemDeletedAdded) {
216 PumpLoop();
217 // Add page, notify adapter.
218 OfflinePageItem page(GURL(kTestUrl),
219 kTestOfflineId2,
220 kTestClientId2,
221 base::FilePath(kTestFilePath),
222 kFileSize,
223 kTestCreationTime);
224 model->AddPageAndNotifyAdapter(page);
225 PumpLoop();
226 EXPECT_EQ(1UL, added_guids.size());
227 EXPECT_EQ(kTestGuid2, added_guids[0]);
228 // Remove pages, notify adapter.
229 model->DeletePageAndNotifyAdapter(kTestGuid1);
230 model->DeletePageAndNotifyAdapter(kTestGuid2);
231 PumpLoop();
232 EXPECT_EQ(2UL, deleted_guids.size());
233 EXPECT_EQ(kTestGuid1, deleted_guids[0]);
234 EXPECT_EQ(kTestGuid2, deleted_guids[1]);
235 }
236
237 TEST_F(DownloadUIAdapterTest, ItemWithWrongNamespace) {
238 PumpLoop();
239 OfflinePageItem page1(GURL(kTestUrl),
240 kTestOfflineId2,
241 kTestClientIdOtherNamespace,
242 base::FilePath(kTestFilePath),
243 kFileSize,
244 kTestCreationTime);
245 model->AddPageAndNotifyAdapter(page1);
246 PumpLoop();
247 // Should not add the page with wrong namespace.
248 EXPECT_EQ(0UL, added_guids.size());
249
250 OfflinePageItem page2(GURL(kTestUrl),
251 kTestOfflineId3,
252 kTestClientIdOtherGuid,
253 base::FilePath(kTestFilePath),
254 kFileSize,
255 kTestCreationTime);
256 model->AddPageAndNotifyAdapter(page2);
257 PumpLoop();
258 // Should not add the page with wrong guid.
259 EXPECT_EQ(0UL, added_guids.size());
260 }
261
262 TEST_F(DownloadUIAdapterTest, ItemUpdated) {
263 PumpLoop();
264 // Clear the initial page and replace it with updated one.
265 model->pages.clear();
266 // Add page with the same offline_id/guid, notify adapter.
267 // This should generate 'updated' notification.
268 OfflinePageItem page1(GURL(kTestUrl),
269 kTestOfflineId1,
270 kTestClientId1,
271 base::FilePath(kTestFilePath),
272 kFileSize,
273 kTestCreationTime);
274 // Add a new page which did not exist before.
275 OfflinePageItem page2(GURL(kTestUrl),
276 kTestOfflineId2,
277 kTestClientId2,
278 base::FilePath(kTestFilePath),
279 kFileSize,
280 kTestCreationTime);
281 model->AddPageAndNotifyAdapter(page1);
282 model->AddPageAndNotifyAdapter(page2);
283 PumpLoop();
284 EXPECT_EQ(1UL, added_guids.size());
285 EXPECT_EQ(kTestGuid2, added_guids[0]);
286 // TODO(dimich): we currently don't report updated items since OPM doesn't
287 // have support for that. Add as needed, this will have to be updated when
288 // support is added.
289 EXPECT_EQ(0UL, updated_guids.size());
290 }
291
292 TEST_F(DownloadUIAdapterTest, NoHangingLoad) {
293 EXPECT_NE(nullptr, model->adapter);
294 EXPECT_FALSE(items_loaded);
295 // Removal of last observer causes cache unload of not-yet-loaded cache.
296 model->adapter->RemoveObserver(this);
297 // This will complete async fetch of items, but...
298 PumpLoop();
299 // items should not be loaded when there is no observers!
300 EXPECT_FALSE(items_loaded);
301 // This should not crash.
302 model->adapter->AddObserver(this);
303 }
304
305 } // namespace offline_pages
OLDNEW
« no previous file with comments | « components/offline_pages/downloads/download_ui_adapter.cc ('k') | components/offline_pages/downloads/download_ui_item.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698