| OLD | NEW |
| (Empty) | |
| 1 // Copyright (c) 2009 The Chromium Authos. 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 "testing/gtest/include/gtest/gtest.h" |
| 6 |
| 7 #include "base/stl_util-inl.h" |
| 8 #include "base/thread.h" |
| 9 #include "base/waitable_event.h" |
| 10 #include "net/url_request/url_request_test_job.h" |
| 11 #include "net/url_request/url_request_unittest.h" |
| 12 #include "webkit/appcache/appcache_group.h" |
| 13 #include "webkit/appcache/appcache_host.h" |
| 14 #include "webkit/appcache/appcache_service.h" |
| 15 #include "webkit/appcache/appcache_update_job.h" |
| 16 |
| 17 namespace appcache { |
| 18 class AppCacheUpdateJobTest; |
| 19 |
| 20 const wchar_t kDocRoot[] = L"webkit/appcache/data/appcache_unittest"; |
| 21 |
| 22 class MockFrontend : public AppCacheFrontend { |
| 23 public: |
| 24 virtual void OnCacheSelected(int host_id, int64 cache_id, |
| 25 Status status) { |
| 26 } |
| 27 |
| 28 virtual void OnStatusChanged(const std::vector<int>& host_ids, |
| 29 Status status) { |
| 30 } |
| 31 |
| 32 virtual void OnEventRaised(const std::vector<int>& host_ids, |
| 33 EventID event_id) { |
| 34 raised_events_.push_back(RaisedEvent(host_ids, event_id)); |
| 35 } |
| 36 |
| 37 void AddExpectedEvent(const std::vector<int>& host_ids, EventID event_id) { |
| 38 expected_events_.push_back(RaisedEvent(host_ids, event_id)); |
| 39 } |
| 40 |
| 41 typedef std::vector<int> HostIds; |
| 42 typedef std::pair<HostIds, EventID> RaisedEvent; |
| 43 typedef std::vector<RaisedEvent> RaisedEvents; |
| 44 RaisedEvents raised_events_; |
| 45 |
| 46 // Set the expected events if verification needs to happen asynchronously. |
| 47 RaisedEvents expected_events_; |
| 48 }; |
| 49 |
| 50 // Helper class to let us call methods of AppCacheUpdateJobTest on a |
| 51 // thread of our choice. |
| 52 template <class Method> |
| 53 class WrapperTask : public Task { |
| 54 public: |
| 55 WrapperTask(AppCacheUpdateJobTest* test, Method method) |
| 56 : test_(test), |
| 57 method_(method) { |
| 58 } |
| 59 |
| 60 virtual void Run() { |
| 61 (test_->*method_)( ); |
| 62 } |
| 63 |
| 64 private: |
| 65 AppCacheUpdateJobTest* test_; |
| 66 Method method_; |
| 67 }; |
| 68 |
| 69 // Helper factories to simulate redirected URL responses for tests. |
| 70 static URLRequestJob* RedirectFactory(URLRequest* request, |
| 71 const std::string& scheme) { |
| 72 return new URLRequestTestJob(request, |
| 73 URLRequestTestJob::test_redirect_headers(), |
| 74 URLRequestTestJob::test_data_1(), |
| 75 true); |
| 76 } |
| 77 |
| 78 class AppCacheUpdateJobTest : public testing::Test, |
| 79 public AppCacheGroup::Observer { |
| 80 public: |
| 81 AppCacheUpdateJobTest() |
| 82 : ALLOW_THIS_IN_INITIALIZER_LIST(method_factory_(this)), |
| 83 do_checks_after_update_finished_(false), |
| 84 expect_group_obsolete_(false), |
| 85 expect_group_has_cache_(false), |
| 86 expect_old_cache_(NULL), |
| 87 expect_newest_cache_(NULL), |
| 88 tested_manifest_(NONE) { |
| 89 } |
| 90 |
| 91 static void SetUpTestCase() { |
| 92 io_thread_.reset(new base::Thread("AppCacheUpdateJob IO test thread")); |
| 93 base::Thread::Options options(MessageLoop::TYPE_IO, 0); |
| 94 io_thread_->StartWithOptions(options); |
| 95 |
| 96 http_server_ = |
| 97 HTTPTestServer::CreateServer(kDocRoot, io_thread_->message_loop()); |
| 98 ASSERT_TRUE(http_server_); |
| 99 } |
| 100 |
| 101 static void TearDownTestCase() { |
| 102 http_server_ = NULL; |
| 103 io_thread_.reset(NULL); |
| 104 } |
| 105 |
| 106 // Use a separate IO thread to run a test. Thread will be destroyed |
| 107 // when it goes out of scope. |
| 108 template <class Method> |
| 109 void RunTestOnIOThread(Method method) { |
| 110 event_ .reset(new base::WaitableEvent(false, false)); |
| 111 io_thread_->message_loop()->PostTask( |
| 112 FROM_HERE, new WrapperTask<Method>(this, method)); |
| 113 |
| 114 // Wait until task is done before exiting the test. |
| 115 event_->Wait(); |
| 116 } |
| 117 |
| 118 void StartCacheAttemptTest() { |
| 119 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 120 |
| 121 MakeService(); |
| 122 group_ = new AppCacheGroup(service_.get(), GURL("http://failme")); |
| 123 |
| 124 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 125 group_->update_job_ = update; |
| 126 |
| 127 MockFrontend mock_frontend; |
| 128 AppCacheHost host(1, &mock_frontend, service_.get()); |
| 129 |
| 130 update->StartUpdate(&host, GURL::EmptyGURL()); |
| 131 |
| 132 // Verify state. |
| 133 EXPECT_EQ(AppCacheUpdateJob::CACHE_ATTEMPT, update->update_type_); |
| 134 EXPECT_EQ(AppCacheUpdateJob::FETCH_MANIFEST, update->internal_state_); |
| 135 EXPECT_EQ(AppCacheGroup::CHECKING, group_->update_status()); |
| 136 |
| 137 // Verify notifications. |
| 138 MockFrontend::RaisedEvents& events = mock_frontend.raised_events_; |
| 139 size_t expected = 1; |
| 140 EXPECT_EQ(expected, events.size()); |
| 141 EXPECT_EQ(expected, events[0].first.size()); |
| 142 EXPECT_EQ(host.host_id(), events[0].first[0]); |
| 143 EXPECT_EQ(CHECKING_EVENT, events[0].second); |
| 144 |
| 145 // Abort as we're not testing actual URL fetches in this test. |
| 146 delete update; |
| 147 UpdateFinished(); |
| 148 } |
| 149 |
| 150 void StartUpgradeAttemptTest() { |
| 151 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 152 |
| 153 { |
| 154 MakeService(); |
| 155 group_ = new AppCacheGroup(service_.get(), GURL("http://failme")); |
| 156 |
| 157 // Give the group some existing caches. |
| 158 AppCache* cache1 = MakeCacheForGroup(1); |
| 159 AppCache* cache2 = MakeCacheForGroup(2); |
| 160 |
| 161 // Associate some hosts with caches in the group. |
| 162 MockFrontend mock_frontend1; |
| 163 MockFrontend mock_frontend2; |
| 164 MockFrontend mock_frontend3; |
| 165 |
| 166 AppCacheHost host1(1, &mock_frontend1, service_.get()); |
| 167 host1.AssociateCache(cache1); |
| 168 |
| 169 AppCacheHost host2(2, &mock_frontend2, service_.get()); |
| 170 host2.AssociateCache(cache2); |
| 171 |
| 172 AppCacheHost host3(3, &mock_frontend1, service_.get()); |
| 173 host3.AssociateCache(cache1); |
| 174 |
| 175 AppCacheHost host4(4, &mock_frontend3, service_.get()); |
| 176 |
| 177 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 178 group_->update_job_ = update; |
| 179 update->StartUpdate(&host4, GURL::EmptyGURL()); |
| 180 |
| 181 // Verify state after starting an update. |
| 182 EXPECT_EQ(AppCacheUpdateJob::UPGRADE_ATTEMPT, update->update_type_); |
| 183 EXPECT_EQ(AppCacheUpdateJob::FETCH_MANIFEST, update->internal_state_); |
| 184 EXPECT_EQ(AppCacheGroup::CHECKING, group_->update_status()); |
| 185 |
| 186 // Verify notifications. |
| 187 MockFrontend::RaisedEvents& events = mock_frontend1.raised_events_; |
| 188 size_t expected = 1; |
| 189 EXPECT_EQ(expected, events.size()); |
| 190 expected = 2; // 2 hosts using frontend1 |
| 191 EXPECT_EQ(expected, events[0].first.size()); |
| 192 MockFrontend::HostIds& host_ids = events[0].first; |
| 193 EXPECT_TRUE(std::find(host_ids.begin(), host_ids.end(), host1.host_id()) |
| 194 != host_ids.end()); |
| 195 EXPECT_TRUE(std::find(host_ids.begin(), host_ids.end(), host3.host_id()) |
| 196 != host_ids.end()); |
| 197 EXPECT_EQ(CHECKING_EVENT, events[0].second); |
| 198 |
| 199 events = mock_frontend2.raised_events_; |
| 200 expected = 1; |
| 201 EXPECT_EQ(expected, events.size()); |
| 202 EXPECT_EQ(expected, events[0].first.size()); // 1 host using frontend2 |
| 203 EXPECT_EQ(host2.host_id(), events[0].first[0]); |
| 204 EXPECT_EQ(CHECKING_EVENT, events[0].second); |
| 205 |
| 206 events = mock_frontend3.raised_events_; |
| 207 EXPECT_TRUE(events.empty()); |
| 208 |
| 209 // Abort as we're not testing actual URL fetches in this test. |
| 210 delete update; |
| 211 } |
| 212 UpdateFinished(); |
| 213 } |
| 214 |
| 215 void CacheAttemptFetchManifestFailTest() { |
| 216 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 217 |
| 218 MakeService(); |
| 219 group_ = new AppCacheGroup(service_.get(), GURL("http://failme")); |
| 220 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 221 group_->update_job_ = update; |
| 222 |
| 223 MockFrontend* frontend = MakeMockFrontend(); |
| 224 AppCacheHost* host = MakeHost(1, frontend); |
| 225 update->StartUpdate(host, GURL::EmptyGURL()); |
| 226 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 227 |
| 228 update->manifest_url_request_->SimulateError(-100); |
| 229 |
| 230 // Set up checks for when update job finishes. |
| 231 do_checks_after_update_finished_ = true; |
| 232 expect_group_obsolete_ = false; |
| 233 expect_group_has_cache_ = false; |
| 234 frontend->AddExpectedEvent(MockFrontend::HostIds(1, host->host_id()), |
| 235 CHECKING_EVENT); |
| 236 |
| 237 WaitForUpdateToFinish(); |
| 238 } |
| 239 |
| 240 void UpgradeFetchManifestFailTest() { |
| 241 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 242 |
| 243 MakeService(); |
| 244 group_ = new AppCacheGroup(service_.get(), GURL("http://failme")); |
| 245 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 246 group_->update_job_ = update; |
| 247 |
| 248 AppCache* cache = MakeCacheForGroup(1); |
| 249 MockFrontend* frontend1 = MakeMockFrontend(); |
| 250 MockFrontend* frontend2 = MakeMockFrontend(); |
| 251 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 252 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 253 host1->AssociateCache(cache); |
| 254 host2->AssociateCache(cache); |
| 255 |
| 256 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 257 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 258 |
| 259 update->manifest_url_request_->SimulateError(-100); |
| 260 |
| 261 // Set up checks for when update job finishes. |
| 262 do_checks_after_update_finished_ = true; |
| 263 expect_group_obsolete_ = false; |
| 264 expect_group_has_cache_ = true; |
| 265 expect_newest_cache_ = cache; // newest cache unaffected by update |
| 266 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 267 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 268 frontend1->AddExpectedEvent(ids1, ERROR_EVENT); |
| 269 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 270 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 271 frontend2->AddExpectedEvent(ids2, ERROR_EVENT); |
| 272 |
| 273 WaitForUpdateToFinish(); |
| 274 } |
| 275 |
| 276 void ManifestRedirectTest() { |
| 277 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 278 |
| 279 URLRequest::RegisterProtocolFactory("http", RedirectFactory); |
| 280 |
| 281 MakeService(); |
| 282 group_ = new AppCacheGroup(service_.get(), GURL("http://testme")); |
| 283 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 284 group_->update_job_ = update; |
| 285 |
| 286 MockFrontend* frontend = MakeMockFrontend(); |
| 287 AppCacheHost* host = MakeHost(1, frontend); |
| 288 update->StartUpdate(host, GURL::EmptyGURL()); |
| 289 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 290 |
| 291 // Set up checks for when update job finishes. |
| 292 do_checks_after_update_finished_ = true; |
| 293 expect_group_obsolete_ = false; |
| 294 expect_group_has_cache_ = false; // redirect is like a failed request |
| 295 frontend->AddExpectedEvent(MockFrontend::HostIds(1, host->host_id()), |
| 296 CHECKING_EVENT); |
| 297 |
| 298 WaitForUpdateToFinish(); |
| 299 } |
| 300 |
| 301 void ManifestWrongMimeTypeTest() { |
| 302 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 303 |
| 304 MakeService(); |
| 305 group_ = new AppCacheGroup( |
| 306 service_.get(), http_server_->TestServerPage("defaultresponse")); |
| 307 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 308 group_->update_job_ = update; |
| 309 |
| 310 MockFrontend* frontend = MakeMockFrontend(); |
| 311 AppCacheHost* host = MakeHost(1, frontend); |
| 312 update->StartUpdate(host, GURL::EmptyGURL()); |
| 313 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 314 |
| 315 // Set up checks for when update job finishes. |
| 316 do_checks_after_update_finished_ = true; |
| 317 expect_group_obsolete_ = false; |
| 318 expect_group_has_cache_ = false; // bad mime type is like a failed request |
| 319 frontend->AddExpectedEvent(MockFrontend::HostIds(1, host->host_id()), |
| 320 CHECKING_EVENT); |
| 321 |
| 322 WaitForUpdateToFinish(); |
| 323 } |
| 324 |
| 325 void ManifestNotFoundTest() { |
| 326 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 327 |
| 328 MakeService(); |
| 329 group_ = new AppCacheGroup( |
| 330 service_.get(), http_server_->TestServerPage("files/nosuchfile")); |
| 331 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 332 group_->update_job_ = update; |
| 333 |
| 334 AppCache* cache = MakeCacheForGroup(1); |
| 335 MockFrontend* frontend1 = MakeMockFrontend(); |
| 336 MockFrontend* frontend2 = MakeMockFrontend(); |
| 337 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 338 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 339 host1->AssociateCache(cache); |
| 340 host2->AssociateCache(cache); |
| 341 |
| 342 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 343 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 344 |
| 345 // Set up checks for when update job finishes. |
| 346 do_checks_after_update_finished_ = true; |
| 347 expect_group_obsolete_ = true; |
| 348 expect_group_has_cache_ = true; |
| 349 expect_newest_cache_ = cache; // newest cache unaffected by update |
| 350 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 351 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 352 frontend1->AddExpectedEvent(ids1, OBSOLETE_EVENT); |
| 353 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 354 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 355 frontend2->AddExpectedEvent(ids2, OBSOLETE_EVENT); |
| 356 |
| 357 WaitForUpdateToFinish(); |
| 358 } |
| 359 |
| 360 void ManifestGoneTest() { |
| 361 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 362 |
| 363 MakeService(); |
| 364 group_ = new AppCacheGroup( |
| 365 service_.get(), http_server_->TestServerPage("files/gone")); |
| 366 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 367 group_->update_job_ = update; |
| 368 |
| 369 MockFrontend* frontend = MakeMockFrontend(); |
| 370 AppCacheHost* host = MakeHost(1, frontend); |
| 371 update->StartUpdate(host, GURL::EmptyGURL()); |
| 372 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 373 |
| 374 // Set up checks for when update job finishes. |
| 375 do_checks_after_update_finished_ = true; |
| 376 expect_group_obsolete_ = true; |
| 377 expect_group_has_cache_ = false; |
| 378 frontend->AddExpectedEvent(MockFrontend::HostIds(1, host->host_id()), |
| 379 CHECKING_EVENT); |
| 380 |
| 381 WaitForUpdateToFinish(); |
| 382 } |
| 383 |
| 384 void CacheAttemptNotModifiedTest() { |
| 385 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 386 |
| 387 MakeService(); |
| 388 group_ = new AppCacheGroup( |
| 389 service_.get(), http_server_->TestServerPage("files/notmodified")); |
| 390 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 391 group_->update_job_ = update; |
| 392 |
| 393 MockFrontend* frontend = MakeMockFrontend(); |
| 394 AppCacheHost* host = MakeHost(1, frontend); |
| 395 update->StartUpdate(host, GURL::EmptyGURL()); |
| 396 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 397 |
| 398 // Set up checks for when update job finishes. |
| 399 do_checks_after_update_finished_ = true; |
| 400 expect_group_obsolete_ = false; |
| 401 expect_group_has_cache_ = false; // treated like cache failure |
| 402 frontend->AddExpectedEvent(MockFrontend::HostIds(1, host->host_id()), |
| 403 CHECKING_EVENT); |
| 404 |
| 405 WaitForUpdateToFinish(); |
| 406 } |
| 407 |
| 408 void UpgradeNotModifiedTest() { |
| 409 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 410 |
| 411 MakeService(); |
| 412 group_ = new AppCacheGroup( |
| 413 service_.get(), http_server_->TestServerPage("files/notmodified")); |
| 414 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 415 group_->update_job_ = update; |
| 416 |
| 417 AppCache* cache = MakeCacheForGroup(1); |
| 418 MockFrontend* frontend1 = MakeMockFrontend(); |
| 419 MockFrontend* frontend2 = MakeMockFrontend(); |
| 420 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 421 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 422 host1->AssociateCache(cache); |
| 423 host2->AssociateCache(cache); |
| 424 |
| 425 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 426 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 427 |
| 428 // Set up checks for when update job finishes. |
| 429 do_checks_after_update_finished_ = true; |
| 430 expect_group_obsolete_ = false; |
| 431 expect_group_has_cache_ = true; |
| 432 expect_newest_cache_ = cache; // newest cache unaffected by update |
| 433 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 434 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 435 frontend1->AddExpectedEvent(ids1, NO_UPDATE_EVENT); |
| 436 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 437 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 438 frontend2->AddExpectedEvent(ids2, NO_UPDATE_EVENT); |
| 439 |
| 440 WaitForUpdateToFinish(); |
| 441 } |
| 442 |
| 443 void UpgradeManifestDataUnchangedTest() { |
| 444 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 445 |
| 446 MakeService(); |
| 447 group_ = new AppCacheGroup( |
| 448 service_.get(), http_server_->TestServerPage("files/manifest1")); |
| 449 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 450 group_->update_job_ = update; |
| 451 |
| 452 AppCache* cache = MakeCacheForGroup(1); |
| 453 MockFrontend* frontend1 = MakeMockFrontend(); |
| 454 MockFrontend* frontend2 = MakeMockFrontend(); |
| 455 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 456 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 457 host1->AssociateCache(cache); |
| 458 host2->AssociateCache(cache); |
| 459 |
| 460 // TODO(jennb): simulate this by mocking storage behavior instead |
| 461 update->SimulateManifestChanged(false); // unchanged |
| 462 |
| 463 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 464 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 465 |
| 466 // Set up checks for when update job finishes. |
| 467 do_checks_after_update_finished_ = true; |
| 468 expect_group_obsolete_ = false; |
| 469 expect_group_has_cache_ = true; |
| 470 expect_newest_cache_ = cache; // newest cache unaffected by update |
| 471 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 472 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 473 frontend1->AddExpectedEvent(ids1, NO_UPDATE_EVENT); |
| 474 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 475 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 476 frontend2->AddExpectedEvent(ids2, NO_UPDATE_EVENT); |
| 477 |
| 478 WaitForUpdateToFinish(); |
| 479 } |
| 480 |
| 481 void BasicCacheAttemptSuccessTest() { |
| 482 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 483 |
| 484 MakeService(); |
| 485 group_ = new AppCacheGroup( |
| 486 service_.get(), http_server_->TestServerPage("files/manifest1")); |
| 487 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 488 group_->update_job_ = update; |
| 489 |
| 490 MockFrontend* frontend = MakeMockFrontend(); |
| 491 AppCacheHost* host = MakeHost(1, frontend); |
| 492 update->StartUpdate(host, GURL::EmptyGURL()); |
| 493 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 494 |
| 495 // Set up checks for when update job finishes. |
| 496 do_checks_after_update_finished_ = true; |
| 497 expect_group_obsolete_ = false; |
| 498 expect_group_has_cache_ = true; |
| 499 tested_manifest_ = MANIFEST1; |
| 500 frontend->AddExpectedEvent(MockFrontend::HostIds(1, host->host_id()), |
| 501 CHECKING_EVENT); |
| 502 |
| 503 WaitForUpdateToFinish(); |
| 504 } |
| 505 |
| 506 void BasicUpgradeSuccessTest() { |
| 507 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 508 |
| 509 MakeService(); |
| 510 group_ = new AppCacheGroup( |
| 511 service_.get(), http_server_->TestServerPage("files/manifest1")); |
| 512 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 513 group_->update_job_ = update; |
| 514 |
| 515 AppCache* cache = MakeCacheForGroup(service_->NewCacheId()); |
| 516 MockFrontend* frontend1 = MakeMockFrontend(); |
| 517 MockFrontend* frontend2 = MakeMockFrontend(); |
| 518 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 519 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 520 host1->AssociateCache(cache); |
| 521 host2->AssociateCache(cache); |
| 522 |
| 523 // TODO(jennb): simulate this by mocking storage behavior instead |
| 524 update->SimulateManifestChanged(true); // changed |
| 525 |
| 526 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 527 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 528 |
| 529 // Set up checks for when update job finishes. |
| 530 do_checks_after_update_finished_ = true; |
| 531 expect_group_obsolete_ = false; |
| 532 expect_group_has_cache_ = true; |
| 533 expect_old_cache_ = cache; |
| 534 tested_manifest_ = MANIFEST1; |
| 535 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 536 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 537 frontend1->AddExpectedEvent(ids1, DOWNLOADING_EVENT); |
| 538 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); |
| 539 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); |
| 540 frontend1->AddExpectedEvent(ids1, UPDATE_READY_EVENT); |
| 541 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 542 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 543 frontend2->AddExpectedEvent(ids2, DOWNLOADING_EVENT); |
| 544 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 545 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 546 frontend2->AddExpectedEvent(ids2, UPDATE_READY_EVENT); |
| 547 |
| 548 WaitForUpdateToFinish(); |
| 549 } |
| 550 |
| 551 void UpgradeSuccessMergedTypesTest() { |
| 552 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 553 |
| 554 MakeService(); |
| 555 group_ = new AppCacheGroup(service_.get(), |
| 556 http_server_->TestServerPage("files/manifest-merged-types")); |
| 557 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 558 group_->update_job_ = update; |
| 559 |
| 560 AppCache* cache = MakeCacheForGroup(service_->NewCacheId()); |
| 561 MockFrontend* frontend1 = MakeMockFrontend(); |
| 562 MockFrontend* frontend2 = MakeMockFrontend(); |
| 563 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 564 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 565 host1->AssociateCache(cache); |
| 566 host2->AssociateCache(cache); |
| 567 |
| 568 // Give the newest cache a master entry that is also one of the explicit |
| 569 // entries in the manifest. |
| 570 cache->AddEntry(http_server_->TestServerPage("files/explicit1"), |
| 571 AppCacheEntry(AppCacheEntry::MASTER)); |
| 572 |
| 573 // TODO(jennb): simulate this by mocking storage behavior instead |
| 574 update->SimulateManifestChanged(true); // changed |
| 575 |
| 576 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 577 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 578 |
| 579 // Set up checks for when update job finishes. |
| 580 do_checks_after_update_finished_ = true; |
| 581 expect_group_obsolete_ = false; |
| 582 expect_group_has_cache_ = true; |
| 583 expect_old_cache_ = cache; |
| 584 tested_manifest_ = MANIFEST_MERGED_TYPES; |
| 585 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 586 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 587 frontend1->AddExpectedEvent(ids1, DOWNLOADING_EVENT); |
| 588 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // explicit1 (load) |
| 589 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // explicit1 (fetch) |
| 590 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // manifest |
| 591 frontend1->AddExpectedEvent(ids1, UPDATE_READY_EVENT); |
| 592 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 593 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 594 frontend2->AddExpectedEvent(ids2, DOWNLOADING_EVENT); |
| 595 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 596 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 597 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 598 frontend2->AddExpectedEvent(ids2, UPDATE_READY_EVENT); |
| 599 |
| 600 WaitForUpdateToFinish(); |
| 601 } |
| 602 |
| 603 void CacheAttemptFailUrlFetchTest() { |
| 604 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 605 |
| 606 MakeService(); |
| 607 group_ = new AppCacheGroup( |
| 608 service_.get(), http_server_->TestServerPage("files/manifest-with-404")); |
| 609 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 610 group_->update_job_ = update; |
| 611 |
| 612 MockFrontend* frontend = MakeMockFrontend(); |
| 613 AppCacheHost* host = MakeHost(1, frontend); |
| 614 update->StartUpdate(host, GURL::EmptyGURL()); |
| 615 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 616 |
| 617 // Set up checks for when update job finishes. |
| 618 do_checks_after_update_finished_ = true; |
| 619 expect_group_obsolete_ = false; |
| 620 expect_group_has_cache_ = false; // 404 explicit url is cache failure |
| 621 frontend->AddExpectedEvent(MockFrontend::HostIds(1, host->host_id()), |
| 622 CHECKING_EVENT); |
| 623 |
| 624 WaitForUpdateToFinish(); |
| 625 } |
| 626 |
| 627 void UpgradeFailUrlFetchTest() { |
| 628 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 629 |
| 630 MakeService(); |
| 631 group_ = new AppCacheGroup( |
| 632 service_.get(), http_server_->TestServerPage("files/manifest-fb-404")); |
| 633 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 634 group_->update_job_ = update; |
| 635 |
| 636 AppCache* cache = MakeCacheForGroup(service_->NewCacheId()); |
| 637 MockFrontend* frontend1 = MakeMockFrontend(); |
| 638 MockFrontend* frontend2 = MakeMockFrontend(); |
| 639 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 640 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 641 host1->AssociateCache(cache); |
| 642 host2->AssociateCache(cache); |
| 643 |
| 644 // TODO(jennb): simulate this by mocking storage behavior instead |
| 645 update->SimulateManifestChanged(true); // changed |
| 646 |
| 647 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 648 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 649 |
| 650 // Set up checks for when update job finishes. |
| 651 do_checks_after_update_finished_ = true; |
| 652 expect_group_obsolete_ = false; |
| 653 expect_group_has_cache_ = true; |
| 654 expect_newest_cache_ = cache; // newest cache unaffectd by failed update |
| 655 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 656 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 657 frontend1->AddExpectedEvent(ids1, DOWNLOADING_EVENT); |
| 658 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); |
| 659 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); |
| 660 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); |
| 661 frontend1->AddExpectedEvent(ids1, ERROR_EVENT); |
| 662 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 663 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 664 frontend2->AddExpectedEvent(ids2, DOWNLOADING_EVENT); |
| 665 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 666 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 667 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 668 frontend2->AddExpectedEvent(ids2, ERROR_EVENT); |
| 669 |
| 670 WaitForUpdateToFinish(); |
| 671 } |
| 672 |
| 673 void UpgradeFailMasterUrlFetchTest() { |
| 674 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 675 |
| 676 MakeService(); |
| 677 group_ = new AppCacheGroup( |
| 678 service_.get(), http_server_->TestServerPage("files/manifest1")); |
| 679 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 680 group_->update_job_ = update; |
| 681 |
| 682 AppCache* cache = MakeCacheForGroup(service_->NewCacheId()); |
| 683 MockFrontend* frontend1 = MakeMockFrontend(); |
| 684 MockFrontend* frontend2 = MakeMockFrontend(); |
| 685 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 686 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 687 host1->AssociateCache(cache); |
| 688 host2->AssociateCache(cache); |
| 689 |
| 690 // Give the newest cache some master entries; one will fail with a 404. |
| 691 cache->AddEntry( |
| 692 http_server_->TestServerPage("files/notfound"), |
| 693 AppCacheEntry(AppCacheEntry::MASTER)); |
| 694 cache->AddEntry( |
| 695 http_server_->TestServerPage("files/explicit2"), |
| 696 AppCacheEntry(AppCacheEntry::MASTER | AppCacheEntry::FOREIGN)); |
| 697 cache->AddEntry( |
| 698 http_server_->TestServerPage("files/servererror"), |
| 699 AppCacheEntry(AppCacheEntry::MASTER)); |
| 700 |
| 701 // TODO(jennb): simulate this by mocking storage behavior instead |
| 702 update->SimulateManifestChanged(true); // changed |
| 703 |
| 704 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 705 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 706 |
| 707 // Set up checks for when update job finishes. |
| 708 do_checks_after_update_finished_ = true; |
| 709 expect_group_obsolete_ = false; |
| 710 expect_group_has_cache_ = true; |
| 711 expect_old_cache_ = cache; |
| 712 tested_manifest_ = MANIFEST1; |
| 713 expect_extra_entries_.insert(AppCache::EntryMap::value_type( |
| 714 http_server_->TestServerPage("files/explicit2"), |
| 715 AppCacheEntry(AppCacheEntry::MASTER))); // foreign flag is dropped |
| 716 expect_extra_entries_.insert(AppCache::EntryMap::value_type( |
| 717 http_server_->TestServerPage("files/servererror"), |
| 718 AppCacheEntry(AppCacheEntry::MASTER))); // foreign flag is dropped |
| 719 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 720 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 721 frontend1->AddExpectedEvent(ids1, DOWNLOADING_EVENT); |
| 722 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // explicit1 |
| 723 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // fallback1a |
| 724 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // notfound (load) |
| 725 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // notfound (fetch) |
| 726 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // explicit2 (load) |
| 727 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // explicit2 (fetch) |
| 728 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // servererror (load) |
| 729 frontend1->AddExpectedEvent(ids1, PROGRESS_EVENT); // servererror (fetch) |
| 730 frontend1->AddExpectedEvent(ids1, UPDATE_READY_EVENT); |
| 731 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 732 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 733 frontend2->AddExpectedEvent(ids2, DOWNLOADING_EVENT); |
| 734 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 735 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 736 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 737 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 738 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 739 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 740 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 741 frontend2->AddExpectedEvent(ids2, PROGRESS_EVENT); |
| 742 frontend2->AddExpectedEvent(ids2, UPDATE_READY_EVENT); |
| 743 |
| 744 WaitForUpdateToFinish(); |
| 745 } |
| 746 |
| 747 void EmptyManifestTest() { |
| 748 ASSERT_EQ(MessageLoop::TYPE_IO, MessageLoop::current()->type()); |
| 749 |
| 750 MakeService(); |
| 751 group_ = new AppCacheGroup( |
| 752 service_.get(), http_server_->TestServerPage("files/empty-manifest")); |
| 753 AppCacheUpdateJob* update = new AppCacheUpdateJob(service_.get(), group_); |
| 754 group_->update_job_ = update; |
| 755 |
| 756 AppCache* cache = MakeCacheForGroup(service_->NewCacheId()); |
| 757 MockFrontend* frontend1 = MakeMockFrontend(); |
| 758 MockFrontend* frontend2 = MakeMockFrontend(); |
| 759 AppCacheHost* host1 = MakeHost(1, frontend1); |
| 760 AppCacheHost* host2 = MakeHost(2, frontend2); |
| 761 host1->AssociateCache(cache); |
| 762 host2->AssociateCache(cache); |
| 763 |
| 764 // TODO(jennb): simulate this by mocking storage behavior instead |
| 765 update->SimulateManifestChanged(true); // changed |
| 766 |
| 767 update->StartUpdate(NULL, GURL::EmptyGURL()); |
| 768 EXPECT_TRUE(update->manifest_url_request_ != NULL); |
| 769 |
| 770 // Set up checks for when update job finishes. |
| 771 do_checks_after_update_finished_ = true; |
| 772 expect_group_obsolete_ = false; |
| 773 expect_group_has_cache_ = true; |
| 774 expect_old_cache_ = cache; |
| 775 tested_manifest_ = EMPTY_MANIFEST; |
| 776 MockFrontend::HostIds ids1(1, host1->host_id()); |
| 777 frontend1->AddExpectedEvent(ids1, CHECKING_EVENT); |
| 778 frontend1->AddExpectedEvent(ids1, DOWNLOADING_EVENT); |
| 779 frontend1->AddExpectedEvent(ids1, UPDATE_READY_EVENT); |
| 780 MockFrontend::HostIds ids2(1, host2->host_id()); |
| 781 frontend2->AddExpectedEvent(ids2, CHECKING_EVENT); |
| 782 frontend2->AddExpectedEvent(ids2, DOWNLOADING_EVENT); |
| 783 frontend2->AddExpectedEvent(ids2, UPDATE_READY_EVENT); |
| 784 |
| 785 WaitForUpdateToFinish(); |
| 786 } |
| 787 |
| 788 void WaitForUpdateToFinish() { |
| 789 if (group_->update_status() == AppCacheGroup::IDLE) |
| 790 UpdateFinished(); |
| 791 else |
| 792 group_->AddObserver(this); |
| 793 } |
| 794 |
| 795 void OnUpdateComplete(AppCacheGroup* group) { |
| 796 ASSERT_EQ(group_, group); |
| 797 |
| 798 // Finish up outside of observer callback so that group can be deleted. |
| 799 MessageLoop::current()->PostTask(FROM_HERE, |
| 800 method_factory_.NewRunnableMethod( |
| 801 &AppCacheUpdateJobTest::UpdateFinished)); |
| 802 } |
| 803 |
| 804 void UpdateFinished() { |
| 805 EXPECT_EQ(AppCacheGroup::IDLE, group_->update_status()); |
| 806 EXPECT_TRUE(group_->update_job() == NULL); |
| 807 if (do_checks_after_update_finished_) |
| 808 VerifyExpectations(); |
| 809 |
| 810 // Clean up everything that was created on the IO thread. |
| 811 group_ = NULL; |
| 812 STLDeleteContainerPointers(hosts_.begin(), hosts_.end()); |
| 813 STLDeleteContainerPointers(frontends_.begin(), frontends_.end()); |
| 814 service_.reset(NULL); |
| 815 URLRequest::RegisterProtocolFactory("http", NULL); |
| 816 |
| 817 event_->Signal(); |
| 818 } |
| 819 |
| 820 void MakeService() { |
| 821 service_.reset(new AppCacheService()); |
| 822 request_context_ = new TestURLRequestContext(); |
| 823 service_->set_request_context(request_context_); |
| 824 } |
| 825 |
| 826 AppCache* MakeCacheForGroup(int64 cache_id) { |
| 827 AppCache* cache = new AppCache(service_.get(), cache_id); |
| 828 cache->set_complete(true); |
| 829 cache->set_update_time(base::TimeTicks::Now()); |
| 830 cache->set_owning_group(group_); |
| 831 group_->AddCache(cache); |
| 832 return cache; |
| 833 } |
| 834 |
| 835 AppCacheHost* MakeHost(int host_id, AppCacheFrontend* frontend) { |
| 836 AppCacheHost* host = new AppCacheHost(host_id, frontend, service_.get()); |
| 837 hosts_.push_back(host); |
| 838 return host; |
| 839 } |
| 840 |
| 841 MockFrontend* MakeMockFrontend() { |
| 842 MockFrontend* frontend = new MockFrontend(); |
| 843 frontends_.push_back(frontend); |
| 844 return frontend; |
| 845 } |
| 846 |
| 847 // Verifies conditions about the group and notifications after an update |
| 848 // has finished. Cannot verify update job internals as update is deleted. |
| 849 void VerifyExpectations() { |
| 850 EXPECT_EQ(expect_group_obsolete_, group_->is_obsolete()); |
| 851 |
| 852 if (expect_group_has_cache_) { |
| 853 EXPECT_TRUE(group_->newest_complete_cache() != NULL); |
| 854 if (expect_old_cache_) { |
| 855 EXPECT_NE(expect_old_cache_, group_->newest_complete_cache()); |
| 856 EXPECT_TRUE(group_->old_caches().end() != |
| 857 std::find(group_->old_caches().begin(), |
| 858 group_->old_caches().end(), expect_old_cache_)); |
| 859 } |
| 860 if (expect_newest_cache_) |
| 861 EXPECT_EQ(expect_newest_cache_, group_->newest_complete_cache()); |
| 862 switch (tested_manifest_) { |
| 863 case MANIFEST1: |
| 864 VerifyManifest1(group_->newest_complete_cache()); |
| 865 break; |
| 866 case MANIFEST_MERGED_TYPES: |
| 867 VerifyManifestMergedTypes(group_->newest_complete_cache()); |
| 868 break; |
| 869 case EMPTY_MANIFEST: |
| 870 VerifyEmptyManifest(group_->newest_complete_cache()); |
| 871 break; |
| 872 case NONE: |
| 873 default: |
| 874 break; |
| 875 } |
| 876 } else { |
| 877 EXPECT_TRUE(group_->newest_complete_cache() == NULL); |
| 878 } |
| 879 |
| 880 // Check expected events. |
| 881 for (size_t i = 0; i < frontends_.size(); ++i) { |
| 882 MockFrontend* frontend = frontends_[i]; |
| 883 |
| 884 MockFrontend::RaisedEvents& expected_events = frontend->expected_events_; |
| 885 MockFrontend::RaisedEvents& actual_events = frontend->raised_events_; |
| 886 EXPECT_EQ(expected_events.size(), actual_events.size()); |
| 887 |
| 888 // Check each expected event. |
| 889 for (size_t j = 0; |
| 890 j < expected_events.size() && j < actual_events.size(); ++j) { |
| 891 EXPECT_EQ(expected_events[j].second, actual_events[j].second); |
| 892 |
| 893 MockFrontend::HostIds& expected_ids = expected_events[j].first; |
| 894 MockFrontend::HostIds& actual_ids = actual_events[j].first; |
| 895 EXPECT_EQ(expected_ids.size(), actual_ids.size()); |
| 896 |
| 897 for (size_t k = 0; k < expected_ids.size(); ++k) { |
| 898 int id = expected_ids[k]; |
| 899 EXPECT_TRUE(std::find(actual_ids.begin(), actual_ids.end(), id) != |
| 900 actual_ids.end()); |
| 901 } |
| 902 } |
| 903 } |
| 904 } |
| 905 |
| 906 void VerifyManifest1(AppCache* cache) { |
| 907 ASSERT_TRUE(cache != NULL); |
| 908 EXPECT_EQ(group_, cache->owning_group()); |
| 909 EXPECT_TRUE(cache->is_complete()); |
| 910 |
| 911 size_t expected = 3 + expect_extra_entries_.size(); |
| 912 EXPECT_EQ(expected, cache->entries().size()); |
| 913 AppCacheEntry* entry = |
| 914 cache->GetEntry(http_server_->TestServerPage("files/manifest1")); |
| 915 ASSERT_TRUE(entry); |
| 916 EXPECT_EQ(AppCacheEntry::MANIFEST, entry->types()); |
| 917 entry = cache->GetEntry(http_server_->TestServerPage("files/explicit1")); |
| 918 ASSERT_TRUE(entry); |
| 919 EXPECT_EQ(AppCacheEntry::EXPLICIT, entry->types()); |
| 920 entry = cache->GetEntry( |
| 921 http_server_->TestServerPage("files/fallback1a")); |
| 922 ASSERT_TRUE(entry); |
| 923 EXPECT_EQ(AppCacheEntry::FALLBACK, entry->types()); |
| 924 |
| 925 for (AppCache::EntryMap::iterator i = expect_extra_entries_.begin(); |
| 926 i != expect_extra_entries_.end(); ++i) { |
| 927 entry = cache->GetEntry(i->first); |
| 928 ASSERT_TRUE(entry); |
| 929 EXPECT_EQ(i->second.types(), entry->types()); |
| 930 // TODO(jennb): if copied, check storage id in entry is as expected |
| 931 } |
| 932 |
| 933 expected = 1; |
| 934 EXPECT_EQ(expected, cache->fallback_namespaces_.size()); |
| 935 EXPECT_TRUE(cache->fallback_namespaces_.end() != |
| 936 std::find(cache->fallback_namespaces_.begin(), |
| 937 cache->fallback_namespaces_.end(), |
| 938 FallbackNamespace( |
| 939 http_server_->TestServerPage("files/fallback1"), |
| 940 http_server_->TestServerPage("files/fallback1a")))); |
| 941 |
| 942 EXPECT_TRUE(cache->online_whitelist_namespaces_.empty()); |
| 943 EXPECT_TRUE(cache->online_whitelist_all_); |
| 944 |
| 945 EXPECT_TRUE(cache->update_time_ > base::TimeTicks()); |
| 946 } |
| 947 |
| 948 void VerifyManifestMergedTypes(AppCache* cache) { |
| 949 ASSERT_TRUE(cache != NULL); |
| 950 EXPECT_EQ(group_, cache->owning_group()); |
| 951 EXPECT_TRUE(cache->is_complete()); |
| 952 |
| 953 size_t expected = 2; |
| 954 EXPECT_EQ(expected, cache->entries().size()); |
| 955 AppCacheEntry* entry = cache->GetEntry( |
| 956 http_server_->TestServerPage("files/manifest-merged-types")); |
| 957 ASSERT_TRUE(entry); |
| 958 EXPECT_EQ(AppCacheEntry::EXPLICIT | AppCacheEntry::MANIFEST, |
| 959 entry->types()); |
| 960 entry = cache->GetEntry(http_server_->TestServerPage("files/explicit1")); |
| 961 ASSERT_TRUE(entry); |
| 962 EXPECT_EQ(AppCacheEntry::EXPLICIT | AppCacheEntry::FALLBACK | |
| 963 AppCacheEntry::MASTER, entry->types()); |
| 964 |
| 965 expected = 1; |
| 966 EXPECT_EQ(expected, cache->fallback_namespaces_.size()); |
| 967 EXPECT_TRUE(cache->fallback_namespaces_.end() != |
| 968 std::find(cache->fallback_namespaces_.begin(), |
| 969 cache->fallback_namespaces_.end(), |
| 970 FallbackNamespace( |
| 971 http_server_->TestServerPage("files/fallback1"), |
| 972 http_server_->TestServerPage("files/explicit1")))); |
| 973 |
| 974 EXPECT_EQ(expected, cache->online_whitelist_namespaces_.size()); |
| 975 EXPECT_TRUE(cache->online_whitelist_namespaces_.end() != |
| 976 std::find(cache->online_whitelist_namespaces_.begin(), |
| 977 cache->online_whitelist_namespaces_.end(), |
| 978 http_server_->TestServerPage("files/online1"))); |
| 979 EXPECT_FALSE(cache->online_whitelist_all_); |
| 980 |
| 981 EXPECT_TRUE(cache->update_time_ > base::TimeTicks()); |
| 982 } |
| 983 |
| 984 void VerifyEmptyManifest(AppCache* cache) { |
| 985 ASSERT_TRUE(cache!= NULL); |
| 986 EXPECT_EQ(group_, cache->owning_group()); |
| 987 EXPECT_TRUE(cache->is_complete()); |
| 988 |
| 989 size_t expected = 1; |
| 990 EXPECT_EQ(expected, cache->entries().size()); |
| 991 AppCacheEntry* entry = cache->GetEntry( |
| 992 http_server_->TestServerPage("files/empty-manifest")); |
| 993 ASSERT_TRUE(entry); |
| 994 EXPECT_EQ(AppCacheEntry::MANIFEST, entry->types()); |
| 995 |
| 996 EXPECT_TRUE(cache->fallback_namespaces_.empty()); |
| 997 EXPECT_TRUE(cache->online_whitelist_namespaces_.empty()); |
| 998 EXPECT_FALSE(cache->online_whitelist_all_); |
| 999 |
| 1000 EXPECT_TRUE(cache->update_time_ > base::TimeTicks()); |
| 1001 } |
| 1002 |
| 1003 private: |
| 1004 // Various manifest files used in this test. |
| 1005 enum TestedManifest { |
| 1006 NONE, |
| 1007 MANIFEST1, |
| 1008 MANIFEST_MERGED_TYPES, |
| 1009 EMPTY_MANIFEST, |
| 1010 }; |
| 1011 |
| 1012 static scoped_ptr<base::Thread> io_thread_; |
| 1013 static scoped_refptr<HTTPTestServer> http_server_; |
| 1014 |
| 1015 ScopedRunnableMethodFactory<AppCacheUpdateJobTest> method_factory_; |
| 1016 scoped_ptr<AppCacheService> service_; |
| 1017 scoped_refptr<TestURLRequestContext> request_context_; |
| 1018 scoped_refptr<AppCacheGroup> group_; |
| 1019 scoped_ptr<base::WaitableEvent> event_; |
| 1020 |
| 1021 // Hosts used by an async test that need to live until update job finishes. |
| 1022 // Otherwise, test can put host on the stack instead of here. |
| 1023 std::vector<AppCacheHost*> hosts_; |
| 1024 |
| 1025 // Flag indicating if test cares to verify the update after update finishes. |
| 1026 bool do_checks_after_update_finished_; |
| 1027 bool expect_group_obsolete_; |
| 1028 bool expect_group_has_cache_; |
| 1029 AppCache* expect_old_cache_; |
| 1030 AppCache* expect_newest_cache_; |
| 1031 std::vector<MockFrontend*> frontends_; // to check expected events |
| 1032 TestedManifest tested_manifest_; |
| 1033 AppCache::EntryMap expect_extra_entries_; |
| 1034 }; |
| 1035 |
| 1036 // static |
| 1037 scoped_ptr<base::Thread> AppCacheUpdateJobTest::io_thread_; |
| 1038 scoped_refptr<HTTPTestServer> AppCacheUpdateJobTest::http_server_; |
| 1039 |
| 1040 TEST_F(AppCacheUpdateJobTest, AlreadyChecking) { |
| 1041 AppCacheService service; |
| 1042 scoped_refptr<AppCacheGroup> group = |
| 1043 new AppCacheGroup(&service, GURL("http://manifesturl.com")); |
| 1044 |
| 1045 AppCacheUpdateJob update(&service, group); |
| 1046 |
| 1047 // Pretend group is in checking state. |
| 1048 group->update_job_ = &update; |
| 1049 group->update_status_ = AppCacheGroup::CHECKING; |
| 1050 |
| 1051 update.StartUpdate(NULL, GURL::EmptyGURL()); |
| 1052 EXPECT_EQ(AppCacheGroup::CHECKING, group->update_status()); |
| 1053 |
| 1054 MockFrontend mock_frontend; |
| 1055 AppCacheHost host(1, &mock_frontend, &service); |
| 1056 update.StartUpdate(&host, GURL::EmptyGURL()); |
| 1057 |
| 1058 MockFrontend::RaisedEvents events = mock_frontend.raised_events_; |
| 1059 size_t expected = 1; |
| 1060 EXPECT_EQ(expected, events.size()); |
| 1061 EXPECT_EQ(expected, events[0].first.size()); |
| 1062 EXPECT_EQ(host.host_id(), events[0].first[0]); |
| 1063 EXPECT_EQ(CHECKING_EVENT, events[0].second); |
| 1064 EXPECT_EQ(AppCacheGroup::CHECKING, group->update_status()); |
| 1065 } |
| 1066 |
| 1067 TEST_F(AppCacheUpdateJobTest, AlreadyDownloading) { |
| 1068 AppCacheService service; |
| 1069 scoped_refptr<AppCacheGroup> group = |
| 1070 new AppCacheGroup(&service, GURL("http://manifesturl.com")); |
| 1071 |
| 1072 AppCacheUpdateJob update(&service, group); |
| 1073 |
| 1074 // Pretend group is in downloading state. |
| 1075 group->update_job_ = &update; |
| 1076 group->update_status_ = AppCacheGroup::DOWNLOADING; |
| 1077 |
| 1078 update.StartUpdate(NULL, GURL::EmptyGURL()); |
| 1079 EXPECT_EQ(AppCacheGroup::DOWNLOADING, group->update_status()); |
| 1080 |
| 1081 MockFrontend mock_frontend; |
| 1082 AppCacheHost host(1, &mock_frontend, &service); |
| 1083 update.StartUpdate(&host, GURL::EmptyGURL()); |
| 1084 |
| 1085 MockFrontend::RaisedEvents events = mock_frontend.raised_events_; |
| 1086 size_t expected = 2; |
| 1087 EXPECT_EQ(expected, events.size()); |
| 1088 expected = 1; |
| 1089 EXPECT_EQ(expected, events[0].first.size()); |
| 1090 EXPECT_EQ(host.host_id(), events[0].first[0]); |
| 1091 EXPECT_EQ(CHECKING_EVENT, events[0].second); |
| 1092 |
| 1093 EXPECT_EQ(expected, events[1].first.size()); |
| 1094 EXPECT_EQ(host.host_id(), events[1].first[0]); |
| 1095 EXPECT_EQ(appcache::DOWNLOADING_EVENT, events[1].second); |
| 1096 |
| 1097 EXPECT_EQ(AppCacheGroup::DOWNLOADING, group->update_status()); |
| 1098 } |
| 1099 |
| 1100 TEST_F(AppCacheUpdateJobTest, StartCacheAttempt) { |
| 1101 RunTestOnIOThread(&AppCacheUpdateJobTest::StartCacheAttemptTest); |
| 1102 } |
| 1103 |
| 1104 TEST_F(AppCacheUpdateJobTest, StartUpgradeAttempt) { |
| 1105 RunTestOnIOThread(&AppCacheUpdateJobTest::StartUpgradeAttemptTest); |
| 1106 } |
| 1107 |
| 1108 TEST_F(AppCacheUpdateJobTest, CacheAttemptFetchManifestFail) { |
| 1109 RunTestOnIOThread(&AppCacheUpdateJobTest::CacheAttemptFetchManifestFailTest); |
| 1110 } |
| 1111 |
| 1112 TEST_F(AppCacheUpdateJobTest, UpgradeFetchManifestFail) { |
| 1113 RunTestOnIOThread(&AppCacheUpdateJobTest::UpgradeFetchManifestFailTest); |
| 1114 } |
| 1115 |
| 1116 TEST_F(AppCacheUpdateJobTest, ManifestRedirect) { |
| 1117 RunTestOnIOThread(&AppCacheUpdateJobTest::ManifestRedirectTest); |
| 1118 } |
| 1119 |
| 1120 TEST_F(AppCacheUpdateJobTest, ManifestWrongMimeType) { |
| 1121 RunTestOnIOThread(&AppCacheUpdateJobTest::ManifestWrongMimeTypeTest); |
| 1122 } |
| 1123 |
| 1124 TEST_F(AppCacheUpdateJobTest, ManifestNotFound) { |
| 1125 RunTestOnIOThread(&AppCacheUpdateJobTest::ManifestNotFoundTest); |
| 1126 } |
| 1127 |
| 1128 TEST_F(AppCacheUpdateJobTest, ManifestGone) { |
| 1129 RunTestOnIOThread(&AppCacheUpdateJobTest::ManifestGoneTest); |
| 1130 } |
| 1131 |
| 1132 TEST_F(AppCacheUpdateJobTest, CacheAttemptNotModified) { |
| 1133 RunTestOnIOThread(&AppCacheUpdateJobTest::CacheAttemptNotModifiedTest); |
| 1134 } |
| 1135 |
| 1136 TEST_F(AppCacheUpdateJobTest, UpgradeNotModified) { |
| 1137 RunTestOnIOThread(&AppCacheUpdateJobTest::UpgradeNotModifiedTest); |
| 1138 } |
| 1139 |
| 1140 TEST_F(AppCacheUpdateJobTest, UpgradeManifestDataUnchanged) { |
| 1141 RunTestOnIOThread(&AppCacheUpdateJobTest::UpgradeManifestDataUnchangedTest); |
| 1142 } |
| 1143 |
| 1144 TEST_F(AppCacheUpdateJobTest, BasicCacheAttemptSuccess) { |
| 1145 RunTestOnIOThread(&AppCacheUpdateJobTest::BasicCacheAttemptSuccessTest); |
| 1146 } |
| 1147 |
| 1148 TEST_F(AppCacheUpdateJobTest, BasicUpgradeSuccess) { |
| 1149 RunTestOnIOThread(&AppCacheUpdateJobTest::BasicUpgradeSuccessTest); |
| 1150 } |
| 1151 |
| 1152 TEST_F(AppCacheUpdateJobTest, UpgradeSuccessMergedTypes) { |
| 1153 RunTestOnIOThread(&AppCacheUpdateJobTest::UpgradeSuccessMergedTypesTest); |
| 1154 } |
| 1155 |
| 1156 TEST_F(AppCacheUpdateJobTest, CacheAttemptFailUrlFetch) { |
| 1157 RunTestOnIOThread(&AppCacheUpdateJobTest::CacheAttemptFailUrlFetchTest); |
| 1158 } |
| 1159 |
| 1160 TEST_F(AppCacheUpdateJobTest, UpgradeFailUrlFetch) { |
| 1161 RunTestOnIOThread(&AppCacheUpdateJobTest::UpgradeFailUrlFetchTest); |
| 1162 } |
| 1163 |
| 1164 TEST_F(AppCacheUpdateJobTest, UpgradeFailMasterUrlFetch) { |
| 1165 RunTestOnIOThread(&AppCacheUpdateJobTest::UpgradeFailMasterUrlFetchTest); |
| 1166 } |
| 1167 |
| 1168 TEST_F(AppCacheUpdateJobTest, EmptyManifest) { |
| 1169 RunTestOnIOThread(&AppCacheUpdateJobTest::EmptyManifestTest); |
| 1170 } |
| 1171 |
| 1172 } // namespace appcache |
| OLD | NEW |