1 // Copyright 2012 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 <string> 7 #include <vector> 8 9 #include "testing/gtest/include/gtest/gtest.h" 10 11 #include "base/bind.h" 12 #include "base/bind_helpers.h" 13 #include "base/callback.h" 14 #include "base/compiler_specific.h" 15 #include "base/location.h" 16 #include "base/memory/ref_counted.h" 17 #include "base/memory/scoped_ptr.h" 18 #include "base/message_loop/message_loop.h" 19 #include "base/strings/string16.h" 20 #include "base/strings/utf_string_conversions.h" 21 #include "base/synchronization/waitable_event.h" 22 #include "base/time/time.h" 23 #include "chrome/browser/autofill/personal_data_manager_factory.h" 24 #include "chrome/browser/signin/signin_manager.h" 25 #include "chrome/browser/signin/signin_manager_factory.h" 26 #include "chrome/browser/signin/token_service_factory.h" 27 #include "chrome/browser/sync/abstract_profile_sync_service_test.h" 28 #include "chrome/browser/sync/glue/autofill_data_type_controller.h" 29 #include "chrome/browser/sync/glue/autofill_profile_data_type_controller.h" 30 #include "chrome/browser/sync/glue/data_type_controller.h" 31 #include "chrome/browser/sync/glue/generic_change_processor.h" 32 #include "chrome/browser/sync/glue/shared_change_processor.h" 33 #include "chrome/browser/sync/profile_sync_components_factory.h" 34 #include "chrome/browser/sync/profile_sync_service.h" 35 #include "chrome/browser/sync/profile_sync_service_factory.h" 36 #include "chrome/browser/sync/profile_sync_test_util.h" 37 #include "chrome/browser/sync/test_profile_sync_service.h" 38 #include "chrome/browser/webdata/autocomplete_syncable_service.h" 39 #include "chrome/browser/webdata/autofill_profile_syncable_service.h" 40 #include "chrome/browser/webdata/web_data_service_factory.h" 41 #include "components/autofill/core/browser/autofill_common_test.h" 42 #include "components/autofill/core/browser/personal_data_manager.h" 43 #include "components/autofill/core/browser/webdata/autofill_change.h" 44 #include "components/autofill/core/browser/webdata/autofill_entry.h" 45 #include "components/autofill/core/browser/webdata/autofill_table.h" 46 #include "components/autofill/core/browser/webdata/autofill_webdata_service.h" 47 #include "components/webdata/common/web_data_service_test_util.h" 48 #include "components/webdata/common/web_database.h" 49 #include "content/public/test/test_browser_thread.h" 50 #include "google_apis/gaia/gaia_constants.h" 51 #include "sync/internal_api/public/base/model_type.h" 52 #include "sync/internal_api/public/data_type_debug_info_listener.h" 53 #include "sync/internal_api/public/read_node.h" 54 #include "sync/internal_api/public/read_transaction.h" 55 #include "sync/internal_api/public/write_node.h" 56 #include "sync/internal_api/public/write_transaction.h" 57 #include "sync/protocol/autofill_specifics.pb.h" 58 #include "sync/syncable/mutable_entry.h" 59 #include "sync/syncable/syncable_write_transaction.h" 60 #include "sync/test/engine/test_id_factory.h" 61 #include "testing/gmock/include/gmock/gmock.h" 62 63 using autofill::AutofillChange; 64 using autofill::AutofillChangeList; 65 using autofill::AutofillEntry; 66 using autofill::ServerFieldType; 67 using autofill::AutofillKey; 68 using autofill::AutofillProfile; 69 using autofill::AutofillProfileChange; 70 using autofill::AutofillTable; 71 using autofill::AutofillWebDataService; 72 using autofill::PersonalDataManager; 73 using base::Time; 74 using base::TimeDelta; 75 using base::WaitableEvent; 76 using browser_sync::AutofillDataTypeController; 77 using browser_sync::AutofillProfileDataTypeController; 78 using browser_sync::DataTypeController; 79 using browser_sync::GenericChangeProcessor; 80 using browser_sync::SharedChangeProcessor; 81 using content::BrowserThread; 82 using syncer::AUTOFILL; 83 using syncer::BaseNode; 84 using syncer::syncable::BASE_VERSION; 85 using syncer::syncable::CREATE; 86 using syncer::syncable::GET_BY_SERVER_TAG; 87 using syncer::syncable::MutableEntry; 88 using syncer::syncable::SERVER_SPECIFICS; 89 using syncer::syncable::SPECIFICS; 90 using syncer::syncable::UNITTEST; 91 using syncer::syncable::WriterTag; 92 using syncer::syncable::WriteTransaction; 93 using testing::_; 94 using testing::DoAll; 95 using testing::ElementsAre; 96 using testing::SetArgumentPointee; 97 using testing::Return; 98 99 class HistoryService; 100 101 namespace syncable { 102 class Id; 103 } 104 105 namespace { 106 107 void RunAndSignal(const base::Closure& cb, WaitableEvent* event) { 108 cb.Run(); 109 event->Signal(); 110 } 111 112 } // namespace 113 114 class AutofillTableMock : public AutofillTable { 115 public: 116 AutofillTableMock() : AutofillTable("en-US") {} 117 MOCK_METHOD2(RemoveFormElement, 118 bool(const string16& name, const string16& value)); // NOLINT 119 MOCK_METHOD1(GetAllAutofillEntries, 120 bool(std::vector<AutofillEntry>* entries)); // NOLINT 121 MOCK_METHOD3(GetAutofillTimestamps, 122 bool(const string16& name, // NOLINT 123 const string16& value, 124 std::vector<base::Time>* timestamps)); 125 MOCK_METHOD1(UpdateAutofillEntries, 126 bool(const std::vector<AutofillEntry>&)); // NOLINT 127 MOCK_METHOD1(GetAutofillProfiles, 128 bool(std::vector<AutofillProfile*>*)); // NOLINT 129 MOCK_METHOD1(UpdateAutofillProfile, 130 bool(const AutofillProfile&)); // NOLINT 131 MOCK_METHOD1(AddAutofillProfile, 132 bool(const AutofillProfile&)); // NOLINT 133 MOCK_METHOD1(RemoveAutofillProfile, 134 bool(const std::string&)); // NOLINT 135 }; 136 137 MATCHER_P(MatchProfiles, profile, "") { 138 return (profile.Compare(arg) == 0); 139 } 140 141 class WebDatabaseFake : public WebDatabase { 142 public: 143 explicit WebDatabaseFake(AutofillTable* autofill_table) { 144 AddTable(autofill_table); 145 } 146 }; 147 148 class MockAutofillBackend : public autofill::AutofillWebDataBackend { 149 public: 150 MockAutofillBackend( 151 WebDatabase* web_database, 152 const base::Closure& on_changed) 153 : web_database_(web_database), 154 on_changed_(on_changed) { 155 } 156 157 virtual ~MockAutofillBackend() {} 158 virtual WebDatabase* GetDatabase() OVERRIDE { return web_database_; } 159 virtual void AddObserver( 160 autofill::AutofillWebDataServiceObserverOnDBThread* observer) OVERRIDE {} 161 virtual void RemoveObserver( 162 autofill::AutofillWebDataServiceObserverOnDBThread* observer) OVERRIDE {} 163 virtual void RemoveExpiredFormElements() OVERRIDE {} 164 virtual void NotifyOfMultipleAutofillChanges() OVERRIDE { 165 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 166 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, on_changed_); 167 } 168 169 private: 170 WebDatabase* web_database_; 171 base::Closure on_changed_; 172 }; 173 174 class ProfileSyncServiceAutofillTest; 175 176 template<class AutofillProfile> 177 syncer::ModelType GetModelType() { 178 return syncer::UNSPECIFIED; 179 } 180 181 template<> 182 syncer::ModelType GetModelType<AutofillEntry>() { 183 return syncer::AUTOFILL; 184 } 185 186 template<> 187 syncer::ModelType GetModelType<AutofillProfile>() { 188 return syncer::AUTOFILL_PROFILE; 189 } 190 191 class TokenWebDataServiceFake : public TokenWebData { 192 public: 193 TokenWebDataServiceFake() 194 : TokenWebData() { 195 } 196 197 virtual bool IsDatabaseLoaded() OVERRIDE { 198 return true; 199 } 200 201 virtual WebDataService::Handle GetAllTokens( 202 WebDataServiceConsumer* consumer) OVERRIDE { 203 // TODO(tim): It would be nice if WebDataService was injected on 204 // construction of TokenService rather than fetched by Initialize so that 205 // this isn't necessary (we could pass a NULL service). We currently do 206 // return it via EXPECT_CALLs, but without depending on order-of- 207 // initialization (which seems way more fragile) we can't tell which 208 // component is asking at what time, and some components in these Autofill 209 // tests require a WebDataService. 210 return 0; 211 } 212 213 private: 214 virtual ~TokenWebDataServiceFake() {} 215 216 DISALLOW_COPY_AND_ASSIGN(TokenWebDataServiceFake); 217 }; 218 219 class WebDataServiceFake : public AutofillWebDataService { 220 public: 221 WebDataServiceFake() 222 : AutofillWebDataService(), 223 web_database_(NULL), 224 autocomplete_syncable_service_(NULL), 225 autofill_profile_syncable_service_(NULL), 226 syncable_service_created_or_destroyed_(false, false) { 227 } 228 229 void SetDatabase(WebDatabase* web_database) { 230 web_database_ = web_database; 231 } 232 233 void StartSyncableService() { 234 // The |autofill_profile_syncable_service_| must be constructed on the DB 235 // thread. 236 const base::Closure& on_changed_callback = base::Bind( 237 &WebDataServiceFake::NotifyAutofillMultipleChangedOnUIThread, 238 AsWeakPtr()); 239 240 BrowserThread::PostTask(BrowserThread::DB, FROM_HERE, 241 base::Bind(&WebDataServiceFake::CreateSyncableService, 242 base::Unretained(this), 243 on_changed_callback)); 244 syncable_service_created_or_destroyed_.Wait(); 245 } 246 247 void ShutdownSyncableService() { 248 // The |autofill_profile_syncable_service_| must be destructed on the DB 249 // thread. 250 BrowserThread::PostTask(BrowserThread::DB, FROM_HERE, 251 base::Bind(&WebDataServiceFake::DestroySyncableService, 252 base::Unretained(this))); 253 syncable_service_created_or_destroyed_.Wait(); 254 } 255 256 virtual bool IsDatabaseLoaded() OVERRIDE { 257 return true; 258 } 259 260 virtual WebDatabase* GetDatabase() OVERRIDE { 261 return web_database_; 262 } 263 264 void OnAutofillEntriesChanged(const AutofillChangeList& changes) { 265 WaitableEvent event(true, false); 266 267 base::Closure notify_cb = 268 base::Bind(&AutocompleteSyncableService::AutofillEntriesChanged, 269 base::Unretained(autocomplete_syncable_service_), 270 changes); 271 BrowserThread::PostTask( 272 BrowserThread::DB, 273 FROM_HERE, 274 base::Bind(&RunAndSignal, notify_cb, &event)); 275 event.Wait(); 276 } 277 278 void OnAutofillProfileChanged(const AutofillProfileChange& changes) { 279 WaitableEvent event(true, false); 280 281 base::Closure notify_cb = 282 base::Bind(&AutocompleteSyncableService::AutofillProfileChanged, 283 base::Unretained(autofill_profile_syncable_service_), 284 changes); 285 BrowserThread::PostTask( 286 BrowserThread::DB, 287 FROM_HERE, 288 base::Bind(&RunAndSignal, notify_cb, &event)); 289 event.Wait(); 290 } 291 292 private: 293 virtual ~WebDataServiceFake() {} 294 295 void CreateSyncableService(const base::Closure& on_changed_callback) { 296 ASSERT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB)); 297 // These services are deleted in DestroySyncableService(). 298 backend_.reset(new MockAutofillBackend( 299 GetDatabase(), on_changed_callback)); 300 AutocompleteSyncableService::CreateForWebDataServiceAndBackend( 301 this, backend_.get()); 302 AutofillProfileSyncableService::CreateForWebDataServiceAndBackend( 303 this, backend_.get(), "en-US"); 304 305 autocomplete_syncable_service_ = 306 AutocompleteSyncableService::FromWebDataService(this); 307 autofill_profile_syncable_service_ = 308 AutofillProfileSyncableService::FromWebDataService(this); 309 310 syncable_service_created_or_destroyed_.Signal(); 311 } 312 313 void DestroySyncableService() { 314 ASSERT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB)); 315 autocomplete_syncable_service_ = NULL; 316 autofill_profile_syncable_service_ = NULL; 317 backend_.reset(); 318 syncable_service_created_or_destroyed_.Signal(); 319 } 320 321 WebDatabase* web_database_; 322 AutocompleteSyncableService* autocomplete_syncable_service_; 323 AutofillProfileSyncableService* autofill_profile_syncable_service_; 324 scoped_ptr<autofill::AutofillWebDataBackend> backend_; 325 326 WaitableEvent syncable_service_created_or_destroyed_; 327 328 DISALLOW_COPY_AND_ASSIGN(WebDataServiceFake); 329 }; 330 331 BrowserContextKeyedService* BuildMockWebDataServiceWrapper( 332 content::BrowserContext* profile) { 333 return new MockWebDataServiceWrapper( 334 NULL, 335 new WebDataServiceFake(), 336 new TokenWebDataServiceFake()); 337 } 338 339 ACTION_P(MakeAutocompleteSyncComponents, wds) { 340 EXPECT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB)); 341 if (!BrowserThread::CurrentlyOn(BrowserThread::DB)) 342 return base::WeakPtr<syncer::SyncableService>(); 343 return AutocompleteSyncableService::FromWebDataService(wds)->AsWeakPtr(); 344 } 345 346 ACTION_P(ReturnNewDataTypeManagerWithDebugListener, debug_listener) { 347 return new browser_sync::DataTypeManagerImpl( 348 debug_listener, 349 arg1, 350 arg2, 351 arg3, 352 arg4, 353 arg5); 354 } 355 356 ACTION(MakeGenericChangeProcessor) { 357 syncer::UserShare* user_share = arg0->GetUserShare(); 358 return new GenericChangeProcessor( 359 arg1, 360 arg2, 361 arg3, 362 user_share); 363 } 364 365 ACTION(MakeSharedChangeProcessor) { 366 return new SharedChangeProcessor(); 367 } 368 369 ACTION_P(MakeAutofillProfileSyncComponents, wds) { 370 EXPECT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB)); 371 if (!BrowserThread::CurrentlyOn(BrowserThread::DB)) 372 return base::WeakPtr<syncer::SyncableService>(); 373 return AutofillProfileSyncableService::FromWebDataService(wds)->AsWeakPtr(); 374 } 375 376 class AbstractAutofillFactory { 377 public: 378 virtual DataTypeController* CreateDataTypeController( 379 ProfileSyncComponentsFactory* factory, 380 ProfileMock* profile, 381 ProfileSyncService* service) = 0; 382 virtual void SetExpectation(ProfileSyncComponentsFactoryMock* factory, 383 ProfileSyncService* service, 384 AutofillWebDataService* wds, 385 DataTypeController* dtc) = 0; 386 virtual ~AbstractAutofillFactory() {} 387 }; 388 389 class AutofillEntryFactory : public AbstractAutofillFactory { 390 public: 391 virtual browser_sync::DataTypeController* CreateDataTypeController( 392 ProfileSyncComponentsFactory* factory, 393 ProfileMock* profile, 394 ProfileSyncService* service) OVERRIDE { 395 return new AutofillDataTypeController(factory, profile, service); 396 } 397 398 virtual void SetExpectation(ProfileSyncComponentsFactoryMock* factory, 399 ProfileSyncService* service, 400 AutofillWebDataService* wds, 401 DataTypeController* dtc) OVERRIDE { 402 EXPECT_CALL(*factory, CreateGenericChangeProcessor(_,_,_,_)). 403 WillOnce(MakeGenericChangeProcessor()); 404 EXPECT_CALL(*factory, CreateSharedChangeProcessor()). 405 WillOnce(MakeSharedChangeProcessor()); 406 EXPECT_CALL(*factory, GetSyncableServiceForType(syncer::AUTOFILL)). 407 WillOnce(MakeAutocompleteSyncComponents(wds)); 408 } 409 }; 410 411 class AutofillProfileFactory : public AbstractAutofillFactory { 412 public: 413 virtual browser_sync::DataTypeController* CreateDataTypeController( 414 ProfileSyncComponentsFactory* factory, 415 ProfileMock* profile, 416 ProfileSyncService* service) OVERRIDE { 417 return new AutofillProfileDataTypeController(factory, profile, service); 418 } 419 420 virtual void SetExpectation(ProfileSyncComponentsFactoryMock* factory, 421 ProfileSyncService* service, 422 AutofillWebDataService* wds, 423 DataTypeController* dtc) OVERRIDE { 424 EXPECT_CALL(*factory, CreateGenericChangeProcessor(_,_,_,_)). 425 WillOnce(MakeGenericChangeProcessor()); 426 EXPECT_CALL(*factory, CreateSharedChangeProcessor()). 427 WillOnce(MakeSharedChangeProcessor()); 428 EXPECT_CALL(*factory, 429 GetSyncableServiceForType(syncer::AUTOFILL_PROFILE)). 430 WillOnce(MakeAutofillProfileSyncComponents(wds)); 431 } 432 }; 433 434 class MockPersonalDataManager : public PersonalDataManager { 435 public: 436 MockPersonalDataManager() : PersonalDataManager("en-US") {} 437 MOCK_CONST_METHOD0(IsDataLoaded, bool()); 438 MOCK_METHOD0(LoadProfiles, void()); 439 MOCK_METHOD0(LoadCreditCards, void()); 440 MOCK_METHOD0(Refresh, void()); 441 }; 442 443 class MockPersonalDataManagerService 444 : public autofill::PersonalDataManagerService { 445 public: 446 static BrowserContextKeyedService* Build(content::BrowserContext* profile) { 447 return new MockPersonalDataManagerService(); 448 } 449 450 MockPersonalDataManagerService() { 451 personal_data_manager_.reset(new MockPersonalDataManager()); 452 } 453 virtual ~MockPersonalDataManagerService() {} 454 455 virtual void Shutdown() OVERRIDE { 456 personal_data_manager_.reset(); 457 } 458 459 virtual MockPersonalDataManager* GetPersonalDataManager() OVERRIDE { 460 return personal_data_manager_.get(); 461 } 462 463 private: 464 scoped_ptr<MockPersonalDataManager> personal_data_manager_; 465 DISALLOW_COPY_AND_ASSIGN(MockPersonalDataManagerService); 466 }; 467 468 template <class T> class AddAutofillHelper; 469 470 class ProfileSyncServiceAutofillTest 471 : public AbstractProfileSyncServiceTest, 472 public syncer::DataTypeDebugInfoListener { 473 public: 474 // DataTypeDebugInfoListener implementation. 475 virtual void OnSingleDataTypeConfigureComplete( 476 const syncer::DataTypeConfigurationStats& configuration_stats) OVERRIDE { 477 association_stats_ = configuration_stats.association_stats; 478 } 479 virtual void OnConfigureComplete() OVERRIDE { 480 // Do nothing. 481 } 482 483 protected: 484 ProfileSyncServiceAutofillTest() 485 : debug_ptr_factory_(this) { 486 } 487 virtual ~ProfileSyncServiceAutofillTest() { 488 } 489 490 AutofillProfileFactory profile_factory_; 491 AutofillEntryFactory entry_factory_; 492 493 AbstractAutofillFactory* GetFactory(syncer::ModelType type) { 494 if (type == syncer::AUTOFILL) { 495 return &entry_factory_; 496 } else if (type == syncer::AUTOFILL_PROFILE) { 497 return &profile_factory_; 498 } else { 499 NOTREACHED(); 500 return NULL; 501 } 502 } 503 504 virtual void SetUp() OVERRIDE { 505 AbstractProfileSyncServiceTest::SetUp(); 506 profile_.reset(new ProfileMock()); 507 web_database_.reset(new WebDatabaseFake(&autofill_table_)); 508 MockWebDataServiceWrapper* wrapper = 509 static_cast<MockWebDataServiceWrapper*>( 510 WebDataServiceFactory::GetInstance()->SetTestingFactoryAndUse( 511 profile_.get(), BuildMockWebDataServiceWrapper)); 512 web_data_service_ = 513 static_cast<WebDataServiceFake*>(wrapper->GetAutofillWebData().get()); 514 web_data_service_->SetDatabase(web_database_.get()); 515 516 MockPersonalDataManagerService* personal_data_manager_service = 517 static_cast<MockPersonalDataManagerService*>( 518 autofill::PersonalDataManagerFactory::GetInstance() 519 ->SetTestingFactoryAndUse( 520 profile_.get(), MockPersonalDataManagerService::Build)); 521 personal_data_manager_ = 522 personal_data_manager_service->GetPersonalDataManager(); 523 524 token_service_ = static_cast<TokenService*>( 525 TokenServiceFactory::GetInstance()->SetTestingFactoryAndUse( 526 profile_.get(), BuildTokenService)); 527 ProfileOAuth2TokenServiceFactory::GetInstance()->SetTestingFactory( 528 profile_.get(), FakeOAuth2TokenService::BuildTokenService); 529 EXPECT_CALL(*personal_data_manager_, LoadProfiles()).Times(1); 530 EXPECT_CALL(*personal_data_manager_, LoadCreditCards()).Times(1); 531 532 personal_data_manager_->Init(profile_.get()); 533 534 web_data_service_->StartSyncableService(); 535 } 536 537 virtual void TearDown() OVERRIDE { 538 // Note: The tear down order is important. 539 ProfileSyncServiceFactory::GetInstance()->SetTestingFactory( 540 profile_.get(), NULL); 541 web_data_service_->ShutdownOnUIThread(); 542 web_data_service_->ShutdownSyncableService(); 543 web_data_service_ = NULL; 544 // To prevent a leak, fully release TestURLRequestContext to ensure its 545 // destruction on the IO message loop. 546 profile_.reset(); 547 AbstractProfileSyncServiceTest::TearDown(); 548 } 549 550 551 int GetSyncCount(syncer::ModelType type) { 552 syncer::ReadTransaction trans(FROM_HERE, sync_service_->GetUserShare()); 553 syncer::ReadNode node(&trans); 554 if (node.InitByTagLookup(syncer::ModelTypeToRootTag(type)) != 555 syncer::BaseNode::INIT_OK) 556 return 0; 557 return node.GetTotalNodeCount() - 1; 558 } 559 560 void StartSyncService(const base::Closure& callback, 561 bool will_fail_association, 562 syncer::ModelType type) { 563 AbstractAutofillFactory* factory = GetFactory(type); 564 SigninManagerBase* signin = 565 SigninManagerFactory::GetForProfile(profile_.get()); 566 signin->SetAuthenticatedUsername("test_user (at) gmail.com"); 567 sync_service_ = static_cast<TestProfileSyncService*>( 568 ProfileSyncServiceFactory::GetInstance()->SetTestingFactoryAndUse( 569 profile_.get(), &TestProfileSyncService::BuildAutoStartAsyncInit)); 570 sync_service_->set_backend_init_callback(callback); 571 572 ProfileSyncComponentsFactoryMock* components = 573 sync_service_->components_factory_mock(); 574 DataTypeController* data_type_controller = 575 factory->CreateDataTypeController(components, 576 profile_.get(), 577 sync_service_); 578 factory->SetExpectation(components, 579 sync_service_, 580 web_data_service_.get(), 581 data_type_controller); 582 583 EXPECT_CALL(*components, CreateDataTypeManager(_, _, _, _, _, _)). 584 WillOnce(ReturnNewDataTypeManagerWithDebugListener( 585 syncer::MakeWeakHandle(debug_ptr_factory_.GetWeakPtr()))); 586 587 EXPECT_CALL(*personal_data_manager_, IsDataLoaded()). 588 WillRepeatedly(Return(true)); 589 590 // We need tokens to get the tests going 591 token_service_->IssueAuthTokenForTest( 592 GaiaConstants::kGaiaOAuth2LoginRefreshToken, "oauth2_login_token"); 593 token_service_->IssueAuthTokenForTest( 594 GaiaConstants::kSyncService, "token"); 595 596 sync_service_->RegisterDataTypeController(data_type_controller); 597 sync_service_->Initialize(); 598 base::MessageLoop::current()->Run(); 599 600 // It's possible this test triggered an unrecoverable error, in which case 601 // we can't get the sync count. 602 if (sync_service_->ShouldPushChanges()) { 603 EXPECT_EQ(GetSyncCount(type), 604 association_stats_.num_sync_items_after_association); 605 } 606 EXPECT_EQ(association_stats_.num_sync_items_after_association, 607 association_stats_.num_sync_items_before_association + 608 association_stats_.num_sync_items_added - 609 association_stats_.num_sync_items_deleted); 610 } 611 612 bool AddAutofillSyncNode(const AutofillEntry& entry) { 613 syncer::WriteTransaction trans(FROM_HERE, sync_service_->GetUserShare()); 614 syncer::ReadNode autofill_root(&trans); 615 if (autofill_root.InitByTagLookup( 616 syncer::ModelTypeToRootTag(syncer::AUTOFILL)) != 617 BaseNode::INIT_OK) { 618 return false; 619 } 620 621 syncer::WriteNode node(&trans); 622 std::string tag = AutocompleteSyncableService::KeyToTag( 623 UTF16ToUTF8(entry.key().name()), UTF16ToUTF8(entry.key().value())); 624 syncer::WriteNode::InitUniqueByCreationResult result = 625 node.InitUniqueByCreation(syncer::AUTOFILL, autofill_root, tag); 626 if (result != syncer::WriteNode::INIT_SUCCESS) 627 return false; 628 629 sync_pb::EntitySpecifics specifics; 630 AutocompleteSyncableService::WriteAutofillEntry(entry, &specifics); 631 sync_pb::AutofillSpecifics* autofill_specifics = 632 specifics.mutable_autofill(); 633 node.SetAutofillSpecifics(*autofill_specifics); 634 return true; 635 } 636 637 bool AddAutofillSyncNode(const AutofillProfile& profile) { 638 syncer::WriteTransaction trans(FROM_HERE, sync_service_->GetUserShare()); 639 syncer::ReadNode autofill_root(&trans); 640 if (autofill_root.InitByTagLookup(kAutofillProfileTag) != 641 BaseNode::INIT_OK) { 642 return false; 643 } 644 syncer::WriteNode node(&trans); 645 std::string tag = profile.guid(); 646 syncer::WriteNode::InitUniqueByCreationResult result = 647 node.InitUniqueByCreation(syncer::AUTOFILL_PROFILE, 648 autofill_root, tag); 649 if (result != syncer::WriteNode::INIT_SUCCESS) 650 return false; 651 652 sync_pb::EntitySpecifics specifics; 653 AutofillProfileSyncableService::WriteAutofillProfile(profile, &specifics); 654 sync_pb::AutofillProfileSpecifics* profile_specifics = 655 specifics.mutable_autofill_profile(); 656 node.SetAutofillProfileSpecifics(*profile_specifics); 657 return true; 658 } 659 660 bool GetAutofillEntriesFromSyncDB(std::vector<AutofillEntry>* entries, 661 std::vector<AutofillProfile>* profiles) { 662 syncer::ReadTransaction trans(FROM_HERE, sync_service_->GetUserShare()); 663 syncer::ReadNode autofill_root(&trans); 664 if (autofill_root.InitByTagLookup( 665 syncer::ModelTypeToRootTag(syncer::AUTOFILL)) != 666 BaseNode::INIT_OK) { 667 return false; 668 } 669 670 int64 child_id = autofill_root.GetFirstChildId(); 671 while (child_id != syncer::kInvalidId) { 672 syncer::ReadNode child_node(&trans); 673 if (child_node.InitByIdLookup(child_id) != BaseNode::INIT_OK) 674 return false; 675 676 const sync_pb::AutofillSpecifics& autofill( 677 child_node.GetAutofillSpecifics()); 678 if (autofill.has_value()) { 679 AutofillKey key(UTF8ToUTF16(autofill.name()), 680 UTF8ToUTF16(autofill.value())); 681 std::vector<base::Time> timestamps; 682 int timestamps_count = autofill.usage_timestamp_size(); 683 for (int i = 0; i < timestamps_count; ++i) { 684 timestamps.push_back(Time::FromInternalValue( 685 autofill.usage_timestamp(i))); 686 } 687 entries->push_back(AutofillEntry(key, timestamps)); 688 } else if (autofill.has_profile()) { 689 AutofillProfile p; 690 p.set_guid(autofill.profile().guid()); 691 AutofillProfileSyncableService::OverwriteProfileWithServerData( 692 autofill.profile(), &p, "en-US"); 693 profiles->push_back(p); 694 } 695 child_id = child_node.GetSuccessorId(); 696 } 697 return true; 698 } 699 700 bool GetAutofillProfilesFromSyncDBUnderProfileNode( 701 std::vector<AutofillProfile>* profiles) { 702 syncer::ReadTransaction trans(FROM_HERE, sync_service_->GetUserShare()); 703 syncer::ReadNode autofill_root(&trans); 704 if (autofill_root.InitByTagLookup(kAutofillProfileTag) != 705 BaseNode::INIT_OK) { 706 return false; 707 } 708 709 int64 child_id = autofill_root.GetFirstChildId(); 710 while (child_id != syncer::kInvalidId) { 711 syncer::ReadNode child_node(&trans); 712 if (child_node.InitByIdLookup(child_id) != BaseNode::INIT_OK) 713 return false; 714 715 const sync_pb::AutofillProfileSpecifics& autofill( 716 child_node.GetAutofillProfileSpecifics()); 717 AutofillProfile p; 718 p.set_guid(autofill.guid()); 719 AutofillProfileSyncableService::OverwriteProfileWithServerData( 720 autofill, &p, "en-US"); 721 profiles->push_back(p); 722 child_id = child_node.GetSuccessorId(); 723 } 724 return true; 725 } 726 727 void SetIdleChangeProcessorExpectations() { 728 EXPECT_CALL(autofill_table_, RemoveFormElement(_, _)).Times(0); 729 EXPECT_CALL(autofill_table_, GetAutofillTimestamps(_, _, _)).Times(0); 730 EXPECT_CALL(autofill_table_, UpdateAutofillEntries(_)).Times(0); 731 } 732 733 static AutofillEntry MakeAutofillEntry(const char* name, 734 const char* value, 735 int time_shift0, 736 int time_shift1) { 737 // Time deep in the past would cause Autocomplete sync to discard the 738 // entries. 739 static Time base_time = Time::Now().LocalMidnight(); 740 741 std::vector<Time> timestamps; 742 if (time_shift0 > 0) 743 timestamps.push_back(base_time + TimeDelta::FromSeconds(time_shift0)); 744 if (time_shift1 > 0) 745 timestamps.push_back(base_time + TimeDelta::FromSeconds(time_shift1)); 746 return AutofillEntry( 747 AutofillKey(ASCIIToUTF16(name), ASCIIToUTF16(value)), timestamps); 748 } 749 750 static AutofillEntry MakeAutofillEntry(const char* name, 751 const char* value, 752 int time_shift) { 753 return MakeAutofillEntry(name, value, time_shift, -1); 754 } 755 756 friend class AddAutofillHelper<AutofillEntry>; 757 friend class AddAutofillHelper<AutofillProfile>; 758 friend class FakeServerUpdater; 759 760 scoped_ptr<ProfileMock> profile_; 761 AutofillTableMock autofill_table_; 762 scoped_ptr<WebDatabaseFake> web_database_; 763 scoped_refptr<WebDataServiceFake> web_data_service_; 764 MockPersonalDataManager* personal_data_manager_; 765 syncer::DataTypeAssociationStats association_stats_; 766 base::WeakPtrFactory<DataTypeDebugInfoListener> debug_ptr_factory_; 767 }; 768 769 template <class T> 770 class AddAutofillHelper { 771 public: 772 AddAutofillHelper(ProfileSyncServiceAutofillTest* test, 773 const std::vector<T>& entries) 774 : callback_(base::Bind(&AddAutofillHelper::AddAutofillCallback, 775 base::Unretained(this), test, entries)), 776 success_(false) { 777 } 778 779 const base::Closure& callback() const { return callback_; } 780 bool success() { return success_; } 781 782 private: 783 void AddAutofillCallback(ProfileSyncServiceAutofillTest* test, 784 const std::vector<T>& entries) { 785 if (!test->CreateRoot(GetModelType<T>())) 786 return; 787 788 for (size_t i = 0; i < entries.size(); ++i) { 789 if (!test->AddAutofillSyncNode(entries[i])) 790 return; 791 } 792 success_ = true; 793 } 794 795 base::Closure callback_; 796 bool success_; 797 }; 798 799 // Overload write transaction to use custom NotifyTransactionComplete 800 class WriteTransactionTest: public WriteTransaction { 801 public: 802 WriteTransactionTest(const tracked_objects::Location& from_here, 803 WriterTag writer, 804 syncer::syncable::Directory* directory, 805 scoped_ptr<WaitableEvent>* wait_for_syncapi) 806 : WriteTransaction(from_here, writer, directory), 807 wait_for_syncapi_(wait_for_syncapi) { } 808 809 virtual void NotifyTransactionComplete( 810 syncer::ModelTypeSet types) OVERRIDE { 811 // This is where we differ. Force a thread change here, giving another 812 // thread a chance to create a WriteTransaction 813 (*wait_for_syncapi_)->Wait(); 814 815 WriteTransaction::NotifyTransactionComplete(types); 816 } 817 818 private: 819 scoped_ptr<WaitableEvent>* wait_for_syncapi_; 820 }; 821 822 // Our fake server updater. Needs the RefCountedThreadSafe inheritance so we can 823 // post tasks with it. 824 class FakeServerUpdater : public base::RefCountedThreadSafe<FakeServerUpdater> { 825 public: 826 FakeServerUpdater(TestProfileSyncService* service, 827 scoped_ptr<WaitableEvent>* wait_for_start, 828 scoped_ptr<WaitableEvent>* wait_for_syncapi) 829 : entry_(ProfileSyncServiceAutofillTest::MakeAutofillEntry("0", "0", 0)), 830 service_(service), 831 wait_for_start_(wait_for_start), 832 wait_for_syncapi_(wait_for_syncapi), 833 is_finished_(false, false) { } 834 835 void Update() { 836 // This gets called in a modelsafeworker thread. 837 ASSERT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB)); 838 839 syncer::UserShare* user_share = service_->GetUserShare(); 840 syncer::syncable::Directory* directory = user_share->directory.get(); 841 842 // Create autofill protobuf. 843 std::string tag = AutocompleteSyncableService::KeyToTag( 844 UTF16ToUTF8(entry_.key().name()), UTF16ToUTF8(entry_.key().value())); 845 sync_pb::AutofillSpecifics new_autofill; 846 new_autofill.set_name(UTF16ToUTF8(entry_.key().name())); 847 new_autofill.set_value(UTF16ToUTF8(entry_.key().value())); 848 const std::vector<base::Time>& ts(entry_.timestamps()); 849 for (std::vector<base::Time>::const_iterator timestamp = ts.begin(); 850 timestamp != ts.end(); ++timestamp) { 851 new_autofill.add_usage_timestamp(timestamp->ToInternalValue()); 852 } 853 854 sync_pb::EntitySpecifics entity_specifics; 855 entity_specifics.mutable_autofill()->CopyFrom(new_autofill); 856 857 { 858 // Tell main thread we've started 859 (*wait_for_start_)->Signal(); 860 861 // Create write transaction. 862 WriteTransactionTest trans(FROM_HERE, UNITTEST, directory, 863 wait_for_syncapi_); 864 865 // Create actual entry based on autofill protobuf information. 866 // Simulates effects of UpdateLocalDataFromServerData 867 MutableEntry parent(&trans, GET_BY_SERVER_TAG, 868 syncer::ModelTypeToRootTag(syncer::AUTOFILL)); 869 MutableEntry item(&trans, CREATE, syncer::AUTOFILL, 870 parent.Get(syncer::syncable::ID), tag); 871 ASSERT_TRUE(item.good()); 872 item.Put(SPECIFICS, entity_specifics); 873 item.Put(SERVER_SPECIFICS, entity_specifics); 874 item.Put(BASE_VERSION, 1); 875 syncer::syncable::Id server_item_id = 876 service_->id_factory()->NewServerId(); 877 item.Put(syncer::syncable::ID, server_item_id); 878 syncer::syncable::Id new_predecessor; 879 ASSERT_TRUE(item.PutPredecessor(new_predecessor)); 880 } 881 DVLOG(1) << "FakeServerUpdater finishing."; 882 is_finished_.Signal(); 883 } 884 885 void CreateNewEntry(const AutofillEntry& entry) { 886 entry_ = entry; 887 ASSERT_FALSE(BrowserThread::CurrentlyOn(BrowserThread::DB)); 888 if (!BrowserThread::PostTask( 889 BrowserThread::DB, FROM_HERE, 890 base::Bind(&FakeServerUpdater::Update, this))) { 891 NOTREACHED() << "Failed to post task to the db thread."; 892 return; 893 } 894 } 895 896 void CreateNewEntryAndWait(const AutofillEntry& entry) { 897 entry_ = entry; 898 ASSERT_FALSE(BrowserThread::CurrentlyOn(BrowserThread::DB)); 899 is_finished_.Reset(); 900 if (!BrowserThread::PostTask(BrowserThread::DB, FROM_HERE, 901 base::Bind(&FakeServerUpdater::Update, this))) { 902 NOTREACHED() << "Failed to post task to the db thread."; 903 return; 904 } 905 is_finished_.Wait(); 906 } 907 908 private: 909 friend class base::RefCountedThreadSafe<FakeServerUpdater>; 910 ~FakeServerUpdater() { } 911 912 AutofillEntry entry_; 913 TestProfileSyncService* service_; 914 scoped_ptr<WaitableEvent>* wait_for_start_; 915 scoped_ptr<WaitableEvent>* wait_for_syncapi_; 916 WaitableEvent is_finished_; 917 syncer::syncable::Id parent_id_; 918 }; 919 920 namespace { 921 922 // Checks if the field of type |field_type| in |profile1| includes all values 923 // of the field in |profile2|. 924 bool IncludesField(const AutofillProfile& profile1, 925 const AutofillProfile& profile2, 926 ServerFieldType field_type) { 927 std::vector<string16> values1; 928 profile1.GetRawMultiInfo(field_type, &values1); 929 std::vector<string16> values2; 930 profile2.GetRawMultiInfo(field_type, &values2); 931 932 std::set<string16> values_set; 933 for (size_t i = 0; i < values1.size(); ++i) 934 values_set.insert(values1[i]); 935 for (size_t i = 0; i < values2.size(); ++i) 936 if (values_set.find(values2[i]) == values_set.end()) 937 return false; 938 return true; 939 } 940 941 } // namespace 942 943 // TODO(skrul): Test abort startup. 944 // TODO(skrul): Test processing of cloud changes. 945 // TODO(tim): Add autofill data type controller test, and a case to cover 946 // waiting for the PersonalDataManager. 947 TEST_F(ProfileSyncServiceAutofillTest, FailModelAssociation) { 948 // Don't create the root autofill node so startup fails. 949 StartSyncService(base::Closure(), true, syncer::AUTOFILL); 950 EXPECT_TRUE(sync_service_->HasUnrecoverableError()); 951 } 952 953 TEST_F(ProfileSyncServiceAutofillTest, EmptyNativeEmptySync) { 954 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)).WillOnce(Return(true)); 955 SetIdleChangeProcessorExpectations(); 956 CreateRootHelper create_root(this, syncer::AUTOFILL); 957 EXPECT_CALL(*personal_data_manager_, Refresh()); 958 StartSyncService(create_root.callback(), false, syncer::AUTOFILL); 959 EXPECT_TRUE(create_root.success()); 960 std::vector<AutofillEntry> sync_entries; 961 std::vector<AutofillProfile> sync_profiles; 962 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries, &sync_profiles)); 963 EXPECT_EQ(0U, sync_entries.size()); 964 EXPECT_EQ(0U, sync_profiles.size()); 965 } 966 967 TEST_F(ProfileSyncServiceAutofillTest, HasNativeEntriesEmptySync) { 968 std::vector<AutofillEntry> entries; 969 entries.push_back(MakeAutofillEntry("foo", "bar", 1)); 970 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)). 971 WillOnce(DoAll(SetArgumentPointee<0>(entries), Return(true))); 972 SetIdleChangeProcessorExpectations(); 973 CreateRootHelper create_root(this, syncer::AUTOFILL); 974 EXPECT_CALL(*personal_data_manager_, Refresh()); 975 StartSyncService(create_root.callback(), false, syncer::AUTOFILL); 976 ASSERT_TRUE(create_root.success()); 977 std::vector<AutofillEntry> sync_entries; 978 std::vector<AutofillProfile> sync_profiles; 979 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries, &sync_profiles)); 980 ASSERT_EQ(1U, entries.size()); 981 EXPECT_TRUE(entries[0] == sync_entries[0]); 982 EXPECT_EQ(0U, sync_profiles.size()); 983 } 984 985 TEST_F(ProfileSyncServiceAutofillTest, HasProfileEmptySync) { 986 std::vector<AutofillProfile*> profiles; 987 std::vector<AutofillProfile> expected_profiles; 988 // Owned by GetAutofillProfiles caller. 989 AutofillProfile* profile0 = new AutofillProfile; 990 autofill::test::SetProfileInfoWithGuid(profile0, 991 "54B3F9AA-335E-4F71-A27D-719C41564230", "Billing", 992 "Mitchell", "Morrison", 993 "johnwayne (at) me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA", 994 "91601", "US", "12345678910"); 995 profiles.push_back(profile0); 996 expected_profiles.push_back(*profile0); 997 EXPECT_CALL(autofill_table_, GetAutofillProfiles(_)). 998 WillOnce(DoAll(SetArgumentPointee<0>(profiles), Return(true))); 999 EXPECT_CALL(*personal_data_manager_, Refresh()); 1000 SetIdleChangeProcessorExpectations(); 1001 CreateRootHelper create_root(this, syncer::AUTOFILL_PROFILE); 1002 StartSyncService(create_root.callback(), false, syncer::AUTOFILL_PROFILE); 1003 ASSERT_TRUE(create_root.success()); 1004 std::vector<AutofillProfile> sync_profiles; 1005 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode(&sync_profiles)); 1006 EXPECT_EQ(1U, sync_profiles.size()); 1007 EXPECT_EQ(0, expected_profiles[0].Compare(sync_profiles[0])); 1008 } 1009 1010 TEST_F(ProfileSyncServiceAutofillTest, HasNativeWithDuplicatesEmptySync) { 1011 // There is buggy autofill code that allows duplicate name/value 1012 // pairs to exist in the database with separate pair_ids. 1013 std::vector<AutofillEntry> entries; 1014 entries.push_back(MakeAutofillEntry("foo", "bar", 1)); 1015 entries.push_back(MakeAutofillEntry("dup", "", 2)); 1016 entries.push_back(MakeAutofillEntry("dup", "", 3)); 1017 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)). 1018 WillOnce(DoAll(SetArgumentPointee<0>(entries), Return(true))); 1019 SetIdleChangeProcessorExpectations(); 1020 CreateRootHelper create_root(this, syncer::AUTOFILL); 1021 EXPECT_CALL(*personal_data_manager_, Refresh()); 1022 StartSyncService(create_root.callback(), false, syncer::AUTOFILL); 1023 ASSERT_TRUE(create_root.success()); 1024 std::vector<AutofillEntry> sync_entries; 1025 std::vector<AutofillProfile> sync_profiles; 1026 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries, &sync_profiles)); 1027 EXPECT_EQ(2U, sync_entries.size()); 1028 } 1029 1030 TEST_F(ProfileSyncServiceAutofillTest, HasNativeHasSyncNoMerge) { 1031 AutofillEntry native_entry(MakeAutofillEntry("native", "entry", 1)); 1032 AutofillEntry sync_entry(MakeAutofillEntry("sync", "entry", 2)); 1033 1034 std::vector<AutofillEntry> native_entries; 1035 native_entries.push_back(native_entry); 1036 1037 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)). 1038 WillOnce(DoAll(SetArgumentPointee<0>(native_entries), Return(true))); 1039 1040 std::vector<AutofillEntry> sync_entries; 1041 sync_entries.push_back(sync_entry); 1042 1043 AddAutofillHelper<AutofillEntry> add_autofill(this, sync_entries); 1044 1045 EXPECT_CALL(autofill_table_, UpdateAutofillEntries(ElementsAre(sync_entry))). 1046 WillOnce(Return(true)); 1047 1048 EXPECT_CALL(*personal_data_manager_, Refresh()); 1049 StartSyncService(add_autofill.callback(), false, syncer::AUTOFILL); 1050 ASSERT_TRUE(add_autofill.success()); 1051 1052 std::set<AutofillEntry> expected_entries; 1053 expected_entries.insert(native_entry); 1054 expected_entries.insert(sync_entry); 1055 1056 std::vector<AutofillEntry> new_sync_entries; 1057 std::vector<AutofillProfile> new_sync_profiles; 1058 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries, 1059 &new_sync_profiles)); 1060 std::set<AutofillEntry> new_sync_entries_set(new_sync_entries.begin(), 1061 new_sync_entries.end()); 1062 1063 EXPECT_TRUE(expected_entries == new_sync_entries_set); 1064 } 1065 1066 TEST_F(ProfileSyncServiceAutofillTest, HasNativeHasSyncMergeEntry) { 1067 AutofillEntry native_entry(MakeAutofillEntry("merge", "entry", 1)); 1068 AutofillEntry sync_entry(MakeAutofillEntry("merge", "entry", 2)); 1069 AutofillEntry merged_entry(MakeAutofillEntry("merge", "entry", 1, 2)); 1070 1071 std::vector<AutofillEntry> native_entries; 1072 native_entries.push_back(native_entry); 1073 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)). 1074 WillOnce(DoAll(SetArgumentPointee<0>(native_entries), Return(true))); 1075 1076 std::vector<AutofillEntry> sync_entries; 1077 sync_entries.push_back(sync_entry); 1078 AddAutofillHelper<AutofillEntry> add_autofill(this, sync_entries); 1079 1080 EXPECT_CALL(autofill_table_, 1081 UpdateAutofillEntries(ElementsAre(merged_entry))).WillOnce(Return(true)); 1082 EXPECT_CALL(*personal_data_manager_, Refresh()); 1083 StartSyncService(add_autofill.callback(), false, syncer::AUTOFILL); 1084 ASSERT_TRUE(add_autofill.success()); 1085 1086 std::vector<AutofillEntry> new_sync_entries; 1087 std::vector<AutofillProfile> new_sync_profiles; 1088 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries, 1089 &new_sync_profiles)); 1090 ASSERT_EQ(1U, new_sync_entries.size()); 1091 EXPECT_TRUE(merged_entry == new_sync_entries[0]); 1092 } 1093 1094 TEST_F(ProfileSyncServiceAutofillTest, HasNativeHasSyncMergeProfile) { 1095 AutofillProfile sync_profile; 1096 autofill::test::SetProfileInfoWithGuid(&sync_profile, 1097 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing", 1098 "Mitchell", "Morrison", 1099 "johnwayne (at) me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA", 1100 "91601", "US", "12345678910"); 1101 1102 AutofillProfile* native_profile = new AutofillProfile; 1103 autofill::test::SetProfileInfoWithGuid(native_profile, 1104 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing", "Alicia", "Saenz", 1105 "joewayne (at) me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL", 1106 "32801", "US", "19482937549"); 1107 1108 std::vector<AutofillProfile*> native_profiles; 1109 native_profiles.push_back(native_profile); 1110 EXPECT_CALL(autofill_table_, GetAutofillProfiles(_)). 1111 WillOnce(DoAll(SetArgumentPointee<0>(native_profiles), Return(true))); 1112 1113 std::vector<AutofillProfile> sync_profiles; 1114 sync_profiles.push_back(sync_profile); 1115 AddAutofillHelper<AutofillProfile> add_autofill(this, sync_profiles); 1116 1117 EXPECT_CALL(autofill_table_, 1118 UpdateAutofillProfile(MatchProfiles(sync_profile))). 1119 WillOnce(Return(true)); 1120 EXPECT_CALL(*personal_data_manager_, Refresh()); 1121 StartSyncService(add_autofill.callback(), false, syncer::AUTOFILL_PROFILE); 1122 ASSERT_TRUE(add_autofill.success()); 1123 1124 std::vector<AutofillProfile> new_sync_profiles; 1125 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode( 1126 &new_sync_profiles)); 1127 ASSERT_EQ(1U, new_sync_profiles.size()); 1128 EXPECT_EQ(0, sync_profile.Compare(new_sync_profiles[0])); 1129 } 1130 1131 TEST_F(ProfileSyncServiceAutofillTest, HasNativeHasSyncMergeProfileCombine) { 1132 AutofillProfile sync_profile; 1133 autofill::test::SetProfileInfoWithGuid(&sync_profile, 1134 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing", 1135 "Mitchell", "Morrison", 1136 "johnwayne (at) me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA", 1137 "91601", "US", "12345678910"); 1138 1139 AutofillProfile* native_profile = new AutofillProfile; 1140 // Same address, but different names, phones and e-mails. 1141 autofill::test::SetProfileInfoWithGuid(native_profile, 1142 "23355099-1170-4B71-8ED4-144470CC9EBF", "Billing", "Alicia", "Saenz", 1143 "joewayne (at) me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA", 1144 "91601", "US", "19482937549"); 1145 1146 AutofillProfile expected_profile(sync_profile); 1147 expected_profile.OverwriteWithOrAddTo(*native_profile, "en-US"); 1148 1149 std::vector<AutofillProfile*> native_profiles; 1150 native_profiles.push_back(native_profile); 1151 EXPECT_CALL(autofill_table_, GetAutofillProfiles(_)). 1152 WillOnce(DoAll(SetArgumentPointee<0>(native_profiles), Return(true))); 1153 EXPECT_CALL(autofill_table_, 1154 AddAutofillProfile(MatchProfiles(expected_profile))). 1155 WillOnce(Return(true)); 1156 EXPECT_CALL(autofill_table_, 1157 RemoveAutofillProfile("23355099-1170-4B71-8ED4-144470CC9EBF")). 1158 WillOnce(Return(true)); 1159 std::vector<AutofillProfile> sync_profiles; 1160 sync_profiles.push_back(sync_profile); 1161 AddAutofillHelper<AutofillProfile> add_autofill(this, sync_profiles); 1162 1163 EXPECT_CALL(*personal_data_manager_, Refresh()); 1164 StartSyncService(add_autofill.callback(), false, syncer::AUTOFILL_PROFILE); 1165 ASSERT_TRUE(add_autofill.success()); 1166 1167 std::vector<AutofillProfile> new_sync_profiles; 1168 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode( 1169 &new_sync_profiles)); 1170 ASSERT_EQ(1U, new_sync_profiles.size()); 1171 // Check that key fields are the same. 1172 EXPECT_TRUE(new_sync_profiles[0].IsSubsetOf(sync_profile, "en-US")); 1173 // Check that multivalued fields of the synced back data include original 1174 // data. 1175 EXPECT_TRUE( 1176 IncludesField(new_sync_profiles[0], sync_profile, autofill::NAME_FULL)); 1177 EXPECT_TRUE(IncludesField( 1178 new_sync_profiles[0], sync_profile, autofill::EMAIL_ADDRESS)); 1179 EXPECT_TRUE(IncludesField( 1180 new_sync_profiles[0], sync_profile, autofill::PHONE_HOME_WHOLE_NUMBER)); 1181 } 1182 1183 TEST_F(ProfileSyncServiceAutofillTest, MergeProfileWithDifferentGuid) { 1184 AutofillProfile sync_profile; 1185 1186 autofill::test::SetProfileInfoWithGuid(&sync_profile, 1187 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing", 1188 "Mitchell", "Morrison", 1189 "johnwayne (at) me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA", 1190 "91601", "US", "12345678910"); 1191 1192 std::string native_guid = "EDC609ED-7EEE-4F27-B00C-423242A9C44B"; 1193 AutofillProfile* native_profile = new AutofillProfile; 1194 autofill::test::SetProfileInfoWithGuid(native_profile, 1195 native_guid.c_str(), "Billing", 1196 "Mitchell", "Morrison", 1197 "johnwayne (at) me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA", 1198 "91601", "US", "12345678910"); 1199 1200 std::vector<AutofillProfile*> native_profiles; 1201 native_profiles.push_back(native_profile); 1202 EXPECT_CALL(autofill_table_, GetAutofillProfiles(_)). 1203 WillOnce(DoAll(SetArgumentPointee<0>(native_profiles), Return(true))); 1204 1205 std::vector<AutofillProfile> sync_profiles; 1206 sync_profiles.push_back(sync_profile); 1207 AddAutofillHelper<AutofillProfile> add_autofill(this, sync_profiles); 1208 1209 EXPECT_CALL(autofill_table_, AddAutofillProfile(_)). 1210 WillOnce(Return(true)); 1211 EXPECT_CALL(autofill_table_, RemoveAutofillProfile(native_guid)). 1212 WillOnce(Return(true)); 1213 EXPECT_CALL(*personal_data_manager_, Refresh()); 1214 StartSyncService(add_autofill.callback(), false, syncer::AUTOFILL_PROFILE); 1215 ASSERT_TRUE(add_autofill.success()); 1216 1217 std::vector<AutofillProfile> new_sync_profiles; 1218 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode( 1219 &new_sync_profiles)); 1220 ASSERT_EQ(1U, new_sync_profiles.size()); 1221 EXPECT_EQ(0, sync_profile.Compare(new_sync_profiles[0])); 1222 EXPECT_EQ(sync_profile.guid(), new_sync_profiles[0].guid()); 1223 } 1224 1225 TEST_F(ProfileSyncServiceAutofillTest, ProcessUserChangeAddEntry) { 1226 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)).WillOnce(Return(true)); 1227 EXPECT_CALL(*personal_data_manager_, Refresh()); 1228 SetIdleChangeProcessorExpectations(); 1229 CreateRootHelper create_root(this, syncer::AUTOFILL); 1230 StartSyncService(create_root.callback(), false, syncer::AUTOFILL); 1231 ASSERT_TRUE(create_root.success()); 1232 1233 AutofillEntry added_entry(MakeAutofillEntry("added", "entry", 1)); 1234 std::vector<base::Time> timestamps(added_entry.timestamps()); 1235 1236 EXPECT_CALL(autofill_table_, GetAutofillTimestamps(_, _, _)). 1237 WillOnce(DoAll(SetArgumentPointee<2>(timestamps), Return(true))); 1238 1239 AutofillChangeList changes; 1240 changes.push_back(AutofillChange(AutofillChange::ADD, added_entry.key())); 1241 1242 web_data_service_->OnAutofillEntriesChanged(changes); 1243 1244 std::vector<AutofillEntry> new_sync_entries; 1245 std::vector<AutofillProfile> new_sync_profiles; 1246 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries, 1247 &new_sync_profiles)); 1248 ASSERT_EQ(1U, new_sync_entries.size()); 1249 EXPECT_TRUE(added_entry == new_sync_entries[0]); 1250 } 1251 1252 TEST_F(ProfileSyncServiceAutofillTest, ProcessUserChangeAddProfile) { 1253 EXPECT_CALL(autofill_table_, GetAutofillProfiles(_)).WillOnce(Return(true)); 1254 EXPECT_CALL(*personal_data_manager_, Refresh()); 1255 SetIdleChangeProcessorExpectations(); 1256 CreateRootHelper create_root(this, syncer::AUTOFILL_PROFILE); 1257 StartSyncService(create_root.callback(), false, syncer::AUTOFILL_PROFILE); 1258 ASSERT_TRUE(create_root.success()); 1259 1260 AutofillProfile added_profile; 1261 autofill::test::SetProfileInfoWithGuid(&added_profile, 1262 "D6ADA912-D374-4C0A-917D-F5C8EBE43011", "Josephine", "Alicia", "Saenz", 1263 "joewayne (at) me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL", 1264 "32801", "US", "19482937549"); 1265 1266 AutofillProfileChange change( 1267 AutofillProfileChange::ADD, added_profile.guid(), &added_profile); 1268 web_data_service_->OnAutofillProfileChanged(change); 1269 1270 std::vector<AutofillProfile> new_sync_profiles; 1271 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode( 1272 &new_sync_profiles)); 1273 ASSERT_EQ(1U, new_sync_profiles.size()); 1274 EXPECT_EQ(0, added_profile.Compare(new_sync_profiles[0])); 1275 } 1276 1277 TEST_F(ProfileSyncServiceAutofillTest, ProcessUserChangeUpdateEntry) { 1278 AutofillEntry original_entry(MakeAutofillEntry("my", "entry", 1)); 1279 std::vector<AutofillEntry> original_entries; 1280 original_entries.push_back(original_entry); 1281 1282 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)). 1283 WillOnce(DoAll(SetArgumentPointee<0>(original_entries), Return(true))); 1284 EXPECT_CALL(*personal_data_manager_, Refresh()); 1285 CreateRootHelper create_root(this, syncer::AUTOFILL); 1286 StartSyncService(create_root.callback(), false, syncer::AUTOFILL); 1287 ASSERT_TRUE(create_root.success()); 1288 1289 AutofillEntry updated_entry(MakeAutofillEntry("my", "entry", 1, 2)); 1290 std::vector<base::Time> timestamps(updated_entry.timestamps()); 1291 1292 EXPECT_CALL(autofill_table_, GetAutofillTimestamps(_, _, _)). 1293 WillOnce(DoAll(SetArgumentPointee<2>(timestamps), Return(true))); 1294 1295 AutofillChangeList changes; 1296 changes.push_back(AutofillChange(AutofillChange::UPDATE, 1297 updated_entry.key())); 1298 web_data_service_->OnAutofillEntriesChanged(changes); 1299 1300 std::vector<AutofillEntry> new_sync_entries; 1301 std::vector<AutofillProfile> new_sync_profiles; 1302 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries, 1303 &new_sync_profiles)); 1304 ASSERT_EQ(1U, new_sync_entries.size()); 1305 EXPECT_TRUE(updated_entry == new_sync_entries[0]); 1306 } 1307 1308 1309 TEST_F(ProfileSyncServiceAutofillTest, ProcessUserChangeRemoveEntry) { 1310 AutofillEntry original_entry(MakeAutofillEntry("my", "entry", 1)); 1311 std::vector<AutofillEntry> original_entries; 1312 original_entries.push_back(original_entry); 1313 1314 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)). 1315 WillOnce(DoAll(SetArgumentPointee<0>(original_entries), Return(true))); 1316 EXPECT_CALL(*personal_data_manager_, Refresh()); 1317 CreateRootHelper create_root(this, syncer::AUTOFILL); 1318 StartSyncService(create_root.callback(), false, syncer::AUTOFILL); 1319 ASSERT_TRUE(create_root.success()); 1320 1321 AutofillChangeList changes; 1322 changes.push_back(AutofillChange(AutofillChange::REMOVE, 1323 original_entry.key())); 1324 web_data_service_->OnAutofillEntriesChanged(changes); 1325 1326 std::vector<AutofillEntry> new_sync_entries; 1327 std::vector<AutofillProfile> new_sync_profiles; 1328 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries, 1329 &new_sync_profiles)); 1330 ASSERT_EQ(0U, new_sync_entries.size()); 1331 } 1332 1333 TEST_F(ProfileSyncServiceAutofillTest, ProcessUserChangeRemoveProfile) { 1334 AutofillProfile sync_profile; 1335 autofill::test::SetProfileInfoWithGuid(&sync_profile, 1336 "3BA5FA1B-1EC4-4BB3-9B57-EC92BE3C1A09", "Josephine", "Alicia", "Saenz", 1337 "joewayne (at) me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL", 1338 "32801", "US", "19482937549"); 1339 AutofillProfile* native_profile = new AutofillProfile; 1340 autofill::test::SetProfileInfoWithGuid(native_profile, 1341 "3BA5FA1B-1EC4-4BB3-9B57-EC92BE3C1A09", "Josephine", "Alicia", "Saenz", 1342 "joewayne (at) me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL", 1343 "32801", "US", "19482937549"); 1344 1345 std::vector<AutofillProfile*> native_profiles; 1346 native_profiles.push_back(native_profile); 1347 EXPECT_CALL(autofill_table_, GetAutofillProfiles(_)). 1348 WillOnce(DoAll(SetArgumentPointee<0>(native_profiles), Return(true))); 1349 1350 std::vector<AutofillProfile> sync_profiles; 1351 sync_profiles.push_back(sync_profile); 1352 AddAutofillHelper<AutofillProfile> add_autofill(this, sync_profiles); 1353 EXPECT_CALL(*personal_data_manager_, Refresh()); 1354 StartSyncService(add_autofill.callback(), false, syncer::AUTOFILL_PROFILE); 1355 ASSERT_TRUE(add_autofill.success()); 1356 1357 AutofillProfileChange change( 1358 AutofillProfileChange::REMOVE, sync_profile.guid(), NULL); 1359 web_data_service_->OnAutofillProfileChanged(change); 1360 1361 std::vector<AutofillProfile> new_sync_profiles; 1362 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode( 1363 &new_sync_profiles)); 1364 ASSERT_EQ(0U, new_sync_profiles.size()); 1365 } 1366 1367 // http://crbug.com/57884 1368 TEST_F(ProfileSyncServiceAutofillTest, DISABLED_ServerChangeRace) { 1369 // Once for MergeDataAndStartSyncing() and twice for ProcessSyncChanges(), via 1370 // LoadAutofillData(). 1371 EXPECT_CALL(autofill_table_, GetAllAutofillEntries(_)). 1372 Times(3).WillRepeatedly(Return(true)); 1373 // On the other hand Autofill and Autocomplete are separated now, so 1374 // GetAutofillProfiles() should not be called. 1375 EXPECT_CALL(autofill_table_, GetAutofillProfiles(_)).Times(0); 1376 EXPECT_CALL(autofill_table_, UpdateAutofillEntries(_)). 1377 WillRepeatedly(Return(true)); 1378 EXPECT_CALL(*personal_data_manager_, Refresh()).Times(3); 1379 CreateRootHelper create_root(this, syncer::AUTOFILL); 1380 StartSyncService(create_root.callback(), false, syncer::AUTOFILL); 1381 ASSERT_TRUE(create_root.success()); 1382 1383 // (true, false) means we have to reset after |Signal|, init to unsignaled. 1384 scoped_ptr<WaitableEvent> wait_for_start(new WaitableEvent(true, false)); 1385 scoped_ptr<WaitableEvent> wait_for_syncapi(new WaitableEvent(true, false)); 1386 scoped_refptr<FakeServerUpdater> updater(new FakeServerUpdater( 1387 sync_service_, &wait_for_start, &wait_for_syncapi)); 1388 1389 // This server side update will stall waiting for CommitWaiter. 1390 updater->CreateNewEntry(MakeAutofillEntry("server", "entry", 1)); 1391 wait_for_start->Wait(); 1392 1393 AutofillEntry syncapi_entry(MakeAutofillEntry("syncapi", "entry", 2)); 1394 ASSERT_TRUE(AddAutofillSyncNode(syncapi_entry)); 1395 DVLOG(1) << "Syncapi update finished."; 1396 1397 // If we reach here, it means syncapi succeeded and we didn't deadlock. Yay! 1398 // Signal FakeServerUpdater that it can complete. 1399 wait_for_syncapi->Signal(); 1400 1401 // Make another entry to ensure nothing broke afterwards and wait for finish 1402 // to clean up. 1403 updater->CreateNewEntryAndWait(MakeAutofillEntry("server2", "entry2", 3)); 1404 1405 std::vector<AutofillEntry> sync_entries; 1406 std::vector<AutofillProfile> sync_profiles; 1407 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries, &sync_profiles)); 1408 EXPECT_EQ(3U, sync_entries.size()); 1409 EXPECT_EQ(0U, sync_profiles.size()); 1410 for (size_t i = 0; i < sync_entries.size(); i++) { 1411 DVLOG(1) << "Entry " << i << ": " << sync_entries[i].key().name() 1412 << ", " << sync_entries[i].key().value(); 1413 } 1414 } 1415