OLD | NEW |
(Empty) | |
| 1 // Copyright 2014 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 <set> |
| 6 #include <utility> |
| 7 #include <vector> |
| 8 |
| 9 #include "base/message_loop/message_loop.h" |
| 10 #include "base/strings/utf_string_conversions.h" |
| 11 #include "chrome/browser/predictors/predictor_database.h" |
| 12 #include "chrome/browser/predictors/resource_prefetch_predictor_tables.h" |
| 13 #include "chrome/test/base/testing_profile.h" |
| 14 #include "content/public/test/test_browser_thread.h" |
| 15 #include "sql/statement.h" |
| 16 #include "testing/gtest/include/gtest/gtest.h" |
| 17 |
| 18 namespace predictors { |
| 19 |
| 20 class ResourcePrefetchPredictorTablesTest : public testing::Test { |
| 21 public: |
| 22 ResourcePrefetchPredictorTablesTest(); |
| 23 virtual ~ResourcePrefetchPredictorTablesTest(); |
| 24 virtual void SetUp() OVERRIDE; |
| 25 virtual void TearDown() OVERRIDE; |
| 26 |
| 27 protected: |
| 28 void TestGetAllData(); |
| 29 void TestUpdateData(); |
| 30 void TestDeleteData(); |
| 31 void TestDeleteSingleDataPoint(); |
| 32 void TestDeleteAllData(); |
| 33 |
| 34 base::MessageLoop loop_; |
| 35 content::TestBrowserThread db_thread_; |
| 36 TestingProfile profile_; |
| 37 scoped_ptr<PredictorDatabase> db_; |
| 38 scoped_refptr<ResourcePrefetchPredictorTables> tables_; |
| 39 |
| 40 private: |
| 41 typedef ResourcePrefetchPredictorTables::ResourceRow ResourceRow; |
| 42 typedef std::vector<ResourceRow> ResourceRows; |
| 43 typedef ResourcePrefetchPredictorTables::PrefetchData PrefetchData; |
| 44 typedef ResourcePrefetchPredictorTables::PrefetchDataMap PrefetchDataMap; |
| 45 |
| 46 // Initializes the tables, |test_url_data_| and |test_host_data_|. |
| 47 void InitializeSampleData(); |
| 48 |
| 49 // Checks that the input PrefetchData are the same, although the resources |
| 50 // can be in different order. |
| 51 void TestPrefetchDataAreEqual(const PrefetchDataMap& lhs, |
| 52 const PrefetchDataMap& rhs) const; |
| 53 void TestResourceRowsAreEqual(const ResourceRows& lhs, |
| 54 const ResourceRows& rhs) const; |
| 55 |
| 56 void AddKey(PrefetchDataMap* m, const std::string& key) const; |
| 57 |
| 58 // Useful for debugging test. |
| 59 void PrintPrefetchData(const PrefetchData& data) const { |
| 60 LOG(ERROR) << "[" << data.key_type << "," << data.primary_key |
| 61 << "," << data.last_visit.ToInternalValue() << "]"; |
| 62 for (ResourceRows::const_iterator it = data.resources.begin(); |
| 63 it != data.resources.end(); ++it) { |
| 64 LOG(ERROR) << "\t\t" << it->resource_url << "\t" << it->resource_type |
| 65 << "\t" << it->number_of_hits << "\t" << it->number_of_misses |
| 66 << "\t" << it->consecutive_misses |
| 67 << "\t" << it->average_position |
| 68 << "\t" << it->score; |
| 69 } |
| 70 } |
| 71 |
| 72 PrefetchDataMap test_url_data_; |
| 73 PrefetchDataMap test_host_data_; |
| 74 }; |
| 75 |
| 76 class ResourcePrefetchPredictorTablesReopenTest |
| 77 : public ResourcePrefetchPredictorTablesTest { |
| 78 public: |
| 79 virtual void SetUp() OVERRIDE { |
| 80 // Write data to the table, and then reopen the db. |
| 81 ResourcePrefetchPredictorTablesTest::SetUp(); |
| 82 ResourcePrefetchPredictorTablesTest::TearDown(); |
| 83 |
| 84 db_.reset(new PredictorDatabase(&profile_)); |
| 85 loop_.RunUntilIdle(); |
| 86 tables_ = db_->resource_prefetch_tables(); |
| 87 } |
| 88 }; |
| 89 |
| 90 ResourcePrefetchPredictorTablesTest::ResourcePrefetchPredictorTablesTest() |
| 91 : loop_(base::MessageLoop::TYPE_DEFAULT), |
| 92 db_thread_(content::BrowserThread::DB, &loop_), |
| 93 db_(new PredictorDatabase(&profile_)), |
| 94 tables_(db_->resource_prefetch_tables()) { |
| 95 loop_.RunUntilIdle(); |
| 96 } |
| 97 |
| 98 ResourcePrefetchPredictorTablesTest::~ResourcePrefetchPredictorTablesTest() { |
| 99 } |
| 100 |
| 101 void ResourcePrefetchPredictorTablesTest::SetUp() { |
| 102 tables_->DeleteAllData(); |
| 103 InitializeSampleData(); |
| 104 } |
| 105 |
| 106 void ResourcePrefetchPredictorTablesTest::TearDown() { |
| 107 tables_ = NULL; |
| 108 db_.reset(); |
| 109 loop_.RunUntilIdle(); |
| 110 } |
| 111 |
| 112 void ResourcePrefetchPredictorTablesTest::TestGetAllData() { |
| 113 PrefetchDataMap actual_url_data, actual_host_data; |
| 114 tables_->GetAllData(&actual_url_data, &actual_host_data); |
| 115 |
| 116 TestPrefetchDataAreEqual(test_url_data_, actual_url_data); |
| 117 TestPrefetchDataAreEqual(test_host_data_, actual_host_data); |
| 118 } |
| 119 |
| 120 void ResourcePrefetchPredictorTablesTest::TestDeleteData() { |
| 121 std::vector<std::string> urls_to_delete, hosts_to_delete; |
| 122 urls_to_delete.push_back("http://www.google.com"); |
| 123 urls_to_delete.push_back("http://www.yahoo.com"); |
| 124 hosts_to_delete.push_back("www.yahoo.com"); |
| 125 |
| 126 tables_->DeleteData(urls_to_delete, hosts_to_delete); |
| 127 |
| 128 PrefetchDataMap actual_url_data, actual_host_data; |
| 129 tables_->GetAllData(&actual_url_data, &actual_host_data); |
| 130 |
| 131 PrefetchDataMap expected_url_data, expected_host_data; |
| 132 AddKey(&expected_url_data, "http://www.reddit.com"); |
| 133 AddKey(&expected_host_data, "www.facebook.com"); |
| 134 |
| 135 TestPrefetchDataAreEqual(expected_url_data, actual_url_data); |
| 136 TestPrefetchDataAreEqual(expected_host_data, actual_host_data); |
| 137 } |
| 138 |
| 139 void ResourcePrefetchPredictorTablesTest::TestDeleteSingleDataPoint() { |
| 140 // Delete a URL. |
| 141 tables_->DeleteSingleDataPoint("http://www.reddit.com", |
| 142 PREFETCH_KEY_TYPE_URL); |
| 143 |
| 144 PrefetchDataMap actual_url_data, actual_host_data; |
| 145 tables_->GetAllData(&actual_url_data, &actual_host_data); |
| 146 |
| 147 PrefetchDataMap expected_url_data; |
| 148 AddKey(&expected_url_data, "http://www.google.com"); |
| 149 AddKey(&expected_url_data, "http://www.yahoo.com"); |
| 150 |
| 151 TestPrefetchDataAreEqual(expected_url_data, actual_url_data); |
| 152 TestPrefetchDataAreEqual(test_host_data_, actual_host_data); |
| 153 |
| 154 // Delete a host. |
| 155 tables_->DeleteSingleDataPoint("www.facebook.com", PREFETCH_KEY_TYPE_HOST); |
| 156 actual_url_data.clear(); |
| 157 actual_host_data.clear(); |
| 158 tables_->GetAllData(&actual_url_data, &actual_host_data); |
| 159 |
| 160 PrefetchDataMap expected_host_data; |
| 161 AddKey(&expected_host_data, "www.yahoo.com"); |
| 162 |
| 163 TestPrefetchDataAreEqual(expected_url_data, actual_url_data); |
| 164 TestPrefetchDataAreEqual(expected_host_data, actual_host_data); |
| 165 } |
| 166 |
| 167 void ResourcePrefetchPredictorTablesTest::TestUpdateData() { |
| 168 PrefetchData google(PREFETCH_KEY_TYPE_URL, "http://www.google.com"); |
| 169 google.last_visit = base::Time::FromInternalValue(10); |
| 170 google.resources.push_back(ResourceRow(std::string(), |
| 171 "http://www.google.com/style.css", |
| 172 content::RESOURCE_TYPE_STYLESHEET, |
| 173 6, |
| 174 2, |
| 175 0, |
| 176 1.0)); |
| 177 google.resources.push_back(ResourceRow(std::string(), |
| 178 "http://www.google.com/image.png", |
| 179 content::RESOURCE_TYPE_IMAGE, |
| 180 6, |
| 181 4, |
| 182 1, |
| 183 4.2)); |
| 184 google.resources.push_back(ResourceRow(std::string(), |
| 185 "http://www.google.com/a.xml", |
| 186 content::RESOURCE_TYPE_LAST_TYPE, |
| 187 1, |
| 188 0, |
| 189 0, |
| 190 6.1)); |
| 191 google.resources |
| 192 .push_back(ResourceRow(std::string(), |
| 193 "http://www.resources.google.com/script.js", |
| 194 content::RESOURCE_TYPE_SCRIPT, |
| 195 12, |
| 196 0, |
| 197 0, |
| 198 8.5)); |
| 199 |
| 200 PrefetchData yahoo(PREFETCH_KEY_TYPE_HOST, "www.yahoo.com"); |
| 201 yahoo.last_visit = base::Time::FromInternalValue(7); |
| 202 yahoo.resources.push_back(ResourceRow(std::string(), |
| 203 "http://www.yahoo.com/image.png", |
| 204 content::RESOURCE_TYPE_IMAGE, |
| 205 120, |
| 206 1, |
| 207 1, |
| 208 10.0)); |
| 209 |
| 210 tables_->UpdateData(google, yahoo); |
| 211 |
| 212 PrefetchDataMap actual_url_data, actual_host_data; |
| 213 tables_->GetAllData(&actual_url_data, &actual_host_data); |
| 214 |
| 215 PrefetchDataMap expected_url_data, expected_host_data; |
| 216 AddKey(&expected_url_data, "http://www.reddit.com"); |
| 217 AddKey(&expected_url_data, "http://www.yahoo.com"); |
| 218 expected_url_data.insert(std::make_pair("http://www.google.com", google)); |
| 219 |
| 220 AddKey(&expected_host_data, "www.facebook.com"); |
| 221 expected_host_data.insert(std::make_pair("www.yahoo.com", yahoo)); |
| 222 |
| 223 TestPrefetchDataAreEqual(expected_url_data, actual_url_data); |
| 224 TestPrefetchDataAreEqual(expected_host_data, actual_host_data); |
| 225 } |
| 226 |
| 227 void ResourcePrefetchPredictorTablesTest::TestDeleteAllData() { |
| 228 tables_->DeleteAllData(); |
| 229 |
| 230 PrefetchDataMap actual_url_data, actual_host_data; |
| 231 tables_->GetAllData(&actual_url_data, &actual_host_data); |
| 232 EXPECT_TRUE(actual_url_data.empty()); |
| 233 EXPECT_TRUE(actual_host_data.empty()); |
| 234 } |
| 235 |
| 236 void ResourcePrefetchPredictorTablesTest::TestPrefetchDataAreEqual( |
| 237 const PrefetchDataMap& lhs, |
| 238 const PrefetchDataMap& rhs) const { |
| 239 EXPECT_EQ(lhs.size(), rhs.size()); |
| 240 |
| 241 for (PrefetchDataMap::const_iterator rhs_it = rhs.begin(); |
| 242 rhs_it != rhs.end(); ++rhs_it) { |
| 243 PrefetchDataMap::const_iterator lhs_it = lhs.find(rhs_it->first); |
| 244 ASSERT_TRUE(lhs_it != lhs.end()) << rhs_it->first; |
| 245 |
| 246 TestResourceRowsAreEqual(lhs_it->second.resources, |
| 247 rhs_it->second.resources); |
| 248 } |
| 249 } |
| 250 |
| 251 void ResourcePrefetchPredictorTablesTest::TestResourceRowsAreEqual( |
| 252 const ResourceRows& lhs, |
| 253 const ResourceRows& rhs) const { |
| 254 EXPECT_EQ(lhs.size(), rhs.size()); |
| 255 |
| 256 std::set<GURL> resources_seen; |
| 257 for (ResourceRows::const_iterator rhs_it = rhs.begin(); |
| 258 rhs_it != rhs.end(); ++rhs_it) { |
| 259 const GURL& resource = rhs_it->resource_url; |
| 260 EXPECT_FALSE(ContainsKey(resources_seen, resource)); |
| 261 |
| 262 for (ResourceRows::const_iterator lhs_it = lhs.begin(); |
| 263 lhs_it != lhs.end(); ++lhs_it) { |
| 264 if (*rhs_it == *lhs_it) { |
| 265 resources_seen.insert(resource); |
| 266 break; |
| 267 } |
| 268 } |
| 269 EXPECT_TRUE(ContainsKey(resources_seen, resource)); |
| 270 } |
| 271 EXPECT_EQ(lhs.size(), resources_seen.size()); |
| 272 } |
| 273 |
| 274 void ResourcePrefetchPredictorTablesTest::AddKey(PrefetchDataMap* m, |
| 275 const std::string& key) const { |
| 276 PrefetchDataMap::const_iterator it = test_url_data_.find(key); |
| 277 if (it != test_url_data_.end()) { |
| 278 m->insert(std::make_pair(it->first, it->second)); |
| 279 return; |
| 280 } |
| 281 it = test_host_data_.find(key); |
| 282 ASSERT_TRUE(it != test_host_data_.end()); |
| 283 m->insert(std::make_pair(it->first, it->second)); |
| 284 } |
| 285 |
| 286 void ResourcePrefetchPredictorTablesTest::InitializeSampleData() { |
| 287 { // Url data. |
| 288 PrefetchData google(PREFETCH_KEY_TYPE_URL, "http://www.google.com"); |
| 289 google.last_visit = base::Time::FromInternalValue(1); |
| 290 google.resources.push_back(ResourceRow(std::string(), |
| 291 "http://www.google.com/style.css", |
| 292 content::RESOURCE_TYPE_STYLESHEET, |
| 293 5, |
| 294 2, |
| 295 1, |
| 296 1.1)); |
| 297 google.resources.push_back(ResourceRow(std::string(), |
| 298 "http://www.google.com/script.js", |
| 299 content::RESOURCE_TYPE_SCRIPT, |
| 300 4, |
| 301 0, |
| 302 1, |
| 303 2.1)); |
| 304 google.resources.push_back(ResourceRow(std::string(), |
| 305 "http://www.google.com/image.png", |
| 306 content::RESOURCE_TYPE_IMAGE, |
| 307 6, |
| 308 3, |
| 309 0, |
| 310 2.2)); |
| 311 google.resources.push_back(ResourceRow(std::string(), |
| 312 "http://www.google.com/a.font", |
| 313 content::RESOURCE_TYPE_LAST_TYPE, |
| 314 2, |
| 315 0, |
| 316 0, |
| 317 5.1)); |
| 318 google.resources |
| 319 .push_back(ResourceRow(std::string(), |
| 320 "http://www.resources.google.com/script.js", |
| 321 content::RESOURCE_TYPE_SCRIPT, |
| 322 11, |
| 323 0, |
| 324 0, |
| 325 8.5)); |
| 326 |
| 327 PrefetchData reddit(PREFETCH_KEY_TYPE_URL, "http://www.reddit.com"); |
| 328 reddit.last_visit = base::Time::FromInternalValue(2); |
| 329 reddit.resources |
| 330 .push_back(ResourceRow(std::string(), |
| 331 "http://reddit-resource.com/script1.js", |
| 332 content::RESOURCE_TYPE_SCRIPT, |
| 333 4, |
| 334 0, |
| 335 1, |
| 336 1.0)); |
| 337 reddit.resources |
| 338 .push_back(ResourceRow(std::string(), |
| 339 "http://reddit-resource.com/script2.js", |
| 340 content::RESOURCE_TYPE_SCRIPT, |
| 341 2, |
| 342 0, |
| 343 0, |
| 344 2.1)); |
| 345 |
| 346 PrefetchData yahoo(PREFETCH_KEY_TYPE_URL, "http://www.yahoo.com"); |
| 347 yahoo.last_visit = base::Time::FromInternalValue(3); |
| 348 yahoo.resources.push_back(ResourceRow(std::string(), |
| 349 "http://www.google.com/image.png", |
| 350 content::RESOURCE_TYPE_IMAGE, |
| 351 20, |
| 352 1, |
| 353 0, |
| 354 10.0)); |
| 355 |
| 356 test_url_data_.clear(); |
| 357 test_url_data_.insert(std::make_pair("http://www.google.com", google)); |
| 358 test_url_data_.insert(std::make_pair("http://www.reddit.com", reddit)); |
| 359 test_url_data_.insert(std::make_pair("http://www.yahoo.com", yahoo)); |
| 360 |
| 361 PrefetchData empty_host_data(PREFETCH_KEY_TYPE_HOST, std::string()); |
| 362 tables_->UpdateData(google, empty_host_data); |
| 363 tables_->UpdateData(reddit, empty_host_data); |
| 364 tables_->UpdateData(yahoo, empty_host_data); |
| 365 } |
| 366 |
| 367 { // Host data. |
| 368 PrefetchData facebook(PREFETCH_KEY_TYPE_HOST, "www.facebook.com"); |
| 369 facebook.last_visit = base::Time::FromInternalValue(4); |
| 370 facebook.resources |
| 371 .push_back(ResourceRow(std::string(), |
| 372 "http://www.facebook.com/style.css", |
| 373 content::RESOURCE_TYPE_STYLESHEET, |
| 374 5, |
| 375 2, |
| 376 1, |
| 377 1.1)); |
| 378 facebook.resources |
| 379 .push_back(ResourceRow(std::string(), |
| 380 "http://www.facebook.com/script.js", |
| 381 content::RESOURCE_TYPE_SCRIPT, |
| 382 4, |
| 383 0, |
| 384 1, |
| 385 2.1)); |
| 386 facebook.resources |
| 387 .push_back(ResourceRow(std::string(), |
| 388 "http://www.facebook.com/image.png", |
| 389 content::RESOURCE_TYPE_IMAGE, |
| 390 6, |
| 391 3, |
| 392 0, |
| 393 2.2)); |
| 394 facebook.resources.push_back(ResourceRow(std::string(), |
| 395 "http://www.facebook.com/a.font", |
| 396 content::RESOURCE_TYPE_LAST_TYPE, |
| 397 2, |
| 398 0, |
| 399 0, |
| 400 5.1)); |
| 401 facebook.resources |
| 402 .push_back(ResourceRow(std::string(), |
| 403 "http://www.resources.facebook.com/script.js", |
| 404 content::RESOURCE_TYPE_SCRIPT, |
| 405 11, |
| 406 0, |
| 407 0, |
| 408 8.5)); |
| 409 |
| 410 PrefetchData yahoo(PREFETCH_KEY_TYPE_HOST, "www.yahoo.com"); |
| 411 yahoo.last_visit = base::Time::FromInternalValue(5); |
| 412 yahoo.resources.push_back(ResourceRow(std::string(), |
| 413 "http://www.google.com/image.png", |
| 414 content::RESOURCE_TYPE_IMAGE, |
| 415 20, |
| 416 1, |
| 417 0, |
| 418 10.0)); |
| 419 |
| 420 test_host_data_.clear(); |
| 421 test_host_data_.insert(std::make_pair("www.facebook.com", facebook)); |
| 422 test_host_data_.insert(std::make_pair("www.yahoo.com", yahoo)); |
| 423 |
| 424 PrefetchData empty_url_data(PREFETCH_KEY_TYPE_URL, std::string()); |
| 425 tables_->UpdateData(empty_url_data, facebook); |
| 426 tables_->UpdateData(empty_url_data, yahoo); |
| 427 } |
| 428 } |
| 429 |
| 430 // Test cases. |
| 431 |
| 432 TEST_F(ResourcePrefetchPredictorTablesTest, GetAllData) { |
| 433 TestGetAllData(); |
| 434 } |
| 435 |
| 436 TEST_F(ResourcePrefetchPredictorTablesTest, UpdateData) { |
| 437 TestUpdateData(); |
| 438 } |
| 439 |
| 440 TEST_F(ResourcePrefetchPredictorTablesTest, DeleteData) { |
| 441 TestDeleteData(); |
| 442 } |
| 443 |
| 444 TEST_F(ResourcePrefetchPredictorTablesTest, DeleteSingleDataPoint) { |
| 445 TestDeleteSingleDataPoint(); |
| 446 } |
| 447 |
| 448 TEST_F(ResourcePrefetchPredictorTablesTest, DeleteAllData) { |
| 449 TestDeleteAllData(); |
| 450 } |
| 451 |
| 452 TEST_F(ResourcePrefetchPredictorTablesReopenTest, GetAllData) { |
| 453 TestGetAllData(); |
| 454 } |
| 455 |
| 456 TEST_F(ResourcePrefetchPredictorTablesReopenTest, UpdateData) { |
| 457 TestUpdateData(); |
| 458 } |
| 459 |
| 460 TEST_F(ResourcePrefetchPredictorTablesReopenTest, DeleteData) { |
| 461 TestDeleteData(); |
| 462 } |
| 463 |
| 464 TEST_F(ResourcePrefetchPredictorTablesReopenTest, DeleteSingleDataPoint) { |
| 465 TestDeleteSingleDataPoint(); |
| 466 } |
| 467 |
| 468 TEST_F(ResourcePrefetchPredictorTablesReopenTest, DeleteAllData) { |
| 469 TestDeleteAllData(); |
| 470 } |
| 471 |
| 472 } // namespace predictors |
OLD | NEW |