| OLD | NEW |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 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 | 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 "components/reading_list/ios/reading_list_model.h" | 5 #include "components/reading_list/ios/reading_list_model.h" |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/memory/ptr_util.h" | 8 #include "base/memory/ptr_util.h" |
| 9 #import "base/test/ios/wait_util.h" | 9 #include "base/test/simple_test_clock.h" |
| 10 #include "components/reading_list/ios/reading_list_model_impl.h" | 10 #include "components/reading_list/ios/reading_list_model_impl.h" |
| 11 #include "components/reading_list/ios/reading_list_model_storage.h" | 11 #include "components/reading_list/ios/reading_list_model_storage.h" |
| 12 #include "components/reading_list/ios/reading_list_store_delegate.h" | 12 #include "components/reading_list/ios/reading_list_store_delegate.h" |
| 13 #include "components/sync/model/metadata_change_list.h" | 13 #include "components/sync/model/metadata_change_list.h" |
| 14 #include "components/sync/model/model_error.h" | 14 #include "components/sync/model/model_error.h" |
| 15 #include "testing/gtest/include/gtest/gtest.h" | 15 #include "testing/gtest/include/gtest/gtest.h" |
| 16 | 16 |
| 17 namespace { | 17 namespace { |
| 18 | 18 |
| 19 const GURL callback_url("http://example.com"); | 19 const GURL callback_url("http://example.com"); |
| 20 const std::string callback_title("test title"); | 20 const std::string callback_title("test title"); |
| 21 | 21 |
| 22 base::Time AdvanceAndGetTime(base::SimpleTestClock* clock) { |
| 23 clock->Advance(base::TimeDelta::FromMilliseconds(10)); |
| 24 return clock->Now(); |
| 25 } |
| 26 |
| 22 class TestReadingListStorageObserver { | 27 class TestReadingListStorageObserver { |
| 23 public: | 28 public: |
| 24 virtual void ReadingListDidSaveEntry() = 0; | 29 virtual void ReadingListDidSaveEntry() = 0; |
| 25 virtual void ReadingListDidRemoveEntry() = 0; | 30 virtual void ReadingListDidRemoveEntry() = 0; |
| 26 }; | 31 }; |
| 27 | 32 |
| 28 class TestReadingListStorage : public ReadingListModelStorage { | 33 class TestReadingListStorage : public ReadingListModelStorage { |
| 29 public: | 34 public: |
| 30 TestReadingListStorage(TestReadingListStorageObserver* observer) | 35 TestReadingListStorage(TestReadingListStorageObserver* observer, |
| 36 base::SimpleTestClock* clock) |
| 31 : ReadingListModelStorage( | 37 : ReadingListModelStorage( |
| 32 base::Bind(&syncer::ModelTypeChangeProcessor::Create, | 38 base::Bind(&syncer::ModelTypeChangeProcessor::Create, |
| 33 base::RepeatingClosure()), | 39 base::RepeatingClosure()), |
| 34 syncer::READING_LIST), | 40 syncer::READING_LIST), |
| 35 entries_(new ReadingListStoreDelegate::ReadingListEntries()), | 41 entries_(new ReadingListStoreDelegate::ReadingListEntries()), |
| 36 observer_(observer) {} | 42 observer_(observer), |
| 43 clock_(clock) {} |
| 37 | 44 |
| 38 void AddSampleEntries() { | 45 void AddSampleEntries() { |
| 39 // Adds timer and interlace read/unread entry creation to avoid having two | 46 // Adds timer and interlace read/unread entry creation to avoid having two |
| 40 // entries with the same creation timestamp. | 47 // entries with the same creation timestamp. |
| 41 ReadingListEntry unread_a(GURL("http://unread_a.com"), "unread_a"); | 48 ReadingListEntry unread_a(GURL("http://unread_a.com"), "unread_a", |
| 49 AdvanceAndGetTime(clock_)); |
| 42 entries_->insert( | 50 entries_->insert( |
| 43 std::make_pair(GURL("http://unread_a.com"), std::move(unread_a))); | 51 std::make_pair(GURL("http://unread_a.com"), std::move(unread_a))); |
| 44 base::test::ios::SpinRunLoopWithMinDelay( | |
| 45 base::TimeDelta::FromMilliseconds(5)); | |
| 46 | 52 |
| 47 ReadingListEntry read_a(GURL("http://read_a.com"), "read_a"); | 53 ReadingListEntry read_a(GURL("http://read_a.com"), "read_a", |
| 48 read_a.SetRead(true); | 54 AdvanceAndGetTime(clock_)); |
| 55 read_a.SetRead(true, AdvanceAndGetTime(clock_)); |
| 49 entries_->insert( | 56 entries_->insert( |
| 50 std::make_pair(GURL("http://read_a.com"), std::move(read_a))); | 57 std::make_pair(GURL("http://read_a.com"), std::move(read_a))); |
| 51 base::test::ios::SpinRunLoopWithMinDelay( | |
| 52 base::TimeDelta::FromMilliseconds(5)); | |
| 53 | 58 |
| 54 ReadingListEntry unread_b(GURL("http://unread_b.com"), "unread_b"); | 59 ReadingListEntry unread_b(GURL("http://unread_b.com"), "unread_b", |
| 60 AdvanceAndGetTime(clock_)); |
| 55 entries_->insert( | 61 entries_->insert( |
| 56 std::make_pair(GURL("http://unread_b.com"), std::move(unread_b))); | 62 std::make_pair(GURL("http://unread_b.com"), std::move(unread_b))); |
| 57 base::test::ios::SpinRunLoopWithMinDelay( | |
| 58 base::TimeDelta::FromMilliseconds(5)); | |
| 59 | 63 |
| 60 ReadingListEntry read_b(GURL("http://read_b.com"), "read_b"); | 64 ReadingListEntry read_b(GURL("http://read_b.com"), "read_b", |
| 61 read_b.SetRead(true); | 65 AdvanceAndGetTime(clock_)); |
| 66 read_b.SetRead(true, AdvanceAndGetTime(clock_)); |
| 62 entries_->insert( | 67 entries_->insert( |
| 63 std::make_pair(GURL("http://read_b.com"), std::move(read_b))); | 68 std::make_pair(GURL("http://read_b.com"), std::move(read_b))); |
| 64 base::test::ios::SpinRunLoopWithMinDelay( | |
| 65 base::TimeDelta::FromMilliseconds(5)); | |
| 66 | 69 |
| 67 ReadingListEntry unread_c(GURL("http://unread_c.com"), "unread_c"); | 70 ReadingListEntry unread_c(GURL("http://unread_c.com"), "unread_c", |
| 71 AdvanceAndGetTime(clock_)); |
| 68 entries_->insert( | 72 entries_->insert( |
| 69 std::make_pair(GURL("http://unread_c.com"), std::move(unread_c))); | 73 std::make_pair(GURL("http://unread_c.com"), std::move(unread_c))); |
| 70 base::test::ios::SpinRunLoopWithMinDelay( | |
| 71 base::TimeDelta::FromMilliseconds(5)); | |
| 72 | 74 |
| 73 ReadingListEntry read_c(GURL("http://read_c.com"), "read_c"); | 75 ReadingListEntry read_c(GURL("http://read_c.com"), "read_c", |
| 74 read_c.SetRead(true); | 76 AdvanceAndGetTime(clock_)); |
| 77 read_c.SetRead(true, AdvanceAndGetTime(clock_)); |
| 75 entries_->insert( | 78 entries_->insert( |
| 76 std::make_pair(GURL("http://read_c.com"), std::move(read_c))); | 79 std::make_pair(GURL("http://read_c.com"), std::move(read_c))); |
| 77 base::test::ios::SpinRunLoopWithMinDelay( | |
| 78 base::TimeDelta::FromMilliseconds(5)); | |
| 79 | 80 |
| 80 ReadingListEntry unread_d(GURL("http://unread_d.com"), "unread_d"); | 81 ReadingListEntry unread_d(GURL("http://unread_d.com"), "unread_d", |
| 82 AdvanceAndGetTime(clock_)); |
| 81 entries_->insert( | 83 entries_->insert( |
| 82 std::make_pair(GURL("http://unread_d.com"), std::move(unread_d))); | 84 std::make_pair(GURL("http://unread_d.com"), std::move(unread_d))); |
| 83 base::test::ios::SpinRunLoopWithMinDelay( | |
| 84 base::TimeDelta::FromMilliseconds(5)); | |
| 85 } | 85 } |
| 86 | 86 |
| 87 void SetReadingListModel(ReadingListModel* model, | 87 void SetReadingListModel(ReadingListModel* model, |
| 88 ReadingListStoreDelegate* delegate) override { | 88 ReadingListStoreDelegate* delegate, |
| 89 base::Clock* clock) override { |
| 89 delegate->StoreLoaded(std::move(entries_)); | 90 delegate->StoreLoaded(std::move(entries_)); |
| 91 clock_ = static_cast<base::SimpleTestClock*>(clock); |
| 90 } | 92 } |
| 91 | 93 |
| 92 // Saves or updates an entry. If the entry is not yet in the database, it is | 94 // Saves or updates an entry. If the entry is not yet in the database, it is |
| 93 // created. | 95 // created. |
| 94 void SaveEntry(const ReadingListEntry& entry) override { | 96 void SaveEntry(const ReadingListEntry& entry) override { |
| 95 observer_->ReadingListDidSaveEntry(); | 97 observer_->ReadingListDidSaveEntry(); |
| 96 } | 98 } |
| 97 | 99 |
| 98 // Removes an entry from the storage. | 100 // Removes an entry from the storage. |
| 99 void RemoveEntry(const ReadingListEntry& entry) override { | 101 void RemoveEntry(const ReadingListEntry& entry) override { |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 141 } | 143 } |
| 142 | 144 |
| 143 std::string GetStorageKey(const syncer::EntityData& entity_data) override { | 145 std::string GetStorageKey(const syncer::EntityData& entity_data) override { |
| 144 NOTREACHED(); | 146 NOTREACHED(); |
| 145 return ""; | 147 return ""; |
| 146 } | 148 } |
| 147 | 149 |
| 148 private: | 150 private: |
| 149 std::unique_ptr<ReadingListStoreDelegate::ReadingListEntries> entries_; | 151 std::unique_ptr<ReadingListStoreDelegate::ReadingListEntries> entries_; |
| 150 TestReadingListStorageObserver* observer_; | 152 TestReadingListStorageObserver* observer_; |
| 153 base::SimpleTestClock* clock_; |
| 151 }; | 154 }; |
| 152 | 155 |
| 153 class ReadingListModelTest : public ReadingListModelObserver, | 156 class ReadingListModelTest : public ReadingListModelObserver, |
| 154 public TestReadingListStorageObserver, | 157 public TestReadingListStorageObserver, |
| 155 public testing::Test { | 158 public testing::Test { |
| 156 public: | 159 public: |
| 157 ReadingListModelTest() | 160 ReadingListModelTest() : callback_called_(false) { |
| 158 : callback_called_(false), model_(new ReadingListModelImpl()) { | 161 auto clock = base::MakeUnique<base::SimpleTestClock>(); |
| 162 clock_ = clock.get(); |
| 163 model_ = base::MakeUnique<ReadingListModelImpl>(nullptr, nullptr, |
| 164 std::move(clock)); |
| 159 ClearCounts(); | 165 ClearCounts(); |
| 160 model_->AddObserver(this); | 166 model_->AddObserver(this); |
| 161 } | 167 } |
| 162 ~ReadingListModelTest() override {} | 168 ~ReadingListModelTest() override {} |
| 163 | 169 |
| 164 void SetStorage(std::unique_ptr<TestReadingListStorage> storage) { | 170 void SetStorage(std::unique_ptr<TestReadingListStorage> storage, |
| 165 model_ = | 171 std::unique_ptr<base::SimpleTestClock> clock) { |
| 166 base::MakeUnique<ReadingListModelImpl>(std::move(storage), nullptr); | 172 clock_ = clock.get(); |
| 173 model_ = base::MakeUnique<ReadingListModelImpl>(std::move(storage), nullptr, |
| 174 std::move(clock)); |
| 167 ClearCounts(); | 175 ClearCounts(); |
| 168 model_->AddObserver(this); | 176 model_->AddObserver(this); |
| 169 } | 177 } |
| 170 | 178 |
| 171 void ClearCounts() { | 179 void ClearCounts() { |
| 172 observer_loaded_ = observer_started_batch_update_ = | 180 observer_loaded_ = observer_started_batch_update_ = |
| 173 observer_completed_batch_update_ = observer_deleted_ = | 181 observer_completed_batch_update_ = observer_deleted_ = |
| 174 observer_remove_ = observer_move_ = observer_add_ = | 182 observer_remove_ = observer_move_ = observer_add_ = |
| 175 observer_did_add_ = observer_update_ = observer_did_apply_ = | 183 observer_did_add_ = observer_update_ = observer_did_apply_ = |
| 176 storage_saved_ = storage_removed_ = 0; | 184 storage_saved_ = storage_removed_ = 0; |
| (...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 287 int observer_move_; | 295 int observer_move_; |
| 288 int observer_add_; | 296 int observer_add_; |
| 289 int observer_did_add_; | 297 int observer_did_add_; |
| 290 int observer_update_; | 298 int observer_update_; |
| 291 int observer_did_apply_; | 299 int observer_did_apply_; |
| 292 int storage_saved_; | 300 int storage_saved_; |
| 293 int storage_removed_; | 301 int storage_removed_; |
| 294 bool callback_called_; | 302 bool callback_called_; |
| 295 | 303 |
| 296 std::unique_ptr<ReadingListModelImpl> model_; | 304 std::unique_ptr<ReadingListModelImpl> model_; |
| 305 // Owned by |model_|; |
| 306 base::SimpleTestClock* clock_; |
| 297 }; | 307 }; |
| 298 | 308 |
| 299 // Tests creating an empty model. | 309 // Tests creating an empty model. |
| 300 TEST_F(ReadingListModelTest, EmptyLoaded) { | 310 TEST_F(ReadingListModelTest, EmptyLoaded) { |
| 301 EXPECT_TRUE(model_->loaded()); | 311 EXPECT_TRUE(model_->loaded()); |
| 302 AssertObserverCount(1, 0, 0, 0, 0, 0, 0, 0, 0); | 312 AssertObserverCount(1, 0, 0, 0, 0, 0, 0, 0, 0); |
| 303 EXPECT_EQ(0ul, UnreadSize()); | 313 EXPECT_EQ(0ul, UnreadSize()); |
| 304 EXPECT_EQ(0ul, ReadSize()); | 314 EXPECT_EQ(0ul, ReadSize()); |
| 305 model_->Shutdown(); | 315 model_->Shutdown(); |
| 306 EXPECT_FALSE(model_->loaded()); | 316 EXPECT_FALSE(model_->loaded()); |
| 307 AssertObserverCount(1, 0, 0, 1, 0, 0, 0, 0, 0); | 317 AssertObserverCount(1, 0, 0, 1, 0, 0, 0, 0, 0); |
| 308 } | 318 } |
| 309 | 319 |
| 310 // Tests load model. | 320 // Tests load model. |
| 311 TEST_F(ReadingListModelTest, ModelLoaded) { | 321 TEST_F(ReadingListModelTest, ModelLoaded) { |
| 312 ClearCounts(); | 322 ClearCounts(); |
| 313 auto storage = base::MakeUnique<TestReadingListStorage>(this); | 323 auto clock = base::MakeUnique<base::SimpleTestClock>(); |
| 324 auto storage = base::MakeUnique<TestReadingListStorage>(this, clock.get()); |
| 314 storage->AddSampleEntries(); | 325 storage->AddSampleEntries(); |
| 315 SetStorage(std::move(storage)); | 326 SetStorage(std::move(storage), std::move(clock)); |
| 316 | 327 |
| 317 AssertObserverCount(1, 0, 0, 0, 0, 0, 0, 0, 0); | 328 AssertObserverCount(1, 0, 0, 0, 0, 0, 0, 0, 0); |
| 318 std::map<GURL, std::string> loaded_entries; | 329 std::map<GURL, std::string> loaded_entries; |
| 319 int size = 0; | 330 int size = 0; |
| 320 for (const auto& url : model_->Keys()) { | 331 for (const auto& url : model_->Keys()) { |
| 321 size++; | 332 size++; |
| 322 const ReadingListEntry* entry = model_->GetEntryByURL(url); | 333 const ReadingListEntry* entry = model_->GetEntryByURL(url); |
| 323 loaded_entries[url] = entry->Title(); | 334 loaded_entries[url] = entry->Title(); |
| 324 } | 335 } |
| 325 EXPECT_EQ(size, 7); | 336 EXPECT_EQ(size, 7); |
| 326 EXPECT_EQ(loaded_entries[GURL("http://unread_a.com")], "unread_a"); | 337 EXPECT_EQ(loaded_entries[GURL("http://unread_a.com")], "unread_a"); |
| 327 EXPECT_EQ(loaded_entries[GURL("http://unread_b.com")], "unread_b"); | 338 EXPECT_EQ(loaded_entries[GURL("http://unread_b.com")], "unread_b"); |
| 328 EXPECT_EQ(loaded_entries[GURL("http://unread_c.com")], "unread_c"); | 339 EXPECT_EQ(loaded_entries[GURL("http://unread_c.com")], "unread_c"); |
| 329 EXPECT_EQ(loaded_entries[GURL("http://unread_d.com")], "unread_d"); | 340 EXPECT_EQ(loaded_entries[GURL("http://unread_d.com")], "unread_d"); |
| 330 EXPECT_EQ(loaded_entries[GURL("http://read_a.com")], "read_a"); | 341 EXPECT_EQ(loaded_entries[GURL("http://read_a.com")], "read_a"); |
| 331 EXPECT_EQ(loaded_entries[GURL("http://read_b.com")], "read_b"); | 342 EXPECT_EQ(loaded_entries[GURL("http://read_b.com")], "read_b"); |
| 332 EXPECT_EQ(loaded_entries[GURL("http://read_c.com")], "read_c"); | 343 EXPECT_EQ(loaded_entries[GURL("http://read_c.com")], "read_c"); |
| 333 } | 344 } |
| 334 | 345 |
| 335 // Tests adding entry. | 346 // Tests adding entry. |
| 336 TEST_F(ReadingListModelTest, AddEntry) { | 347 TEST_F(ReadingListModelTest, AddEntry) { |
| 337 auto storage = base::MakeUnique<TestReadingListStorage>(this); | 348 auto clock = base::MakeUnique<base::SimpleTestClock>(); |
| 338 SetStorage(std::move(storage)); | 349 auto storage = base::MakeUnique<TestReadingListStorage>(this, clock.get()); |
| 350 SetStorage(std::move(storage), std::move(clock)); |
| 339 ClearCounts(); | 351 ClearCounts(); |
| 340 | 352 |
| 341 const ReadingListEntry& entry = | 353 const ReadingListEntry& entry = |
| 342 model_->AddEntry(GURL("http://example.com"), "\n \tsample Test ", | 354 model_->AddEntry(GURL("http://example.com"), "\n \tsample Test ", |
| 343 reading_list::ADDED_VIA_CURRENT_APP); | 355 reading_list::ADDED_VIA_CURRENT_APP); |
| 344 EXPECT_EQ(GURL("http://example.com"), entry.URL()); | 356 EXPECT_EQ(GURL("http://example.com"), entry.URL()); |
| 345 EXPECT_EQ("sample Test", entry.Title()); | 357 EXPECT_EQ("sample Test", entry.Title()); |
| 346 | 358 |
| 347 AssertObserverCount(0, 0, 0, 0, 0, 0, 1, 0, 1); | 359 AssertObserverCount(0, 0, 0, 0, 0, 0, 1, 0, 1); |
| 348 AssertStorageCount(1, 0); | 360 AssertStorageCount(1, 0); |
| 349 EXPECT_EQ(1ul, UnreadSize()); | 361 EXPECT_EQ(1ul, UnreadSize()); |
| 350 EXPECT_EQ(0ul, ReadSize()); | 362 EXPECT_EQ(0ul, ReadSize()); |
| 351 EXPECT_TRUE(model_->GetLocalUnseenFlag()); | 363 EXPECT_TRUE(model_->GetLocalUnseenFlag()); |
| 352 | 364 |
| 353 const ReadingListEntry* other_entry = | 365 const ReadingListEntry* other_entry = |
| 354 model_->GetEntryByURL(GURL("http://example.com")); | 366 model_->GetEntryByURL(GURL("http://example.com")); |
| 355 EXPECT_NE(other_entry, nullptr); | 367 EXPECT_NE(other_entry, nullptr); |
| 356 EXPECT_FALSE(other_entry->IsRead()); | 368 EXPECT_FALSE(other_entry->IsRead()); |
| 357 EXPECT_EQ(GURL("http://example.com"), other_entry->URL()); | 369 EXPECT_EQ(GURL("http://example.com"), other_entry->URL()); |
| 358 EXPECT_EQ("sample Test", other_entry->Title()); | 370 EXPECT_EQ("sample Test", other_entry->Title()); |
| 359 } | 371 } |
| 360 | 372 |
| 361 // Tests addin entry from sync. | 373 // Tests addin entry from sync. |
| 362 TEST_F(ReadingListModelTest, SyncAddEntry) { | 374 TEST_F(ReadingListModelTest, SyncAddEntry) { |
| 363 auto storage = base::MakeUnique<TestReadingListStorage>(this); | 375 auto clock = base::MakeUnique<base::SimpleTestClock>(); |
| 364 SetStorage(std::move(storage)); | 376 auto storage = base::MakeUnique<TestReadingListStorage>(this, clock.get()); |
| 365 auto entry = | 377 SetStorage(std::move(storage), std::move(clock)); |
| 366 base::MakeUnique<ReadingListEntry>(GURL("http://example.com"), "sample"); | 378 auto entry = base::MakeUnique<ReadingListEntry>( |
| 367 entry->SetRead(true); | 379 GURL("http://example.com"), "sample", AdvanceAndGetTime(clock_)); |
| 380 entry->SetRead(true, AdvanceAndGetTime(clock_)); |
| 368 ClearCounts(); | 381 ClearCounts(); |
| 369 | 382 |
| 370 model_->SyncAddEntry(std::move(entry)); | 383 model_->SyncAddEntry(std::move(entry)); |
| 371 AssertObserverCount(0, 0, 0, 0, 0, 0, 1, 0, 1); | 384 AssertObserverCount(0, 0, 0, 0, 0, 0, 1, 0, 1); |
| 372 AssertStorageCount(0, 0); | 385 AssertStorageCount(0, 0); |
| 373 EXPECT_EQ(0ul, UnreadSize()); | 386 EXPECT_EQ(0ul, UnreadSize()); |
| 374 EXPECT_EQ(1ul, ReadSize()); | 387 EXPECT_EQ(1ul, ReadSize()); |
| 375 ClearCounts(); | 388 ClearCounts(); |
| 376 } | 389 } |
| 377 | 390 |
| 378 // Tests updating entry from sync. | 391 // Tests updating entry from sync. |
| 379 TEST_F(ReadingListModelTest, SyncMergeEntry) { | 392 TEST_F(ReadingListModelTest, SyncMergeEntry) { |
| 380 auto storage = base::MakeUnique<TestReadingListStorage>(this); | 393 auto clock = base::MakeUnique<base::SimpleTestClock>(); |
| 381 SetStorage(std::move(storage)); | 394 auto storage = base::MakeUnique<TestReadingListStorage>(this, clock.get()); |
| 395 SetStorage(std::move(storage), std::move(clock)); |
| 382 model_->AddEntry(GURL("http://example.com"), "sample", | 396 model_->AddEntry(GURL("http://example.com"), "sample", |
| 383 reading_list::ADDED_VIA_CURRENT_APP); | 397 reading_list::ADDED_VIA_CURRENT_APP); |
| 384 const base::FilePath distilled_path("distilled/page.html"); | 398 const base::FilePath distilled_path("distilled/page.html"); |
| 385 const GURL distilled_url("http://example.com/distilled"); | 399 const GURL distilled_url("http://example.com/distilled"); |
| 386 int64_t size = 50; | 400 int64_t size = 50; |
| 387 int64_t time = 100; | 401 int64_t time = 100; |
| 388 model_->SetEntryDistilledInfo(GURL("http://example.com"), distilled_path, | 402 model_->SetEntryDistilledInfo(GURL("http://example.com"), distilled_path, |
| 389 distilled_url, size, time); | 403 distilled_url, size, |
| 404 base::Time::FromTimeT(time)); |
| 390 const ReadingListEntry* local_entry = | 405 const ReadingListEntry* local_entry = |
| 391 model_->GetEntryByURL(GURL("http://example.com")); | 406 model_->GetEntryByURL(GURL("http://example.com")); |
| 392 int64_t local_update_time = local_entry->UpdateTime(); | 407 int64_t local_update_time = local_entry->UpdateTime(); |
| 393 | 408 |
| 394 base::test::ios::SpinRunLoopWithMinDelay( | 409 auto sync_entry = base::MakeUnique<ReadingListEntry>( |
| 395 base::TimeDelta::FromMilliseconds(10)); | 410 GURL("http://example.com"), "sample", AdvanceAndGetTime(clock_)); |
| 396 auto sync_entry = | 411 sync_entry->SetRead(true, AdvanceAndGetTime(clock_)); |
| 397 base::MakeUnique<ReadingListEntry>(GURL("http://example.com"), "sample"); | |
| 398 sync_entry->SetRead(true); | |
| 399 ASSERT_GT(sync_entry->UpdateTime(), local_update_time); | 412 ASSERT_GT(sync_entry->UpdateTime(), local_update_time); |
| 400 int64_t sync_update_time = sync_entry->UpdateTime(); | 413 int64_t sync_update_time = sync_entry->UpdateTime(); |
| 401 EXPECT_TRUE(sync_entry->DistilledPath().empty()); | 414 EXPECT_TRUE(sync_entry->DistilledPath().empty()); |
| 402 | 415 |
| 403 EXPECT_EQ(1ul, UnreadSize()); | 416 EXPECT_EQ(1ul, UnreadSize()); |
| 404 EXPECT_EQ(0ul, ReadSize()); | 417 EXPECT_EQ(0ul, ReadSize()); |
| 405 | 418 |
| 406 ReadingListEntry* merged_entry = | 419 ReadingListEntry* merged_entry = |
| 407 model_->SyncMergeEntry(std::move(sync_entry)); | 420 model_->SyncMergeEntry(std::move(sync_entry)); |
| 408 EXPECT_EQ(0ul, UnreadSize()); | 421 EXPECT_EQ(0ul, UnreadSize()); |
| 409 EXPECT_EQ(1ul, ReadSize()); | 422 EXPECT_EQ(1ul, ReadSize()); |
| 410 EXPECT_EQ(merged_entry->DistilledPath(), | 423 EXPECT_EQ(merged_entry->DistilledPath(), |
| 411 base::FilePath("distilled/page.html")); | 424 base::FilePath("distilled/page.html")); |
| 412 EXPECT_EQ(merged_entry->UpdateTime(), sync_update_time); | 425 EXPECT_EQ(merged_entry->UpdateTime(), sync_update_time); |
| 413 EXPECT_EQ(size, merged_entry->DistillationSize()); | 426 EXPECT_EQ(size, merged_entry->DistillationSize()); |
| 414 EXPECT_EQ(time, merged_entry->DistillationTime()); | 427 EXPECT_EQ(time * base::Time::kMicrosecondsPerSecond, |
| 428 merged_entry->DistillationTime()); |
| 415 } | 429 } |
| 416 | 430 |
| 417 // Tests deleting entry. | 431 // Tests deleting entry. |
| 418 TEST_F(ReadingListModelTest, RemoveEntryByUrl) { | 432 TEST_F(ReadingListModelTest, RemoveEntryByUrl) { |
| 419 auto storage = base::MakeUnique<TestReadingListStorage>(this); | 433 auto clock = base::MakeUnique<base::SimpleTestClock>(); |
| 420 SetStorage(std::move(storage)); | 434 auto storage = base::MakeUnique<TestReadingListStorage>(this, clock.get()); |
| 435 SetStorage(std::move(storage), std::move(clock)); |
| 421 model_->AddEntry(GURL("http://example.com"), "sample", | 436 model_->AddEntry(GURL("http://example.com"), "sample", |
| 422 reading_list::ADDED_VIA_CURRENT_APP); | 437 reading_list::ADDED_VIA_CURRENT_APP); |
| 423 ClearCounts(); | 438 ClearCounts(); |
| 424 EXPECT_NE(model_->GetEntryByURL(GURL("http://example.com")), nullptr); | 439 EXPECT_NE(model_->GetEntryByURL(GURL("http://example.com")), nullptr); |
| 425 EXPECT_EQ(1ul, UnreadSize()); | 440 EXPECT_EQ(1ul, UnreadSize()); |
| 426 EXPECT_EQ(0ul, ReadSize()); | 441 EXPECT_EQ(0ul, ReadSize()); |
| 427 model_->RemoveEntryByURL(GURL("http://example.com")); | 442 model_->RemoveEntryByURL(GURL("http://example.com")); |
| 428 AssertObserverCount(0, 0, 0, 0, 1, 0, 0, 0, 1); | 443 AssertObserverCount(0, 0, 0, 0, 1, 0, 0, 0, 1); |
| 429 AssertStorageCount(0, 1); | 444 AssertStorageCount(0, 1); |
| 430 EXPECT_EQ(0ul, UnreadSize()); | 445 EXPECT_EQ(0ul, UnreadSize()); |
| (...skipping 10 matching lines...) Expand all Loading... |
| 441 model_->RemoveEntryByURL(GURL("http://example.com")); | 456 model_->RemoveEntryByURL(GURL("http://example.com")); |
| 442 AssertObserverCount(0, 0, 0, 0, 1, 0, 0, 0, 1); | 457 AssertObserverCount(0, 0, 0, 0, 1, 0, 0, 0, 1); |
| 443 AssertStorageCount(0, 1); | 458 AssertStorageCount(0, 1); |
| 444 EXPECT_EQ(0ul, UnreadSize()); | 459 EXPECT_EQ(0ul, UnreadSize()); |
| 445 EXPECT_EQ(0ul, ReadSize()); | 460 EXPECT_EQ(0ul, ReadSize()); |
| 446 EXPECT_EQ(model_->GetEntryByURL(GURL("http://example.com")), nullptr); | 461 EXPECT_EQ(model_->GetEntryByURL(GURL("http://example.com")), nullptr); |
| 447 } | 462 } |
| 448 | 463 |
| 449 // Tests deleting entry from sync. | 464 // Tests deleting entry from sync. |
| 450 TEST_F(ReadingListModelTest, RemoveSyncEntryByUrl) { | 465 TEST_F(ReadingListModelTest, RemoveSyncEntryByUrl) { |
| 451 auto storage = base::MakeUnique<TestReadingListStorage>(this); | 466 auto clock = base::MakeUnique<base::SimpleTestClock>(); |
| 452 SetStorage(std::move(storage)); | 467 auto storage = base::MakeUnique<TestReadingListStorage>(this, clock.get()); |
| 468 SetStorage(std::move(storage), std::move(clock)); |
| 453 model_->AddEntry(GURL("http://example.com"), "sample", | 469 model_->AddEntry(GURL("http://example.com"), "sample", |
| 454 reading_list::ADDED_VIA_CURRENT_APP); | 470 reading_list::ADDED_VIA_CURRENT_APP); |
| 455 ClearCounts(); | 471 ClearCounts(); |
| 456 EXPECT_NE(model_->GetEntryByURL(GURL("http://example.com")), nullptr); | 472 EXPECT_NE(model_->GetEntryByURL(GURL("http://example.com")), nullptr); |
| 457 EXPECT_EQ(1ul, UnreadSize()); | 473 EXPECT_EQ(1ul, UnreadSize()); |
| 458 EXPECT_EQ(0ul, ReadSize()); | 474 EXPECT_EQ(0ul, ReadSize()); |
| 459 model_->SyncRemoveEntry(GURL("http://example.com")); | 475 model_->SyncRemoveEntry(GURL("http://example.com")); |
| 460 AssertObserverCount(0, 0, 0, 0, 1, 0, 0, 0, 1); | 476 AssertObserverCount(0, 0, 0, 0, 1, 0, 0, 0, 1); |
| 461 AssertStorageCount(0, 0); | 477 AssertStorageCount(0, 0); |
| 462 EXPECT_EQ(0ul, UnreadSize()); | 478 EXPECT_EQ(0ul, UnreadSize()); |
| (...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 624 const GURL gurl("http://example.com"); | 640 const GURL gurl("http://example.com"); |
| 625 const ReadingListEntry& entry = | 641 const ReadingListEntry& entry = |
| 626 model_->AddEntry(gurl, "sample", reading_list::ADDED_VIA_CURRENT_APP); | 642 model_->AddEntry(gurl, "sample", reading_list::ADDED_VIA_CURRENT_APP); |
| 627 ClearCounts(); | 643 ClearCounts(); |
| 628 | 644 |
| 629 const base::FilePath distilled_path("distilled/page.html"); | 645 const base::FilePath distilled_path("distilled/page.html"); |
| 630 const GURL distilled_url("http://example.com/distilled"); | 646 const GURL distilled_url("http://example.com/distilled"); |
| 631 int64_t size = 50; | 647 int64_t size = 50; |
| 632 int64_t time = 100; | 648 int64_t time = 100; |
| 633 model_->SetEntryDistilledInfo(GURL("http://example.com"), distilled_path, | 649 model_->SetEntryDistilledInfo(GURL("http://example.com"), distilled_path, |
| 634 distilled_url, size, time); | 650 distilled_url, size, |
| 651 base::Time::FromTimeT(time)); |
| 635 AssertObserverCount(0, 0, 0, 0, 0, 0, 0, 1, 1); | 652 AssertObserverCount(0, 0, 0, 0, 0, 0, 0, 1, 1); |
| 636 EXPECT_EQ(ReadingListEntry::PROCESSED, entry.DistilledState()); | 653 EXPECT_EQ(ReadingListEntry::PROCESSED, entry.DistilledState()); |
| 637 EXPECT_EQ(distilled_path, entry.DistilledPath()); | 654 EXPECT_EQ(distilled_path, entry.DistilledPath()); |
| 638 EXPECT_EQ(distilled_url, entry.DistilledURL()); | 655 EXPECT_EQ(distilled_url, entry.DistilledURL()); |
| 639 EXPECT_EQ(size, entry.DistillationSize()); | 656 EXPECT_EQ(size, entry.DistillationSize()); |
| 640 EXPECT_EQ(time, entry.DistillationTime()); | 657 EXPECT_EQ(time * base::Time::kMicrosecondsPerSecond, |
| 658 entry.DistillationTime()); |
| 641 } | 659 } |
| 642 | 660 |
| 643 // Tests setting title on read entry. | 661 // Tests setting title on read entry. |
| 644 TEST_F(ReadingListModelTest, UpdateReadEntryTitle) { | 662 TEST_F(ReadingListModelTest, UpdateReadEntryTitle) { |
| 645 const GURL gurl("http://example.com"); | 663 const GURL gurl("http://example.com"); |
| 646 model_->AddEntry(gurl, "sample", reading_list::ADDED_VIA_CURRENT_APP); | 664 model_->AddEntry(gurl, "sample", reading_list::ADDED_VIA_CURRENT_APP); |
| 647 model_->SetReadStatus(gurl, true); | 665 model_->SetReadStatus(gurl, true); |
| 648 const ReadingListEntry* entry = model_->GetEntryByURL(gurl); | 666 const ReadingListEntry* entry = model_->GetEntryByURL(gurl); |
| 649 ClearCounts(); | 667 ClearCounts(); |
| 650 | 668 |
| (...skipping 21 matching lines...) Expand all Loading... |
| 672 model_->AddEntry(gurl, "sample", reading_list::ADDED_VIA_CURRENT_APP); | 690 model_->AddEntry(gurl, "sample", reading_list::ADDED_VIA_CURRENT_APP); |
| 673 model_->SetReadStatus(gurl, true); | 691 model_->SetReadStatus(gurl, true); |
| 674 const ReadingListEntry* entry = model_->GetEntryByURL(gurl); | 692 const ReadingListEntry* entry = model_->GetEntryByURL(gurl); |
| 675 ClearCounts(); | 693 ClearCounts(); |
| 676 | 694 |
| 677 const base::FilePath distilled_path("distilled/page.html"); | 695 const base::FilePath distilled_path("distilled/page.html"); |
| 678 const GURL distilled_url("http://example.com/distilled"); | 696 const GURL distilled_url("http://example.com/distilled"); |
| 679 int64_t size = 50; | 697 int64_t size = 50; |
| 680 int64_t time = 100; | 698 int64_t time = 100; |
| 681 model_->SetEntryDistilledInfo(GURL("http://example.com"), distilled_path, | 699 model_->SetEntryDistilledInfo(GURL("http://example.com"), distilled_path, |
| 682 distilled_url, size, time); | 700 distilled_url, size, |
| 701 base::Time::FromTimeT(time)); |
| 683 AssertObserverCount(0, 0, 0, 0, 0, 0, 0, 1, 1); | 702 AssertObserverCount(0, 0, 0, 0, 0, 0, 0, 1, 1); |
| 684 EXPECT_EQ(ReadingListEntry::PROCESSED, entry->DistilledState()); | 703 EXPECT_EQ(ReadingListEntry::PROCESSED, entry->DistilledState()); |
| 685 EXPECT_EQ(distilled_path, entry->DistilledPath()); | 704 EXPECT_EQ(distilled_path, entry->DistilledPath()); |
| 686 EXPECT_EQ(distilled_url, entry->DistilledURL()); | 705 EXPECT_EQ(distilled_url, entry->DistilledURL()); |
| 687 EXPECT_EQ(size, entry->DistillationSize()); | 706 EXPECT_EQ(size, entry->DistillationSize()); |
| 688 EXPECT_EQ(time, entry->DistillationTime()); | 707 EXPECT_EQ(time * base::Time::kMicrosecondsPerSecond, |
| 708 entry->DistillationTime()); |
| 689 } | 709 } |
| 690 | 710 |
| 691 // Tests that ReadingListModel calls CallbackModelBeingDeleted when destroyed. | 711 // Tests that ReadingListModel calls CallbackModelBeingDeleted when destroyed. |
| 692 TEST_F(ReadingListModelTest, CallbackModelBeingDeleted) { | 712 TEST_F(ReadingListModelTest, CallbackModelBeingDeleted) { |
| 693 AssertObserverCount(1, 0, 0, 0, 0, 0, 0, 0, 0); | 713 AssertObserverCount(1, 0, 0, 0, 0, 0, 0, 0, 0); |
| 694 model_.reset(); | 714 model_.reset(); |
| 695 AssertObserverCount(1, 0, 0, 1, 0, 0, 0, 0, 0); | 715 AssertObserverCount(1, 0, 0, 1, 0, 0, 0, 0, 0); |
| 696 } | 716 } |
| 697 | 717 |
| 698 // Tests that new line characters and spaces are collapsed in title. | 718 // Tests that new line characters and spaces are collapsed in title. |
| 699 TEST_F(ReadingListModelTest, TestTrimmingTitle) { | 719 TEST_F(ReadingListModelTest, TestTrimmingTitle) { |
| 700 const GURL gurl("http://example.com"); | 720 const GURL gurl("http://example.com"); |
| 701 std::string title = "\n This\ttitle \n contains new line \n characters "; | 721 std::string title = "\n This\ttitle \n contains new line \n characters "; |
| 702 model_->AddEntry(gurl, title, reading_list::ADDED_VIA_CURRENT_APP); | 722 model_->AddEntry(gurl, title, reading_list::ADDED_VIA_CURRENT_APP); |
| 703 model_->SetReadStatus(gurl, true); | 723 model_->SetReadStatus(gurl, true); |
| 704 const ReadingListEntry* entry = model_->GetEntryByURL(gurl); | 724 const ReadingListEntry* entry = model_->GetEntryByURL(gurl); |
| 705 EXPECT_EQ(entry->Title(), "This title contains new line characters"); | 725 EXPECT_EQ(entry->Title(), "This title contains new line characters"); |
| 706 model_->SetEntryTitle(gurl, "test"); | 726 model_->SetEntryTitle(gurl, "test"); |
| 707 EXPECT_EQ(entry->Title(), "test"); | 727 EXPECT_EQ(entry->Title(), "test"); |
| 708 model_->SetEntryTitle(gurl, title); | 728 model_->SetEntryTitle(gurl, title); |
| 709 EXPECT_EQ(entry->Title(), "This title contains new line characters"); | 729 EXPECT_EQ(entry->Title(), "This title contains new line characters"); |
| 710 } | 730 } |
| 711 | 731 |
| 712 } // namespace | 732 } // namespace |
| OLD | NEW |