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

Side by Side Diff: components/visitedlink/test/visitedlink_unittest.cc

Issue 1417943002: Load the table of visited links from database file asynchronously. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Add extra comment and fix compilation error. Created 5 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
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 <cstdio> 5 #include <cstdio>
6 #include <string> 6 #include <string>
7 #include <vector> 7 #include <vector>
8 8
9 #include "base/files/file_util.h" 9 #include "base/files/file_util.h"
10 #include "base/location.h" 10 #include "base/location.h"
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after
100 bool TestURLIterator::HasNextURL() const { 100 bool TestURLIterator::HasNextURL() const {
101 return iterator_ != end_; 101 return iterator_ != end_;
102 } 102 }
103 103
104 } // namespace 104 } // namespace
105 105
106 class TrackingVisitedLinkEventListener : public VisitedLinkMaster::Listener { 106 class TrackingVisitedLinkEventListener : public VisitedLinkMaster::Listener {
107 public: 107 public:
108 TrackingVisitedLinkEventListener() 108 TrackingVisitedLinkEventListener()
109 : reset_count_(0), 109 : reset_count_(0),
110 completely_reset_count_(0),
110 add_count_(0) {} 111 add_count_(0) {}
111 112
112 void NewTable(base::SharedMemory* table) override { 113 void NewTable(base::SharedMemory* table) override {
113 if (table) { 114 if (table) {
114 for (std::vector<VisitedLinkSlave>::size_type i = 0; 115 for (std::vector<VisitedLinkSlave>::size_type i = 0;
115 i < g_slaves.size(); i++) { 116 i < g_slaves.size(); i++) {
116 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle(); 117 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle();
117 table->ShareToProcess(base::GetCurrentProcessHandle(), &new_handle); 118 table->ShareToProcess(base::GetCurrentProcessHandle(), &new_handle);
118 g_slaves[i]->OnUpdateVisitedLinks(new_handle); 119 g_slaves[i]->OnUpdateVisitedLinks(new_handle);
119 } 120 }
120 } 121 }
121 } 122 }
122 void Add(VisitedLinkCommon::Fingerprint) override { add_count_++; } 123 void Add(VisitedLinkCommon::Fingerprint) override { add_count_++; }
123 void Reset() override { reset_count_++; } 124 void Reset(bool invalidate_hashes) override {
125 if (invalidate_hashes)
126 completely_reset_count_++;
127 else
128 reset_count_++;
129 }
124 130
125 void SetUp() { 131 void SetUp() {
126 reset_count_ = 0; 132 reset_count_ = 0;
127 add_count_ = 0; 133 add_count_ = 0;
128 } 134 }
129 135
130 int reset_count() const { return reset_count_; } 136 int reset_count() const { return reset_count_; }
137 int completely_reset_count() { return completely_reset_count_; }
131 int add_count() const { return add_count_; } 138 int add_count() const { return add_count_; }
132 139
133 private: 140 private:
134 int reset_count_; 141 int reset_count_;
142 int completely_reset_count_;
135 int add_count_; 143 int add_count_;
136 }; 144 };
137 145
138 class VisitedLinkTest : public testing::Test { 146 class VisitedLinkTest : public testing::Test {
139 protected: 147 protected:
140 // Initializes the visited link objects. Pass in the size that you want a 148 // Initializes the visited link objects. Pass in the size that you want a
141 // freshly created table to be. 0 means use the default. 149 // freshly created table to be. 0 means use the default.
142 // 150 //
143 // |suppress_rebuild| is set when we're not testing rebuilding, see 151 // |suppress_rebuild| is set when we're not testing rebuilding, see
144 // the VisitedLinkMaster constructor. 152 // the VisitedLinkMaster constructor.
145 bool InitVisited(int initial_size, bool suppress_rebuild) { 153 //
154 // |wait_for_io_complete| wait for result of async loading.
155 bool InitVisited(int initial_size,
156 bool suppress_rebuild,
157 bool wait_for_io_complete) {
146 // Initialize the visited link system. 158 // Initialize the visited link system.
147 master_.reset(new VisitedLinkMaster(new TrackingVisitedLinkEventListener(), 159 master_.reset(new VisitedLinkMaster(new TrackingVisitedLinkEventListener(),
148 &delegate_, 160 &delegate_,
149 true, 161 true,
150 suppress_rebuild, visited_file_, 162 suppress_rebuild, visited_file_,
151 initial_size)); 163 initial_size));
152 return master_->Init(); 164 bool result = master_->Init();
165 if (result && wait_for_io_complete) {
166 // Wait for all pending file I/O to be completed.
167 content::RunAllBlockingPoolTasksUntilIdle();
168 }
169 return result;
153 } 170 }
154 171
155 // May be called multiple times (some tests will do this to clear things, 172 // May be called multiple times (some tests will do this to clear things,
156 // and TearDown will do this to make sure eveything is shiny before quitting. 173 // and TearDown will do this to make sure eveything is shiny before quitting.
157 void ClearDB() { 174 void ClearDB() {
158 if (master_.get()) 175 if (master_.get())
159 master_.reset(NULL); 176 master_.reset(NULL);
160 177
161 // Wait for all pending file I/O to be completed. 178 // Wait for all pending file I/O to be completed.
162 content::RunAllBlockingPoolTasksUntilIdle(); 179 content::RunAllBlockingPoolTasksUntilIdle();
163 } 180 }
164 181
165 // Loads the database from disk and makes sure that the same URLs are present 182 // Loads the database from disk and makes sure that the same URLs are present
166 // as were generated by TestIO_Create(). This also checks the URLs with a 183 // as were generated by TestIO_Create(). This also checks the URLs with a
167 // slave to make sure it reads the data properly. 184 // slave to make sure it reads the data properly.
168 void Reload() { 185 void Reload() {
169 // Clean up after our caller, who may have left the database open. 186 // Clean up after our caller, who may have left the database open.
170 ClearDB(); 187 ClearDB();
171 188
172 ASSERT_TRUE(InitVisited(0, true)); 189 ASSERT_TRUE(InitVisited(0, true, true));
190
173 master_->DebugValidate(); 191 master_->DebugValidate();
174 192
175 // check that the table has the proper number of entries 193 // check that the table has the proper number of entries
176 int used_count = master_->GetUsedCount(); 194 int used_count = master_->GetUsedCount();
177 ASSERT_EQ(used_count, g_test_count); 195 ASSERT_EQ(used_count, g_test_count);
178 196
179 // Create a slave database. 197 // Create a slave database.
180 VisitedLinkSlave slave; 198 VisitedLinkSlave slave;
181 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle(); 199 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle();
182 master_->shared_memory()->ShareToProcess( 200 master_->shared_memory()->ShareToProcess(
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
224 base::FilePath visited_file_; 242 base::FilePath visited_file_;
225 243
226 scoped_ptr<VisitedLinkMaster> master_; 244 scoped_ptr<VisitedLinkMaster> master_;
227 TestVisitedLinkDelegate delegate_; 245 TestVisitedLinkDelegate delegate_;
228 content::TestBrowserThreadBundle thread_bundle_; 246 content::TestBrowserThreadBundle thread_bundle_;
229 }; 247 };
230 248
231 // This test creates and reads some databases to make sure the data is 249 // This test creates and reads some databases to make sure the data is
232 // preserved throughout those operations. 250 // preserved throughout those operations.
233 TEST_F(VisitedLinkTest, DatabaseIO) { 251 TEST_F(VisitedLinkTest, DatabaseIO) {
234 ASSERT_TRUE(InitVisited(0, true)); 252 ASSERT_TRUE(InitVisited(0, true, true));
235 253
236 for (int i = 0; i < g_test_count; i++) 254 for (int i = 0; i < g_test_count; i++)
237 master_->AddURL(TestURL(i)); 255 master_->AddURL(TestURL(i));
238 256
239 // Test that the database was written properly 257 // Test that the database was written properly
240 Reload(); 258 Reload();
241 } 259 }
242 260
243 // Checks that we can delete things properly when there are collisions. 261 // Checks that we can delete things properly when there are collisions.
244 TEST_F(VisitedLinkTest, Delete) { 262 TEST_F(VisitedLinkTest, Delete) {
245 static const int32 kInitialSize = 17; 263 static const int32 kInitialSize = 17;
246 ASSERT_TRUE(InitVisited(kInitialSize, true)); 264 ASSERT_TRUE(InitVisited(kInitialSize, true, true));
247 265
248 // Add a cluster from 14-17 wrapping around to 0. These will all hash to the 266 // Add a cluster from 14-17 wrapping around to 0. These will all hash to the
249 // same value. 267 // same value.
250 const VisitedLinkCommon::Fingerprint kFingerprint0 = kInitialSize * 0 + 14; 268 const VisitedLinkCommon::Fingerprint kFingerprint0 = kInitialSize * 0 + 14;
251 const VisitedLinkCommon::Fingerprint kFingerprint1 = kInitialSize * 1 + 14; 269 const VisitedLinkCommon::Fingerprint kFingerprint1 = kInitialSize * 1 + 14;
252 const VisitedLinkCommon::Fingerprint kFingerprint2 = kInitialSize * 2 + 14; 270 const VisitedLinkCommon::Fingerprint kFingerprint2 = kInitialSize * 2 + 14;
253 const VisitedLinkCommon::Fingerprint kFingerprint3 = kInitialSize * 3 + 14; 271 const VisitedLinkCommon::Fingerprint kFingerprint3 = kInitialSize * 3 + 14;
254 const VisitedLinkCommon::Fingerprint kFingerprint4 = kInitialSize * 4 + 14; 272 const VisitedLinkCommon::Fingerprint kFingerprint4 = kInitialSize * 4 + 14;
255 master_->AddFingerprint(kFingerprint0, false); // @14 273 master_->AddFingerprint(kFingerprint0, false); // @14
256 master_->AddFingerprint(kFingerprint1, false); // @15 274 master_->AddFingerprint(kFingerprint1, false); // @15
(...skipping 17 matching lines...) Expand all
274 292
275 EXPECT_EQ(0, master_->used_items_); 293 EXPECT_EQ(0, master_->used_items_);
276 for (int i = 0; i < kInitialSize; i++) 294 for (int i = 0; i < kInitialSize; i++)
277 EXPECT_EQ(zero_fingerprint, master_->hash_table_[i]) << 295 EXPECT_EQ(zero_fingerprint, master_->hash_table_[i]) <<
278 "Hash table has values in it."; 296 "Hash table has values in it.";
279 } 297 }
280 298
281 // When we delete more than kBigDeleteThreshold we trigger different behavior 299 // When we delete more than kBigDeleteThreshold we trigger different behavior
282 // where the entire file is rewritten. 300 // where the entire file is rewritten.
283 TEST_F(VisitedLinkTest, BigDelete) { 301 TEST_F(VisitedLinkTest, BigDelete) {
284 ASSERT_TRUE(InitVisited(16381, true)); 302 ASSERT_TRUE(InitVisited(16381, true, true));
285 303
286 // Add the base set of URLs that won't be deleted. 304 // Add the base set of URLs that won't be deleted.
287 // Reload() will test for these. 305 // Reload() will test for these.
288 for (int32 i = 0; i < g_test_count; i++) 306 for (int32 i = 0; i < g_test_count; i++)
289 master_->AddURL(TestURL(i)); 307 master_->AddURL(TestURL(i));
290 308
291 // Add more URLs than necessary to trigger this case. 309 // Add more URLs than necessary to trigger this case.
292 const int kTestDeleteCount = VisitedLinkMaster::kBigDeleteThreshold + 2; 310 const int kTestDeleteCount = VisitedLinkMaster::kBigDeleteThreshold + 2;
293 URLs urls_to_delete; 311 URLs urls_to_delete;
294 for (int32 i = g_test_count; i < g_test_count + kTestDeleteCount; i++) { 312 for (int32 i = g_test_count; i < g_test_count + kTestDeleteCount; i++) {
295 GURL url(TestURL(i)); 313 GURL url(TestURL(i));
296 master_->AddURL(url); 314 master_->AddURL(url);
297 urls_to_delete.push_back(url); 315 urls_to_delete.push_back(url);
298 } 316 }
299 317
300 TestURLIterator iterator(urls_to_delete); 318 TestURLIterator iterator(urls_to_delete);
301 master_->DeleteURLs(&iterator); 319 master_->DeleteURLs(&iterator);
302 master_->DebugValidate(); 320 master_->DebugValidate();
303 321
304 Reload(); 322 Reload();
305 } 323 }
306 324
307 TEST_F(VisitedLinkTest, DeleteAll) { 325 TEST_F(VisitedLinkTest, DeleteAll) {
308 ASSERT_TRUE(InitVisited(0, true)); 326 ASSERT_TRUE(InitVisited(0, true, true));
309 327
310 { 328 {
311 VisitedLinkSlave slave; 329 VisitedLinkSlave slave;
312 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle(); 330 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle();
313 master_->shared_memory()->ShareToProcess( 331 master_->shared_memory()->ShareToProcess(
314 base::GetCurrentProcessHandle(), &new_handle); 332 base::GetCurrentProcessHandle(), &new_handle);
315 slave.OnUpdateVisitedLinks(new_handle); 333 slave.OnUpdateVisitedLinks(new_handle);
316 g_slaves.push_back(&slave); 334 g_slaves.push_back(&slave);
317 335
318 // Add the test URLs. 336 // Add the test URLs.
(...skipping 14 matching lines...) Expand all
333 EXPECT_FALSE(master_->IsVisited(TestURL(i))); 351 EXPECT_FALSE(master_->IsVisited(TestURL(i)));
334 EXPECT_FALSE(slave.IsVisited(TestURL(i))); 352 EXPECT_FALSE(slave.IsVisited(TestURL(i)));
335 } 353 }
336 354
337 // Close the database. 355 // Close the database.
338 g_slaves.clear(); 356 g_slaves.clear();
339 ClearDB(); 357 ClearDB();
340 } 358 }
341 359
342 // Reopen and validate. 360 // Reopen and validate.
343 ASSERT_TRUE(InitVisited(0, true)); 361 ASSERT_TRUE(InitVisited(0, true, true));
344 master_->DebugValidate(); 362 master_->DebugValidate();
345 EXPECT_EQ(0, master_->GetUsedCount()); 363 EXPECT_EQ(0, master_->GetUsedCount());
346 for (int i = 0; i < g_test_count; i++) 364 for (int i = 0; i < g_test_count; i++)
347 EXPECT_FALSE(master_->IsVisited(TestURL(i))); 365 EXPECT_FALSE(master_->IsVisited(TestURL(i)));
348 } 366 }
349 367
350 // This tests that the master correctly resizes its tables when it gets too 368 // This tests that the master correctly resizes its tables when it gets too
351 // full, notifies its slaves of the change, and updates the disk. 369 // full, notifies its slaves of the change, and updates the disk.
352 TEST_F(VisitedLinkTest, Resizing) { 370 TEST_F(VisitedLinkTest, Resizing) {
353 // Create a very small database. 371 // Create a very small database.
354 const int32 initial_size = 17; 372 const int32 initial_size = 17;
355 ASSERT_TRUE(InitVisited(initial_size, true)); 373 ASSERT_TRUE(InitVisited(initial_size, true, true));
356 374
357 // ...and a slave 375 // ...and a slave
358 VisitedLinkSlave slave; 376 VisitedLinkSlave slave;
359 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle(); 377 base::SharedMemoryHandle new_handle = base::SharedMemory::NULLHandle();
360 master_->shared_memory()->ShareToProcess( 378 master_->shared_memory()->ShareToProcess(
361 base::GetCurrentProcessHandle(), &new_handle); 379 base::GetCurrentProcessHandle(), &new_handle);
362 slave.OnUpdateVisitedLinks(new_handle); 380 slave.OnUpdateVisitedLinks(new_handle);
363 g_slaves.push_back(&slave); 381 g_slaves.push_back(&slave);
364 382
365 int32 used_count = master_->GetUsedCount(); 383 int32 used_count = master_->GetUsedCount();
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
401 // Tests that if the database doesn't exist, it will be rebuilt from history. 419 // Tests that if the database doesn't exist, it will be rebuilt from history.
402 TEST_F(VisitedLinkTest, Rebuild) { 420 TEST_F(VisitedLinkTest, Rebuild) {
403 // Add half of our URLs to history. This needs to be done before we 421 // Add half of our URLs to history. This needs to be done before we
404 // initialize the visited link DB. 422 // initialize the visited link DB.
405 int history_count = g_test_count / 2; 423 int history_count = g_test_count / 2;
406 for (int i = 0; i < history_count; i++) 424 for (int i = 0; i < history_count; i++)
407 delegate_.AddURLForRebuild(TestURL(i)); 425 delegate_.AddURLForRebuild(TestURL(i));
408 426
409 // Initialize the visited link DB. Since the visited links file doesn't exist 427 // Initialize the visited link DB. Since the visited links file doesn't exist
410 // and we don't suppress history rebuilding, this will load from history. 428 // and we don't suppress history rebuilding, this will load from history.
411 ASSERT_TRUE(InitVisited(0, false)); 429 ASSERT_TRUE(InitVisited(0, false, false));
412 430
413 // While the table is rebuilding, add the rest of the URLs to the visited 431 // While the table is rebuilding, add the rest of the URLs to the visited
414 // link system. This isn't guaranteed to happen during the rebuild, so we 432 // link system. This isn't guaranteed to happen during the rebuild, so we
415 // can't be 100% sure we're testing the right thing, but in practice is. 433 // can't be 100% sure we're testing the right thing, but in practice is.
416 // All the adds above will generally take some time queuing up on the 434 // All the adds above will generally take some time queuing up on the
417 // history thread, and it will take a while to catch up to actually 435 // history thread, and it will take a while to catch up to actually
418 // processing the rebuild that has queued behind it. We will generally 436 // processing the rebuild that has queued behind it. We will generally
419 // finish adding all of the URLs before it has even found the first URL. 437 // finish adding all of the URLs before it has even found the first URL.
420 for (int i = history_count; i < g_test_count; i++) 438 for (int i = history_count; i < g_test_count; i++)
421 master_->AddURL(TestURL(i)); 439 master_->AddURL(TestURL(i));
(...skipping 16 matching lines...) Expand all
438 456
439 // Test that all URLs were written to the database properly. 457 // Test that all URLs were written to the database properly.
440 Reload(); 458 Reload();
441 459
442 // Make sure the extra one was *not* written (Reload won't test this). 460 // Make sure the extra one was *not* written (Reload won't test this).
443 EXPECT_FALSE(master_->IsVisited(TestURL(g_test_count))); 461 EXPECT_FALSE(master_->IsVisited(TestURL(g_test_count)));
444 } 462 }
445 463
446 // Test that importing a large number of URLs will work 464 // Test that importing a large number of URLs will work
447 TEST_F(VisitedLinkTest, BigImport) { 465 TEST_F(VisitedLinkTest, BigImport) {
448 ASSERT_TRUE(InitVisited(0, false)); 466 ASSERT_TRUE(InitVisited(0, false, false));
449 467
450 // Before the table rebuilds, add a large number of URLs 468 // Before the table rebuilds, add a large number of URLs
451 int total_count = VisitedLinkMaster::kDefaultTableSize + 10; 469 int total_count = VisitedLinkMaster::kDefaultTableSize + 10;
452 for (int i = 0; i < total_count; i++) 470 for (int i = 0; i < total_count; i++)
453 master_->AddURL(TestURL(i)); 471 master_->AddURL(TestURL(i));
454 472
455 // Wait for the rebuild to complete. 473 // Wait for the rebuild to complete.
456 base::RunLoop run_loop; 474 base::RunLoop run_loop;
457 master_->set_rebuild_complete_task(run_loop.QuitClosure()); 475 master_->set_rebuild_complete_task(run_loop.QuitClosure());
458 run_loop.Run(); 476 run_loop.Run();
459 477
460 // Ensure that the right number of URLs are present 478 // Ensure that the right number of URLs are present
461 int used_count = master_->GetUsedCount(); 479 int used_count = master_->GetUsedCount();
462 ASSERT_EQ(used_count, total_count); 480 ASSERT_EQ(used_count, total_count);
463 } 481 }
464 482
465 TEST_F(VisitedLinkTest, Listener) { 483 TEST_F(VisitedLinkTest, Listener) {
466 ASSERT_TRUE(InitVisited(0, true)); 484 ASSERT_TRUE(InitVisited(0, true, true));
485
486 TrackingVisitedLinkEventListener* listener =
487 static_cast<TrackingVisitedLinkEventListener*>(master_->GetListener());
488
489 // Verify that VisitedLinkMaster::Listener::Reset(true) was never called when
490 // the table was created.
491 EXPECT_EQ(0, listener->completely_reset_count());
467 492
468 // Add test URLs. 493 // Add test URLs.
469 for (int i = 0; i < g_test_count; i++) { 494 for (int i = 0; i < g_test_count; i++) {
470 master_->AddURL(TestURL(i)); 495 master_->AddURL(TestURL(i));
471 ASSERT_EQ(i + 1, master_->GetUsedCount()); 496 ASSERT_EQ(i + 1, master_->GetUsedCount());
472 } 497 }
473 498
474 // Delete an URL. 499 // Delete an URL.
475 URLs urls_to_delete; 500 URLs urls_to_delete;
476 urls_to_delete.push_back(TestURL(0)); 501 urls_to_delete.push_back(TestURL(0));
477 TestURLIterator iterator(urls_to_delete); 502 TestURLIterator iterator(urls_to_delete);
478 master_->DeleteURLs(&iterator); 503 master_->DeleteURLs(&iterator);
479 504
480 // ... and all of the remaining ones. 505 // ... and all of the remaining ones.
481 master_->DeleteAllURLs(); 506 master_->DeleteAllURLs();
482 507
483 TrackingVisitedLinkEventListener* listener =
484 static_cast<TrackingVisitedLinkEventListener*>(master_->GetListener());
485
486 // Verify that VisitedLinkMaster::Listener::Add was called for each added URL. 508 // Verify that VisitedLinkMaster::Listener::Add was called for each added URL.
487 EXPECT_EQ(g_test_count, listener->add_count()); 509 EXPECT_EQ(g_test_count, listener->add_count());
488 // Verify that VisitedLinkMaster::Listener::Reset was called both when one and 510 // Verify that VisitedLinkMaster::Listener::Reset was called both when one and
489 // all URLs are deleted. 511 // all URLs are deleted.
490 EXPECT_EQ(2, listener->reset_count()); 512 EXPECT_EQ(2, listener->reset_count());
513
514 ClearDB();
515
516 ASSERT_TRUE(InitVisited(0, true, true));
517
518 listener =
519 static_cast<TrackingVisitedLinkEventListener*>(master_->GetListener());
520 // Verify that VisitedLinkMaster::Listener::Reset(true) was called when the
521 // table was loaded.
522 EXPECT_EQ(1, listener->completely_reset_count());
491 } 523 }
492 524
493 class VisitCountingContext : public content::TestBrowserContext { 525 class VisitCountingContext : public content::TestBrowserContext {
494 public: 526 public:
495 VisitCountingContext() 527 VisitCountingContext()
496 : add_count_(0), 528 : add_count_(0),
497 add_event_count_(0), 529 add_event_count_(0),
498 reset_event_count_(0), 530 reset_event_count_(0),
531 completely_reset_event_count_(0),
499 new_table_count_(0) {} 532 new_table_count_(0) {}
500 533
501 void CountAddEvent(int by) { 534 void CountAddEvent(int by) {
502 add_count_ += by; 535 add_count_ += by;
503 add_event_count_++; 536 add_event_count_++;
504 } 537 }
505 538
506 void CountResetEvent() { 539 void CountResetEvent() {
507 reset_event_count_++; 540 reset_event_count_++;
508 } 541 }
509 542
543 void CountCompletelyResetEvent() {
544 completely_reset_event_count_++;
545 }
546
510 void CountNewTable() { 547 void CountNewTable() {
511 new_table_count_++; 548 new_table_count_++;
512 } 549 }
513 550
514 int add_count() const { return add_count_; } 551 int add_count() const { return add_count_; }
515 int add_event_count() const { return add_event_count_; } 552 int add_event_count() const { return add_event_count_; }
516 int reset_event_count() const { return reset_event_count_; } 553 int reset_event_count() const { return reset_event_count_; }
554 int completely_reset_event_count() const {
555 return completely_reset_event_count_;
556 }
517 int new_table_count() const { return new_table_count_; } 557 int new_table_count() const { return new_table_count_; }
518 558
519 private: 559 private:
520 int add_count_; 560 int add_count_;
521 int add_event_count_; 561 int add_event_count_;
522 int reset_event_count_; 562 int reset_event_count_;
563 int completely_reset_event_count_;
523 int new_table_count_; 564 int new_table_count_;
524 }; 565 };
525 566
526 // Stub out as little as possible, borrowing from RenderProcessHost. 567 // Stub out as little as possible, borrowing from RenderProcessHost.
527 class VisitRelayingRenderProcessHost : public MockRenderProcessHost { 568 class VisitRelayingRenderProcessHost : public MockRenderProcessHost {
528 public: 569 public:
529 explicit VisitRelayingRenderProcessHost( 570 explicit VisitRelayingRenderProcessHost(
530 content::BrowserContext* browser_context) 571 content::BrowserContext* browser_context)
531 : MockRenderProcessHost(browser_context), widgets_(0) { 572 : MockRenderProcessHost(browser_context), widgets_(0) {
532 content::NotificationService::current()->Notify( 573 content::NotificationService::current()->Notify(
(...skipping 16 matching lines...) Expand all
549 VisitCountingContext* counting_context = 590 VisitCountingContext* counting_context =
550 static_cast<VisitCountingContext*>( 591 static_cast<VisitCountingContext*>(
551 GetBrowserContext()); 592 GetBrowserContext());
552 593
553 if (msg->type() == ChromeViewMsg_VisitedLink_Add::ID) { 594 if (msg->type() == ChromeViewMsg_VisitedLink_Add::ID) {
554 base::PickleIterator iter(*msg); 595 base::PickleIterator iter(*msg);
555 std::vector<uint64> fingerprints; 596 std::vector<uint64> fingerprints;
556 CHECK(IPC::ReadParam(msg, &iter, &fingerprints)); 597 CHECK(IPC::ReadParam(msg, &iter, &fingerprints));
557 counting_context->CountAddEvent(fingerprints.size()); 598 counting_context->CountAddEvent(fingerprints.size());
558 } else if (msg->type() == ChromeViewMsg_VisitedLink_Reset::ID) { 599 } else if (msg->type() == ChromeViewMsg_VisitedLink_Reset::ID) {
559 counting_context->CountResetEvent(); 600 base::PickleIterator iter(*msg);
601 bool invalidate_hashes;
602 CHECK(IPC::ReadParam(msg, &iter, &invalidate_hashes));
603 if (invalidate_hashes)
604 counting_context->CountCompletelyResetEvent();
605 else
606 counting_context->CountResetEvent();
560 } else if (msg->type() == ChromeViewMsg_VisitedLink_NewTable::ID) { 607 } else if (msg->type() == ChromeViewMsg_VisitedLink_NewTable::ID) {
561 counting_context->CountNewTable(); 608 counting_context->CountNewTable();
562 } 609 }
563 610
564 delete msg; 611 delete msg;
565 return true; 612 return true;
566 } 613 }
567 614
568 private: 615 private:
569 int widgets_; 616 int widgets_;
(...skipping 28 matching lines...) Expand all
598 // of teardown because it posts a task to close a file handle, and 645 // of teardown because it posts a task to close a file handle, and
599 // we need to make sure we've finished all file related work 646 // we need to make sure we've finished all file related work
600 // before our superclass sets about destroying the scoped temp 647 // before our superclass sets about destroying the scoped temp
601 // directory. 648 // directory.
602 master_.reset(); 649 master_.reset();
603 RenderViewHostTestHarness::TearDown(); 650 RenderViewHostTestHarness::TearDown();
604 } 651 }
605 652
606 content::BrowserContext* CreateBrowserContext() override { 653 content::BrowserContext* CreateBrowserContext() override {
607 VisitCountingContext* context = new VisitCountingContext(); 654 VisitCountingContext* context = new VisitCountingContext();
608 master_.reset(new VisitedLinkMaster(context, &delegate_, true)); 655 CreateVisitedLinkMaster(context);
609 master_->Init();
610 return context; 656 return context;
611 } 657 }
612 658
613 VisitCountingContext* context() { 659 VisitCountingContext* context() {
614 return static_cast<VisitCountingContext*>(browser_context()); 660 return static_cast<VisitCountingContext*>(browser_context());
615 } 661 }
616 662
617 VisitedLinkMaster* master() const { 663 VisitedLinkMaster* master() const {
618 return master_.get(); 664 return master_.get();
619 } 665 }
620 666
621 void WaitForCoalescence() { 667 void WaitForCoalescence() {
622 // Let the timer fire. 668 // Let the timer fire.
623 // 669 //
624 // TODO(ajwong): This is horrid! What is the right synchronization method? 670 // TODO(ajwong): This is horrid! What is the right synchronization method?
625 base::RunLoop run_loop; 671 base::RunLoop run_loop;
626 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( 672 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
627 FROM_HERE, run_loop.QuitClosure(), 673 FROM_HERE, run_loop.QuitClosure(),
628 base::TimeDelta::FromMilliseconds(110)); 674 base::TimeDelta::FromMilliseconds(110));
629 run_loop.Run(); 675 run_loop.Run();
630 } 676 }
631 677
632 protected: 678 protected:
679 void CreateVisitedLinkMaster(content::BrowserContext* browser_context) {
680 master_.reset(new VisitedLinkMaster(browser_context, &delegate_, true));
681 master_->Init();
682 }
683
633 VisitedLinkRenderProcessHostFactory vc_rph_factory_; 684 VisitedLinkRenderProcessHostFactory vc_rph_factory_;
634 685
635 private:
636 TestVisitedLinkDelegate delegate_; 686 TestVisitedLinkDelegate delegate_;
637 scoped_ptr<VisitedLinkMaster> master_; 687 scoped_ptr<VisitedLinkMaster> master_;
638 }; 688 };
639 689
640 TEST_F(VisitedLinkEventsTest, Coalescence) { 690 TEST_F(VisitedLinkEventsTest, Coalescence) {
691 // Waiting complete rebuild the table.
692 content::RunAllBlockingPoolTasksUntilIdle();
693
694 WaitForCoalescence();
695
696 // After rebuild table expect reset event.
697 EXPECT_EQ(1, context()->reset_event_count());
698
641 // add some URLs to master. 699 // add some URLs to master.
642 // Add a few URLs. 700 // Add a few URLs.
643 master()->AddURL(GURL("http://acidtests.org/")); 701 master()->AddURL(GURL("http://acidtests.org/"));
644 master()->AddURL(GURL("http://google.com/")); 702 master()->AddURL(GURL("http://google.com/"));
645 master()->AddURL(GURL("http://chromium.org/")); 703 master()->AddURL(GURL("http://chromium.org/"));
646 // Just for kicks, add a duplicate URL. This shouldn't increase the resulting 704 // Just for kicks, add a duplicate URL. This shouldn't increase the resulting
647 master()->AddURL(GURL("http://acidtests.org/")); 705 master()->AddURL(GURL("http://acidtests.org/"));
648 706
649 // Make sure that coalescing actually occurs. There should be no links or 707 // Make sure that coalescing actually occurs. There should be no links or
650 // events received by the renderer. 708 // events received by the renderer.
(...skipping 28 matching lines...) Expand all
679 737
680 // Ensure that the coalescing does not resume after resetting. 738 // Ensure that the coalescing does not resume after resetting.
681 master()->AddURL(GURL("http://build.chromium.org/")); 739 master()->AddURL(GURL("http://build.chromium.org/"));
682 master()->DeleteAllURLs(); 740 master()->DeleteAllURLs();
683 741
684 WaitForCoalescence(); 742 WaitForCoalescence();
685 743
686 // We should have no change in results except for one new reset event. 744 // We should have no change in results except for one new reset event.
687 EXPECT_EQ(6, context()->add_count()); 745 EXPECT_EQ(6, context()->add_count());
688 EXPECT_EQ(2, context()->add_event_count()); 746 EXPECT_EQ(2, context()->add_event_count());
689 EXPECT_EQ(1, context()->reset_event_count()); 747 EXPECT_EQ(2, context()->reset_event_count());
690 } 748 }
691 749
692 TEST_F(VisitedLinkEventsTest, Basics) { 750 TEST_F(VisitedLinkEventsTest, Basics) {
693 RenderViewHostTester::For(rvh())->CreateTestRenderView( 751 RenderViewHostTester::For(rvh())->CreateTestRenderView(
694 base::string16(), MSG_ROUTING_NONE, MSG_ROUTING_NONE, -1, false); 752 base::string16(), MSG_ROUTING_NONE, MSG_ROUTING_NONE, -1, false);
695 753
754 // Waiting complete rebuild the table.
755 content::RunAllBlockingPoolTasksUntilIdle();
756
757 WaitForCoalescence();
758
759 // After rebuild table expect reset event.
760 EXPECT_EQ(1, context()->reset_event_count());
761
696 // Add a few URLs. 762 // Add a few URLs.
697 master()->AddURL(GURL("http://acidtests.org/")); 763 master()->AddURL(GURL("http://acidtests.org/"));
698 master()->AddURL(GURL("http://google.com/")); 764 master()->AddURL(GURL("http://google.com/"));
699 master()->AddURL(GURL("http://chromium.org/")); 765 master()->AddURL(GURL("http://chromium.org/"));
700 766
701 WaitForCoalescence(); 767 WaitForCoalescence();
702 768
703 // We now should have 1 add event. 769 // We now should have 1 add event.
704 EXPECT_EQ(1, context()->add_event_count()); 770 EXPECT_EQ(1, context()->add_event_count());
705 EXPECT_EQ(0, context()->reset_event_count()); 771 EXPECT_EQ(1, context()->reset_event_count());
706 772
707 master()->DeleteAllURLs(); 773 master()->DeleteAllURLs();
708 774
709 WaitForCoalescence(); 775 WaitForCoalescence();
710 776
711 // We should have no change in add results, plus one new reset event. 777 // We should have no change in add results, plus one new reset event.
712 EXPECT_EQ(1, context()->add_event_count()); 778 EXPECT_EQ(1, context()->add_event_count());
713 EXPECT_EQ(1, context()->reset_event_count()); 779 EXPECT_EQ(2, context()->reset_event_count());
714 } 780 }
715 781
716 TEST_F(VisitedLinkEventsTest, TabVisibility) { 782 TEST_F(VisitedLinkEventsTest, TabVisibility) {
717 RenderViewHostTester::For(rvh())->CreateTestRenderView( 783 RenderViewHostTester::For(rvh())->CreateTestRenderView(
718 base::string16(), MSG_ROUTING_NONE, MSG_ROUTING_NONE, -1, false); 784 base::string16(), MSG_ROUTING_NONE, MSG_ROUTING_NONE, -1, false);
719 785
786 // Waiting complete rebuild the table.
787 content::RunAllBlockingPoolTasksUntilIdle();
788
789 WaitForCoalescence();
790
791 // After rebuild table expect reset event.
792 EXPECT_EQ(1, context()->reset_event_count());
793
720 // Simulate tab becoming inactive. 794 // Simulate tab becoming inactive.
721 RenderViewHostTester::For(rvh())->SimulateWasHidden(); 795 RenderViewHostTester::For(rvh())->SimulateWasHidden();
722 796
723 // Add a few URLs. 797 // Add a few URLs.
724 master()->AddURL(GURL("http://acidtests.org/")); 798 master()->AddURL(GURL("http://acidtests.org/"));
725 master()->AddURL(GURL("http://google.com/")); 799 master()->AddURL(GURL("http://google.com/"));
726 master()->AddURL(GURL("http://chromium.org/")); 800 master()->AddURL(GURL("http://chromium.org/"));
727 801
728 WaitForCoalescence(); 802 WaitForCoalescence();
729 803
730 // We shouldn't have any events. 804 // We shouldn't have any events.
731 EXPECT_EQ(0, context()->add_event_count()); 805 EXPECT_EQ(0, context()->add_event_count());
732 EXPECT_EQ(0, context()->reset_event_count()); 806 EXPECT_EQ(1, context()->reset_event_count());
733 807
734 // Simulate the tab becoming active. 808 // Simulate the tab becoming active.
735 RenderViewHostTester::For(rvh())->SimulateWasShown(); 809 RenderViewHostTester::For(rvh())->SimulateWasShown();
736 810
737 // We should now have 3 add events, still no reset events. 811 // We should now have 3 add events, still no reset events.
738 EXPECT_EQ(1, context()->add_event_count()); 812 EXPECT_EQ(1, context()->add_event_count());
739 EXPECT_EQ(0, context()->reset_event_count()); 813 EXPECT_EQ(1, context()->reset_event_count());
740 814
741 // Deactivate the tab again. 815 // Deactivate the tab again.
742 RenderViewHostTester::For(rvh())->SimulateWasHidden(); 816 RenderViewHostTester::For(rvh())->SimulateWasHidden();
743 817
744 // Add a bunch of URLs (over 50) to exhaust the link event buffer. 818 // Add a bunch of URLs (over 50) to exhaust the link event buffer.
745 for (int i = 0; i < 100; i++) 819 for (int i = 0; i < 100; i++)
746 master()->AddURL(TestURL(i)); 820 master()->AddURL(TestURL(i));
747 821
748 WaitForCoalescence(); 822 WaitForCoalescence();
749 823
750 // Again, no change in events until tab is active. 824 // Again, no change in events until tab is active.
751 EXPECT_EQ(1, context()->add_event_count()); 825 EXPECT_EQ(1, context()->add_event_count());
752 EXPECT_EQ(0, context()->reset_event_count()); 826 EXPECT_EQ(1, context()->reset_event_count());
753 827
754 // Activate the tab. 828 // Activate the tab.
755 RenderViewHostTester::For(rvh())->SimulateWasShown(); 829 RenderViewHostTester::For(rvh())->SimulateWasShown();
756 830
757 // We should have only one more reset event. 831 // We should have only one more reset event.
758 EXPECT_EQ(1, context()->add_event_count()); 832 EXPECT_EQ(1, context()->add_event_count());
759 EXPECT_EQ(1, context()->reset_event_count()); 833 EXPECT_EQ(2, context()->reset_event_count());
760 } 834 }
761 835
762 // Tests that VisitedLink ignores renderer process creation notification for a 836 // Tests that VisitedLink ignores renderer process creation notification for a
763 // different context. 837 // different context.
764 TEST_F(VisitedLinkEventsTest, IgnoreRendererCreationFromDifferentContext) { 838 TEST_F(VisitedLinkEventsTest, IgnoreRendererCreationFromDifferentContext) {
765 VisitCountingContext different_context; 839 VisitCountingContext different_context;
766 VisitRelayingRenderProcessHost different_process_host(&different_context); 840 VisitRelayingRenderProcessHost different_process_host(&different_context);
767 841
768 content::NotificationService::current()->Notify( 842 content::NotificationService::current()->Notify(
769 content::NOTIFICATION_RENDERER_PROCESS_CREATED, 843 content::NOTIFICATION_RENDERER_PROCESS_CREATED,
770 content::Source<content::RenderProcessHost>(&different_process_host), 844 content::Source<content::RenderProcessHost>(&different_process_host),
771 content::NotificationService::NoDetails()); 845 content::NotificationService::NoDetails());
772 WaitForCoalescence(); 846 WaitForCoalescence();
773 847
774 EXPECT_EQ(0, different_context.new_table_count()); 848 EXPECT_EQ(0, different_context.new_table_count());
775 } 849 }
776 850
851 class VisitedLinkCompletelyResetEventTest : public VisitedLinkEventsTest {
852 public:
853 content::BrowserContext* CreateBrowserContext() override {
854 VisitCountingContext* context = new VisitCountingContext();
855 CreateVisitedLinkFile(context);
856 CreateVisitedLinkMaster(context);
857 return context;
858 }
859
860 void CreateVisitedLinkFile(content::BrowserContext* browser_context) {
861 base::FilePath visited_file =
862 browser_context->GetPath().Append(FILE_PATH_LITERAL("Visited Links"));
863 scoped_ptr<VisitedLinkMaster> master(
864 new VisitedLinkMaster(new TrackingVisitedLinkEventListener(),
865 &delegate_, true, true, visited_file, 0));
866 master->Init();
867 // Waiting complete create the table.
868 content::RunAllBlockingPoolTasksUntilIdle();
869
870 master.reset();
871 // Wait for all pending file I/O to be completed.
872 content::RunAllBlockingPoolTasksUntilIdle();
873 }
874 };
875
876 TEST_F(VisitedLinkCompletelyResetEventTest, LoadTable) {
877 // Waiting complete loading the table.
878 content::RunAllBlockingPoolTasksUntilIdle();
879
880 WaitForCoalescence();
881
882 // After load table expect completely reset event.
883 EXPECT_EQ(1, context()->completely_reset_event_count());
884 }
885
777 } // namespace visitedlink 886 } // namespace visitedlink
OLDNEW
« no previous file with comments | « components/visitedlink/test/visitedlink_perftest.cc ('k') | third_party/WebKit/Source/core/dom/VisitedLinkState.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698