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.
9 #include "testing/gtest/include/gtest/gtest.h"
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/profile_oauth2_token_service_factory.h"
25 #include "chrome/browser/signin/signin_manager.h"
26 #include "chrome/browser/signin/signin_manager_factory.h"
27 #include "chrome/browser/sync/abstract_profile_sync_service_test.h"
28 #include "chrome/browser/sync/fake_oauth2_token_service_for_sync.h"
29 #include "chrome/browser/sync/glue/autofill_data_type_controller.h"
30 #include "chrome/browser/sync/glue/autofill_profile_data_type_controller.h"
31 #include "chrome/browser/sync/glue/data_type_controller.h"
32 #include "chrome/browser/sync/glue/generic_change_processor.h"
33 #include "chrome/browser/sync/glue/shared_change_processor.h"
34 #include "chrome/browser/sync/profile_sync_components_factory.h"
35 #include "chrome/browser/sync/profile_sync_service.h"
36 #include "chrome/browser/sync/profile_sync_service_factory.h"
37 #include "chrome/browser/sync/profile_sync_test_util.h"
38 #include "chrome/browser/sync/test_profile_sync_service.h"
39 #include "chrome/browser/webdata/autocomplete_syncable_service.h"
40 #include "chrome/browser/webdata/web_data_service_factory.h"
41 #include "chrome/test/base/testing_profile.h"
42 #include "components/autofill/core/browser/autofill_test_utils.h"
43 #include "components/autofill/core/browser/personal_data_manager.h"
44 #include "components/autofill/core/browser/webdata/autofill_change.h"
45 #include "components/autofill/core/browser/webdata/autofill_entry.h"
46 #include "components/autofill/core/browser/webdata/autofill_profile_syncable_service.h"
47 #include "components/autofill/core/browser/webdata/autofill_table.h"
48 #include "components/autofill/core/browser/webdata/autofill_webdata_service.h"
49 #include "components/webdata/common/web_data_service_test_util.h"
50 #include "components/webdata/common/web_database.h"
51 #include "content/public/test/test_browser_thread.h"
52 #include "google_apis/gaia/gaia_constants.h"
53 #include "sync/internal_api/public/base/model_type.h"
54 #include "sync/internal_api/public/data_type_debug_info_listener.h"
55 #include "sync/internal_api/public/read_node.h"
56 #include "sync/internal_api/public/read_transaction.h"
57 #include "sync/internal_api/public/write_node.h"
58 #include "sync/internal_api/public/write_transaction.h"
59 #include "sync/protocol/autofill_specifics.pb.h"
60 #include "sync/syncable/mutable_entry.h"
61 #include "sync/syncable/syncable_write_transaction.h"
62 #include "sync/test/engine/test_id_factory.h"
63 #include "testing/gmock/include/gmock/gmock.h"
65 using autofill::AutofillChange
;
66 using autofill::AutofillChangeList
;
67 using autofill::AutofillEntry
;
68 using autofill::ServerFieldType
;
69 using autofill::AutofillKey
;
70 using autofill::AutofillProfile
;
71 using autofill::AutofillProfileChange
;
72 using autofill::AutofillProfileSyncableService
;
73 using autofill::AutofillTable
;
74 using autofill::AutofillWebDataService
;
75 using autofill::PersonalDataManager
;
77 using base::TimeDelta
;
78 using base::WaitableEvent
;
79 using browser_sync::AutofillDataTypeController
;
80 using browser_sync::AutofillProfileDataTypeController
;
81 using browser_sync::DataTypeController
;
82 using browser_sync::GenericChangeProcessor
;
83 using browser_sync::SharedChangeProcessor
;
84 using content::BrowserThread
;
85 using syncer::AUTOFILL
;
86 using syncer::BaseNode
;
87 using syncer::syncable::BASE_VERSION
;
88 using syncer::syncable::CREATE
;
89 using syncer::syncable::GET_BY_SERVER_TAG
;
90 using syncer::syncable::MutableEntry
;
91 using syncer::syncable::SERVER_SPECIFICS
;
92 using syncer::syncable::SPECIFICS
;
93 using syncer::syncable::UNITTEST
;
94 using syncer::syncable::WriterTag
;
95 using syncer::syncable::WriteTransaction
;
98 using testing::ElementsAre
;
99 using testing::SetArgumentPointee
;
100 using testing::Return
;
102 class HistoryService
;
110 void RunAndSignal(const base::Closure
& cb
, WaitableEvent
* event
) {
117 class AutofillTableMock
: public AutofillTable
{
119 AutofillTableMock() : AutofillTable("en-US") {}
120 MOCK_METHOD2(RemoveFormElement
,
121 bool(const base::string16
& name
,
122 const base::string16
& value
)); // NOLINT
123 MOCK_METHOD1(GetAllAutofillEntries
,
124 bool(std::vector
<AutofillEntry
>* entries
)); // NOLINT
125 MOCK_METHOD3(GetAutofillTimestamps
,
126 bool(const base::string16
& name
, // NOLINT
127 const base::string16
& value
,
128 std::vector
<base::Time
>* timestamps
));
129 MOCK_METHOD1(UpdateAutofillEntries
,
130 bool(const std::vector
<AutofillEntry
>&)); // NOLINT
131 MOCK_METHOD1(GetAutofillProfiles
,
132 bool(std::vector
<AutofillProfile
*>*)); // NOLINT
133 MOCK_METHOD1(UpdateAutofillProfile
,
134 bool(const AutofillProfile
&)); // NOLINT
135 MOCK_METHOD1(AddAutofillProfile
,
136 bool(const AutofillProfile
&)); // NOLINT
137 MOCK_METHOD1(RemoveAutofillProfile
,
138 bool(const std::string
&)); // NOLINT
141 MATCHER_P(MatchProfiles
, profile
, "") {
142 return (profile
.Compare(arg
) == 0);
145 class WebDatabaseFake
: public WebDatabase
{
147 explicit WebDatabaseFake(AutofillTable
* autofill_table
) {
148 AddTable(autofill_table
);
152 class MockAutofillBackend
: public autofill::AutofillWebDataBackend
{
155 WebDatabase
* web_database
,
156 const base::Closure
& on_changed
)
157 : web_database_(web_database
),
158 on_changed_(on_changed
) {
161 virtual ~MockAutofillBackend() {}
162 virtual WebDatabase
* GetDatabase() OVERRIDE
{ return web_database_
; }
163 virtual void AddObserver(
164 autofill::AutofillWebDataServiceObserverOnDBThread
* observer
) OVERRIDE
{}
165 virtual void RemoveObserver(
166 autofill::AutofillWebDataServiceObserverOnDBThread
* observer
) OVERRIDE
{}
167 virtual void RemoveExpiredFormElements() OVERRIDE
{}
168 virtual void NotifyOfMultipleAutofillChanges() OVERRIDE
{
169 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB
));
170 BrowserThread::PostTask(BrowserThread::UI
, FROM_HERE
, on_changed_
);
174 WebDatabase
* web_database_
;
175 base::Closure on_changed_
;
178 class ProfileSyncServiceAutofillTest
;
180 template<class AutofillProfile
>
181 syncer::ModelType
GetModelType() {
182 return syncer::UNSPECIFIED
;
186 syncer::ModelType GetModelType
<AutofillEntry
>() {
187 return syncer::AUTOFILL
;
191 syncer::ModelType GetModelType
<AutofillProfile
>() {
192 return syncer::AUTOFILL_PROFILE
;
195 class TokenWebDataServiceFake
: public TokenWebData
{
197 TokenWebDataServiceFake()
199 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::UI
),
200 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::DB
)) {
203 virtual bool IsDatabaseLoaded() OVERRIDE
{
207 virtual WebDataService::Handle
GetAllTokens(
208 WebDataServiceConsumer
* consumer
) OVERRIDE
{
209 // TODO(tim): It would be nice if WebDataService was injected on
210 // construction of ProfileOAuth2TokenService rather than fetched by
211 // Initialize so that this isn't necessary (we could pass a NULL service).
212 // We currently do return it via EXPECT_CALLs, but without depending on
213 // order-of-initialization (which seems way more fragile) we can't tell
214 // which component is asking at what time, and some components in these
215 // Autofill tests require a WebDataService.
220 virtual ~TokenWebDataServiceFake() {}
222 DISALLOW_COPY_AND_ASSIGN(TokenWebDataServiceFake
);
225 class WebDataServiceFake
: public AutofillWebDataService
{
228 : AutofillWebDataService(
229 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::UI
),
230 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::DB
)),
232 autocomplete_syncable_service_(NULL
),
233 autofill_profile_syncable_service_(NULL
),
234 syncable_service_created_or_destroyed_(false, false) {
237 void SetDatabase(WebDatabase
* web_database
) {
238 web_database_
= web_database
;
241 void StartSyncableService() {
242 // The |autofill_profile_syncable_service_| must be constructed on the DB
244 const base::Closure
& on_changed_callback
= base::Bind(
245 &WebDataServiceFake::NotifyAutofillMultipleChangedOnUIThread
,
248 BrowserThread::PostTask(BrowserThread::DB
, FROM_HERE
,
249 base::Bind(&WebDataServiceFake::CreateSyncableService
,
250 base::Unretained(this),
251 on_changed_callback
));
252 syncable_service_created_or_destroyed_
.Wait();
255 void ShutdownSyncableService() {
256 // The |autofill_profile_syncable_service_| must be destructed on the DB
258 BrowserThread::PostTask(BrowserThread::DB
, FROM_HERE
,
259 base::Bind(&WebDataServiceFake::DestroySyncableService
,
260 base::Unretained(this)));
261 syncable_service_created_or_destroyed_
.Wait();
264 virtual bool IsDatabaseLoaded() OVERRIDE
{
268 virtual WebDatabase
* GetDatabase() OVERRIDE
{
269 return web_database_
;
272 void OnAutofillEntriesChanged(const AutofillChangeList
& changes
) {
273 WaitableEvent
event(true, false);
275 base::Closure notify_cb
=
276 base::Bind(&AutocompleteSyncableService::AutofillEntriesChanged
,
277 base::Unretained(autocomplete_syncable_service_
),
279 BrowserThread::PostTask(
282 base::Bind(&RunAndSignal
, notify_cb
, &event
));
286 void OnAutofillProfileChanged(const AutofillProfileChange
& changes
) {
287 WaitableEvent
event(true, false);
289 base::Closure notify_cb
=
290 base::Bind(&AutocompleteSyncableService::AutofillProfileChanged
,
291 base::Unretained(autofill_profile_syncable_service_
),
293 BrowserThread::PostTask(
296 base::Bind(&RunAndSignal
, notify_cb
, &event
));
301 virtual ~WebDataServiceFake() {}
303 void CreateSyncableService(const base::Closure
& on_changed_callback
) {
304 ASSERT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB
));
305 // These services are deleted in DestroySyncableService().
306 backend_
.reset(new MockAutofillBackend(
307 GetDatabase(), on_changed_callback
));
308 AutocompleteSyncableService::CreateForWebDataServiceAndBackend(
309 this, backend_
.get());
310 AutofillProfileSyncableService::CreateForWebDataServiceAndBackend(
311 this, backend_
.get(), "en-US");
313 autocomplete_syncable_service_
=
314 AutocompleteSyncableService::FromWebDataService(this);
315 autofill_profile_syncable_service_
=
316 AutofillProfileSyncableService::FromWebDataService(this);
318 syncable_service_created_or_destroyed_
.Signal();
321 void DestroySyncableService() {
322 ASSERT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB
));
323 autocomplete_syncable_service_
= NULL
;
324 autofill_profile_syncable_service_
= NULL
;
326 syncable_service_created_or_destroyed_
.Signal();
329 WebDatabase
* web_database_
;
330 AutocompleteSyncableService
* autocomplete_syncable_service_
;
331 AutofillProfileSyncableService
* autofill_profile_syncable_service_
;
332 scoped_ptr
<autofill::AutofillWebDataBackend
> backend_
;
334 WaitableEvent syncable_service_created_or_destroyed_
;
336 DISALLOW_COPY_AND_ASSIGN(WebDataServiceFake
);
339 BrowserContextKeyedService
* BuildMockWebDataServiceWrapper(
340 content::BrowserContext
* profile
) {
341 return new MockWebDataServiceWrapper(
343 new WebDataServiceFake(),
344 new TokenWebDataServiceFake());
347 ACTION_P(MakeAutocompleteSyncComponents
, wds
) {
348 EXPECT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB
));
349 if (!BrowserThread::CurrentlyOn(BrowserThread::DB
))
350 return base::WeakPtr
<syncer::SyncableService
>();
351 return AutocompleteSyncableService::FromWebDataService(wds
)->AsWeakPtr();
354 ACTION_P(ReturnNewDataTypeManagerWithDebugListener
, debug_listener
) {
355 return new browser_sync::DataTypeManagerImpl(
364 ACTION(MakeGenericChangeProcessor
) {
365 syncer::UserShare
* user_share
= arg0
->GetUserShare();
366 return new GenericChangeProcessor(
373 ACTION(MakeSharedChangeProcessor
) {
374 return new SharedChangeProcessor();
377 ACTION_P(MakeAutofillProfileSyncComponents
, wds
) {
378 EXPECT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB
));
379 if (!BrowserThread::CurrentlyOn(BrowserThread::DB
))
380 return base::WeakPtr
<syncer::SyncableService
>();
381 return AutofillProfileSyncableService::FromWebDataService(wds
)->AsWeakPtr();
384 class AbstractAutofillFactory
{
386 virtual DataTypeController
* CreateDataTypeController(
387 ProfileSyncComponentsFactory
* factory
,
388 TestingProfile
* profile
,
389 ProfileSyncService
* service
) = 0;
390 virtual void SetExpectation(ProfileSyncComponentsFactoryMock
* factory
,
391 ProfileSyncService
* service
,
392 AutofillWebDataService
* wds
,
393 DataTypeController
* dtc
) = 0;
394 virtual ~AbstractAutofillFactory() {}
397 class AutofillEntryFactory
: public AbstractAutofillFactory
{
399 virtual browser_sync::DataTypeController
* CreateDataTypeController(
400 ProfileSyncComponentsFactory
* factory
,
401 TestingProfile
* profile
,
402 ProfileSyncService
* service
) OVERRIDE
{
403 return new AutofillDataTypeController(factory
, profile
, service
);
406 virtual void SetExpectation(ProfileSyncComponentsFactoryMock
* factory
,
407 ProfileSyncService
* service
,
408 AutofillWebDataService
* wds
,
409 DataTypeController
* dtc
) OVERRIDE
{
410 EXPECT_CALL(*factory
, CreateGenericChangeProcessor(_
,_
,_
,_
)).
411 WillOnce(MakeGenericChangeProcessor());
412 EXPECT_CALL(*factory
, CreateSharedChangeProcessor()).
413 WillOnce(MakeSharedChangeProcessor());
414 EXPECT_CALL(*factory
, GetSyncableServiceForType(syncer::AUTOFILL
)).
415 WillOnce(MakeAutocompleteSyncComponents(wds
));
419 class AutofillProfileFactory
: public AbstractAutofillFactory
{
421 virtual browser_sync::DataTypeController
* CreateDataTypeController(
422 ProfileSyncComponentsFactory
* factory
,
423 TestingProfile
* profile
,
424 ProfileSyncService
* service
) OVERRIDE
{
425 return new AutofillProfileDataTypeController(factory
, profile
, service
);
428 virtual void SetExpectation(ProfileSyncComponentsFactoryMock
* factory
,
429 ProfileSyncService
* service
,
430 AutofillWebDataService
* wds
,
431 DataTypeController
* dtc
) OVERRIDE
{
432 EXPECT_CALL(*factory
, CreateGenericChangeProcessor(_
,_
,_
,_
)).
433 WillOnce(MakeGenericChangeProcessor());
434 EXPECT_CALL(*factory
, CreateSharedChangeProcessor()).
435 WillOnce(MakeSharedChangeProcessor());
436 EXPECT_CALL(*factory
,
437 GetSyncableServiceForType(syncer::AUTOFILL_PROFILE
)).
438 WillOnce(MakeAutofillProfileSyncComponents(wds
));
442 class MockPersonalDataManager
: public PersonalDataManager
{
444 MockPersonalDataManager() : PersonalDataManager("en-US") {}
445 MOCK_CONST_METHOD0(IsDataLoaded
, bool());
446 MOCK_METHOD0(LoadProfiles
, void());
447 MOCK_METHOD0(LoadCreditCards
, void());
448 MOCK_METHOD0(Refresh
, void());
451 class MockPersonalDataManagerService
452 : public autofill::PersonalDataManagerService
{
454 static BrowserContextKeyedService
* Build(content::BrowserContext
* profile
) {
455 return new MockPersonalDataManagerService();
458 MockPersonalDataManagerService() {
459 personal_data_manager_
.reset(new MockPersonalDataManager());
461 virtual ~MockPersonalDataManagerService() {}
463 virtual void Shutdown() OVERRIDE
{
464 personal_data_manager_
.reset();
467 virtual MockPersonalDataManager
* GetPersonalDataManager() OVERRIDE
{
468 return personal_data_manager_
.get();
472 scoped_ptr
<MockPersonalDataManager
> personal_data_manager_
;
473 DISALLOW_COPY_AND_ASSIGN(MockPersonalDataManagerService
);
476 template <class T
> class AddAutofillHelper
;
478 class ProfileSyncServiceAutofillTest
479 : public AbstractProfileSyncServiceTest
,
480 public syncer::DataTypeDebugInfoListener
{
482 // DataTypeDebugInfoListener implementation.
483 virtual void OnDataTypeConfigureComplete(
484 const std::vector
<syncer::DataTypeConfigurationStats
>&
485 configuration_stats
) OVERRIDE
{
486 ASSERT_EQ(1u, configuration_stats
.size());
487 association_stats_
= configuration_stats
[0].association_stats
;
491 ProfileSyncServiceAutofillTest()
492 : debug_ptr_factory_(this) {
494 virtual ~ProfileSyncServiceAutofillTest() {
497 AutofillProfileFactory profile_factory_
;
498 AutofillEntryFactory entry_factory_
;
500 AbstractAutofillFactory
* GetFactory(syncer::ModelType type
) {
501 if (type
== syncer::AUTOFILL
) {
502 return &entry_factory_
;
503 } else if (type
== syncer::AUTOFILL_PROFILE
) {
504 return &profile_factory_
;
511 virtual void SetUp() OVERRIDE
{
512 AbstractProfileSyncServiceTest::SetUp();
513 TestingProfile::Builder builder
;
514 builder
.AddTestingFactory(ProfileOAuth2TokenServiceFactory::GetInstance(),
515 FakeOAuth2TokenServiceForSync::BuildTokenService
);
516 profile_
= builder
.Build().Pass();
517 web_database_
.reset(new WebDatabaseFake(&autofill_table_
));
518 MockWebDataServiceWrapper
* wrapper
=
519 static_cast<MockWebDataServiceWrapper
*>(
520 WebDataServiceFactory::GetInstance()->SetTestingFactoryAndUse(
521 profile_
.get(), BuildMockWebDataServiceWrapper
));
523 static_cast<WebDataServiceFake
*>(wrapper
->GetAutofillWebData().get());
524 web_data_service_
->SetDatabase(web_database_
.get());
526 MockPersonalDataManagerService
* personal_data_manager_service
=
527 static_cast<MockPersonalDataManagerService
*>(
528 autofill::PersonalDataManagerFactory::GetInstance()
529 ->SetTestingFactoryAndUse(
530 profile_
.get(), MockPersonalDataManagerService::Build
));
531 personal_data_manager_
=
532 personal_data_manager_service
->GetPersonalDataManager();
534 EXPECT_CALL(*personal_data_manager_
, LoadProfiles()).Times(1);
535 EXPECT_CALL(*personal_data_manager_
, LoadCreditCards()).Times(1);
537 personal_data_manager_
->Init(
538 WebDataServiceFactory::GetAutofillWebDataForProfile(
539 profile_
.get(), Profile::EXPLICIT_ACCESS
),
540 profile_
->GetPrefs(),
541 profile_
->IsOffTheRecord());
543 web_data_service_
->StartSyncableService();
546 virtual void TearDown() OVERRIDE
{
547 // Note: The tear down order is important.
548 ProfileSyncServiceFactory::GetInstance()->SetTestingFactory(
549 profile_
.get(), NULL
);
550 web_data_service_
->ShutdownOnUIThread();
551 web_data_service_
->ShutdownSyncableService();
552 web_data_service_
= NULL
;
553 // To prevent a leak, fully release TestURLRequestContext to ensure its
554 // destruction on the IO message loop.
556 AbstractProfileSyncServiceTest::TearDown();
560 int GetSyncCount(syncer::ModelType type
) {
561 syncer::ReadTransaction
trans(FROM_HERE
, sync_service_
->GetUserShare());
562 syncer::ReadNode
node(&trans
);
563 if (node
.InitByTagLookup(syncer::ModelTypeToRootTag(type
)) !=
564 syncer::BaseNode::INIT_OK
)
566 return node
.GetTotalNodeCount() - 1;
569 void StartSyncService(const base::Closure
& callback
,
570 bool will_fail_association
,
571 syncer::ModelType type
) {
572 AbstractAutofillFactory
* factory
= GetFactory(type
);
573 SigninManagerBase
* signin
=
574 SigninManagerFactory::GetForProfile(profile_
.get());
575 signin
->SetAuthenticatedUsername("test_user@gmail.com");
576 sync_service_
= static_cast<TestProfileSyncService
*>(
577 ProfileSyncServiceFactory::GetInstance()->SetTestingFactoryAndUse(
578 profile_
.get(), &TestProfileSyncService::BuildAutoStartAsyncInit
));
579 sync_service_
->set_backend_init_callback(callback
);
581 ProfileSyncComponentsFactoryMock
* components
=
582 sync_service_
->components_factory_mock();
583 DataTypeController
* data_type_controller
=
584 factory
->CreateDataTypeController(components
,
587 factory
->SetExpectation(components
,
589 web_data_service_
.get(),
590 data_type_controller
);
592 EXPECT_CALL(*components
, CreateDataTypeManager(_
, _
, _
, _
, _
, _
)).
593 WillOnce(ReturnNewDataTypeManagerWithDebugListener(
594 syncer::MakeWeakHandle(debug_ptr_factory_
.GetWeakPtr())));
596 EXPECT_CALL(*personal_data_manager_
, IsDataLoaded()).
597 WillRepeatedly(Return(true));
599 // We need tokens to get the tests going
600 ProfileOAuth2TokenServiceFactory::GetForProfile(profile_
.get())
601 ->UpdateCredentials("test_user@gmail.com", "oauth2_login_token");
603 sync_service_
->RegisterDataTypeController(data_type_controller
);
604 sync_service_
->Initialize();
605 base::MessageLoop::current()->Run();
607 // It's possible this test triggered an unrecoverable error, in which case
608 // we can't get the sync count.
609 if (sync_service_
->ShouldPushChanges()) {
610 EXPECT_EQ(GetSyncCount(type
),
611 association_stats_
.num_sync_items_after_association
);
613 EXPECT_EQ(association_stats_
.num_sync_items_after_association
,
614 association_stats_
.num_sync_items_before_association
+
615 association_stats_
.num_sync_items_added
-
616 association_stats_
.num_sync_items_deleted
);
619 bool AddAutofillSyncNode(const AutofillEntry
& entry
) {
620 syncer::WriteTransaction
trans(FROM_HERE
, sync_service_
->GetUserShare());
621 syncer::ReadNode
autofill_root(&trans
);
622 if (autofill_root
.InitByTagLookup(
623 syncer::ModelTypeToRootTag(syncer::AUTOFILL
)) !=
628 syncer::WriteNode
node(&trans
);
629 std::string tag
= AutocompleteSyncableService::KeyToTag(
630 base::UTF16ToUTF8(entry
.key().name()),
631 base::UTF16ToUTF8(entry
.key().value()));
632 syncer::WriteNode::InitUniqueByCreationResult result
=
633 node
.InitUniqueByCreation(syncer::AUTOFILL
, autofill_root
, tag
);
634 if (result
!= syncer::WriteNode::INIT_SUCCESS
)
637 sync_pb::EntitySpecifics specifics
;
638 AutocompleteSyncableService::WriteAutofillEntry(entry
, &specifics
);
639 sync_pb::AutofillSpecifics
* autofill_specifics
=
640 specifics
.mutable_autofill();
641 node
.SetAutofillSpecifics(*autofill_specifics
);
645 bool AddAutofillSyncNode(const AutofillProfile
& profile
) {
646 syncer::WriteTransaction
trans(FROM_HERE
, sync_service_
->GetUserShare());
647 syncer::ReadNode
autofill_root(&trans
);
648 if (autofill_root
.InitByTagLookup(autofill::kAutofillProfileTag
) !=
652 syncer::WriteNode
node(&trans
);
653 std::string tag
= profile
.guid();
654 syncer::WriteNode::InitUniqueByCreationResult result
=
655 node
.InitUniqueByCreation(syncer::AUTOFILL_PROFILE
,
657 if (result
!= syncer::WriteNode::INIT_SUCCESS
)
660 sync_pb::EntitySpecifics specifics
;
661 AutofillProfileSyncableService::WriteAutofillProfile(profile
, &specifics
);
662 sync_pb::AutofillProfileSpecifics
* profile_specifics
=
663 specifics
.mutable_autofill_profile();
664 node
.SetAutofillProfileSpecifics(*profile_specifics
);
668 bool GetAutofillEntriesFromSyncDB(std::vector
<AutofillEntry
>* entries
,
669 std::vector
<AutofillProfile
>* profiles
) {
670 syncer::ReadTransaction
trans(FROM_HERE
, sync_service_
->GetUserShare());
671 syncer::ReadNode
autofill_root(&trans
);
672 if (autofill_root
.InitByTagLookup(
673 syncer::ModelTypeToRootTag(syncer::AUTOFILL
)) !=
678 int64 child_id
= autofill_root
.GetFirstChildId();
679 while (child_id
!= syncer::kInvalidId
) {
680 syncer::ReadNode
child_node(&trans
);
681 if (child_node
.InitByIdLookup(child_id
) != BaseNode::INIT_OK
)
684 const sync_pb::AutofillSpecifics
& autofill(
685 child_node
.GetAutofillSpecifics());
686 if (autofill
.has_value()) {
687 AutofillKey
key(base::UTF8ToUTF16(autofill
.name()),
688 base::UTF8ToUTF16(autofill
.value()));
689 std::vector
<base::Time
> timestamps
;
690 int timestamps_count
= autofill
.usage_timestamp_size();
691 for (int i
= 0; i
< timestamps_count
; ++i
) {
692 timestamps
.push_back(Time::FromInternalValue(
693 autofill
.usage_timestamp(i
)));
695 entries
->push_back(AutofillEntry(key
, timestamps
));
696 } else if (autofill
.has_profile()) {
698 p
.set_guid(autofill
.profile().guid());
699 AutofillProfileSyncableService::OverwriteProfileWithServerData(
700 autofill
.profile(), &p
, "en-US");
701 profiles
->push_back(p
);
703 child_id
= child_node
.GetSuccessorId();
708 bool GetAutofillProfilesFromSyncDBUnderProfileNode(
709 std::vector
<AutofillProfile
>* profiles
) {
710 syncer::ReadTransaction
trans(FROM_HERE
, sync_service_
->GetUserShare());
711 syncer::ReadNode
autofill_root(&trans
);
712 if (autofill_root
.InitByTagLookup(autofill::kAutofillProfileTag
) !=
717 int64 child_id
= autofill_root
.GetFirstChildId();
718 while (child_id
!= syncer::kInvalidId
) {
719 syncer::ReadNode
child_node(&trans
);
720 if (child_node
.InitByIdLookup(child_id
) != BaseNode::INIT_OK
)
723 const sync_pb::AutofillProfileSpecifics
& autofill(
724 child_node
.GetAutofillProfileSpecifics());
726 p
.set_guid(autofill
.guid());
727 AutofillProfileSyncableService::OverwriteProfileWithServerData(
728 autofill
, &p
, "en-US");
729 profiles
->push_back(p
);
730 child_id
= child_node
.GetSuccessorId();
735 void SetIdleChangeProcessorExpectations() {
736 EXPECT_CALL(autofill_table_
, RemoveFormElement(_
, _
)).Times(0);
737 EXPECT_CALL(autofill_table_
, GetAutofillTimestamps(_
, _
, _
)).Times(0);
738 EXPECT_CALL(autofill_table_
, UpdateAutofillEntries(_
)).Times(0);
741 static AutofillEntry
MakeAutofillEntry(const char* name
,
745 // Time deep in the past would cause Autocomplete sync to discard the
747 static Time base_time
= Time::Now().LocalMidnight();
749 std::vector
<Time
> timestamps
;
751 timestamps
.push_back(base_time
+ TimeDelta::FromSeconds(time_shift0
));
753 timestamps
.push_back(base_time
+ TimeDelta::FromSeconds(time_shift1
));
754 return AutofillEntry(
755 AutofillKey(base::ASCIIToUTF16(name
), base::ASCIIToUTF16(value
)),
759 static AutofillEntry
MakeAutofillEntry(const char* name
,
762 return MakeAutofillEntry(name
, value
, time_shift
, -1);
765 friend class AddAutofillHelper
<AutofillEntry
>;
766 friend class AddAutofillHelper
<AutofillProfile
>;
767 friend class FakeServerUpdater
;
769 scoped_ptr
<TestingProfile
> profile_
;
770 AutofillTableMock autofill_table_
;
771 scoped_ptr
<WebDatabaseFake
> web_database_
;
772 scoped_refptr
<WebDataServiceFake
> web_data_service_
;
773 MockPersonalDataManager
* personal_data_manager_
;
774 syncer::DataTypeAssociationStats association_stats_
;
775 base::WeakPtrFactory
<DataTypeDebugInfoListener
> debug_ptr_factory_
;
779 class AddAutofillHelper
{
781 AddAutofillHelper(ProfileSyncServiceAutofillTest
* test
,
782 const std::vector
<T
>& entries
)
783 : callback_(base::Bind(&AddAutofillHelper::AddAutofillCallback
,
784 base::Unretained(this), test
, entries
)),
788 const base::Closure
& callback() const { return callback_
; }
789 bool success() { return success_
; }
792 void AddAutofillCallback(ProfileSyncServiceAutofillTest
* test
,
793 const std::vector
<T
>& entries
) {
794 if (!test
->CreateRoot(GetModelType
<T
>()))
797 for (size_t i
= 0; i
< entries
.size(); ++i
) {
798 if (!test
->AddAutofillSyncNode(entries
[i
]))
804 base::Closure callback_
;
808 // Overload write transaction to use custom NotifyTransactionComplete
809 class WriteTransactionTest
: public WriteTransaction
{
811 WriteTransactionTest(const tracked_objects::Location
& from_here
,
813 syncer::syncable::Directory
* directory
,
814 scoped_ptr
<WaitableEvent
>* wait_for_syncapi
)
815 : WriteTransaction(from_here
, writer
, directory
),
816 wait_for_syncapi_(wait_for_syncapi
) { }
818 virtual void NotifyTransactionComplete(
819 syncer::ModelTypeSet types
) OVERRIDE
{
820 // This is where we differ. Force a thread change here, giving another
821 // thread a chance to create a WriteTransaction
822 (*wait_for_syncapi_
)->Wait();
824 WriteTransaction::NotifyTransactionComplete(types
);
828 scoped_ptr
<WaitableEvent
>* wait_for_syncapi_
;
831 // Our fake server updater. Needs the RefCountedThreadSafe inheritance so we can
832 // post tasks with it.
833 class FakeServerUpdater
: public base::RefCountedThreadSafe
<FakeServerUpdater
> {
835 FakeServerUpdater(TestProfileSyncService
* service
,
836 scoped_ptr
<WaitableEvent
>* wait_for_start
,
837 scoped_ptr
<WaitableEvent
>* wait_for_syncapi
)
838 : entry_(ProfileSyncServiceAutofillTest::MakeAutofillEntry("0", "0", 0)),
840 wait_for_start_(wait_for_start
),
841 wait_for_syncapi_(wait_for_syncapi
),
842 is_finished_(false, false) { }
845 // This gets called in a modelsafeworker thread.
846 ASSERT_TRUE(BrowserThread::CurrentlyOn(BrowserThread::DB
));
848 syncer::UserShare
* user_share
= service_
->GetUserShare();
849 syncer::syncable::Directory
* directory
= user_share
->directory
.get();
851 // Create autofill protobuf.
852 std::string tag
= AutocompleteSyncableService::KeyToTag(
853 base::UTF16ToUTF8(entry_
.key().name()),
854 base::UTF16ToUTF8(entry_
.key().value()));
855 sync_pb::AutofillSpecifics new_autofill
;
856 new_autofill
.set_name(base::UTF16ToUTF8(entry_
.key().name()));
857 new_autofill
.set_value(base::UTF16ToUTF8(entry_
.key().value()));
858 const std::vector
<base::Time
>& ts(entry_
.timestamps());
859 for (std::vector
<base::Time
>::const_iterator timestamp
= ts
.begin();
860 timestamp
!= ts
.end(); ++timestamp
) {
861 new_autofill
.add_usage_timestamp(timestamp
->ToInternalValue());
864 sync_pb::EntitySpecifics entity_specifics
;
865 entity_specifics
.mutable_autofill()->CopyFrom(new_autofill
);
868 // Tell main thread we've started
869 (*wait_for_start_
)->Signal();
871 // Create write transaction.
872 WriteTransactionTest
trans(FROM_HERE
, UNITTEST
, directory
,
875 // Create actual entry based on autofill protobuf information.
876 // Simulates effects of UpdateLocalDataFromServerData
877 MutableEntry
parent(&trans
, GET_BY_SERVER_TAG
,
878 syncer::ModelTypeToRootTag(syncer::AUTOFILL
));
879 MutableEntry
item(&trans
, CREATE
, syncer::AUTOFILL
, parent
.GetId(), tag
);
880 ASSERT_TRUE(item
.good());
881 item
.PutSpecifics(entity_specifics
);
882 item
.PutServerSpecifics(entity_specifics
);
883 item
.PutBaseVersion(1);
884 syncer::syncable::Id server_item_id
=
885 service_
->id_factory()->NewServerId();
886 item
.PutId(server_item_id
);
887 syncer::syncable::Id new_predecessor
;
888 ASSERT_TRUE(item
.PutPredecessor(new_predecessor
));
890 DVLOG(1) << "FakeServerUpdater finishing.";
891 is_finished_
.Signal();
894 void CreateNewEntry(const AutofillEntry
& entry
) {
896 ASSERT_FALSE(BrowserThread::CurrentlyOn(BrowserThread::DB
));
897 if (!BrowserThread::PostTask(
898 BrowserThread::DB
, FROM_HERE
,
899 base::Bind(&FakeServerUpdater::Update
, this))) {
900 NOTREACHED() << "Failed to post task to the db thread.";
905 void CreateNewEntryAndWait(const AutofillEntry
& entry
) {
907 ASSERT_FALSE(BrowserThread::CurrentlyOn(BrowserThread::DB
));
908 is_finished_
.Reset();
909 if (!BrowserThread::PostTask(BrowserThread::DB
, FROM_HERE
,
910 base::Bind(&FakeServerUpdater::Update
, this))) {
911 NOTREACHED() << "Failed to post task to the db thread.";
918 friend class base::RefCountedThreadSafe
<FakeServerUpdater
>;
919 ~FakeServerUpdater() { }
921 AutofillEntry entry_
;
922 TestProfileSyncService
* service_
;
923 scoped_ptr
<WaitableEvent
>* wait_for_start_
;
924 scoped_ptr
<WaitableEvent
>* wait_for_syncapi_
;
925 WaitableEvent is_finished_
;
926 syncer::syncable::Id parent_id_
;
931 // Checks if the field of type |field_type| in |profile1| includes all values
932 // of the field in |profile2|.
933 bool IncludesField(const AutofillProfile
& profile1
,
934 const AutofillProfile
& profile2
,
935 ServerFieldType field_type
) {
936 std::vector
<base::string16
> values1
;
937 profile1
.GetRawMultiInfo(field_type
, &values1
);
938 std::vector
<base::string16
> values2
;
939 profile2
.GetRawMultiInfo(field_type
, &values2
);
941 std::set
<base::string16
> values_set
;
942 for (size_t i
= 0; i
< values1
.size(); ++i
)
943 values_set
.insert(values1
[i
]);
944 for (size_t i
= 0; i
< values2
.size(); ++i
)
945 if (values_set
.find(values2
[i
]) == values_set
.end())
952 // TODO(skrul): Test abort startup.
953 // TODO(skrul): Test processing of cloud changes.
954 // TODO(tim): Add autofill data type controller test, and a case to cover
955 // waiting for the PersonalDataManager.
956 TEST_F(ProfileSyncServiceAutofillTest
, FailModelAssociation
) {
957 // Don't create the root autofill node so startup fails.
958 StartSyncService(base::Closure(), true, syncer::AUTOFILL
);
959 EXPECT_TRUE(sync_service_
->HasUnrecoverableError());
962 TEST_F(ProfileSyncServiceAutofillTest
, EmptyNativeEmptySync
) {
963 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).WillOnce(Return(true));
964 SetIdleChangeProcessorExpectations();
965 CreateRootHelper
create_root(this, syncer::AUTOFILL
);
966 EXPECT_CALL(*personal_data_manager_
, Refresh());
967 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL
);
968 EXPECT_TRUE(create_root
.success());
969 std::vector
<AutofillEntry
> sync_entries
;
970 std::vector
<AutofillProfile
> sync_profiles
;
971 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries
, &sync_profiles
));
972 EXPECT_EQ(0U, sync_entries
.size());
973 EXPECT_EQ(0U, sync_profiles
.size());
976 TEST_F(ProfileSyncServiceAutofillTest
, HasNativeEntriesEmptySync
) {
977 std::vector
<AutofillEntry
> entries
;
978 entries
.push_back(MakeAutofillEntry("foo", "bar", 1));
979 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).
980 WillOnce(DoAll(SetArgumentPointee
<0>(entries
), Return(true)));
981 SetIdleChangeProcessorExpectations();
982 CreateRootHelper
create_root(this, syncer::AUTOFILL
);
983 EXPECT_CALL(*personal_data_manager_
, Refresh());
984 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL
);
985 ASSERT_TRUE(create_root
.success());
986 std::vector
<AutofillEntry
> sync_entries
;
987 std::vector
<AutofillProfile
> sync_profiles
;
988 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries
, &sync_profiles
));
989 ASSERT_EQ(1U, entries
.size());
990 EXPECT_TRUE(entries
[0] == sync_entries
[0]);
991 EXPECT_EQ(0U, sync_profiles
.size());
994 TEST_F(ProfileSyncServiceAutofillTest
, HasProfileEmptySync
) {
995 std::vector
<AutofillProfile
*> profiles
;
996 std::vector
<AutofillProfile
> expected_profiles
;
997 // Owned by GetAutofillProfiles caller.
998 AutofillProfile
* profile0
= new AutofillProfile
;
999 autofill::test::SetProfileInfoWithGuid(profile0
,
1000 "54B3F9AA-335E-4F71-A27D-719C41564230", "Billing",
1001 "Mitchell", "Morrison",
1002 "johnwayne@me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA",
1003 "91601", "US", "12345678910");
1004 profiles
.push_back(profile0
);
1005 expected_profiles
.push_back(*profile0
);
1006 EXPECT_CALL(autofill_table_
, GetAutofillProfiles(_
)).
1007 WillOnce(DoAll(SetArgumentPointee
<0>(profiles
), Return(true)));
1008 EXPECT_CALL(*personal_data_manager_
, Refresh());
1009 SetIdleChangeProcessorExpectations();
1010 CreateRootHelper
create_root(this, syncer::AUTOFILL_PROFILE
);
1011 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL_PROFILE
);
1012 ASSERT_TRUE(create_root
.success());
1013 std::vector
<AutofillProfile
> sync_profiles
;
1014 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode(&sync_profiles
));
1015 EXPECT_EQ(1U, sync_profiles
.size());
1016 EXPECT_EQ(0, expected_profiles
[0].Compare(sync_profiles
[0]));
1019 TEST_F(ProfileSyncServiceAutofillTest
, HasNativeWithDuplicatesEmptySync
) {
1020 // There is buggy autofill code that allows duplicate name/value
1021 // pairs to exist in the database with separate pair_ids.
1022 std::vector
<AutofillEntry
> entries
;
1023 entries
.push_back(MakeAutofillEntry("foo", "bar", 1));
1024 entries
.push_back(MakeAutofillEntry("dup", "", 2));
1025 entries
.push_back(MakeAutofillEntry("dup", "", 3));
1026 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).
1027 WillOnce(DoAll(SetArgumentPointee
<0>(entries
), Return(true)));
1028 SetIdleChangeProcessorExpectations();
1029 CreateRootHelper
create_root(this, syncer::AUTOFILL
);
1030 EXPECT_CALL(*personal_data_manager_
, Refresh());
1031 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL
);
1032 ASSERT_TRUE(create_root
.success());
1033 std::vector
<AutofillEntry
> sync_entries
;
1034 std::vector
<AutofillProfile
> sync_profiles
;
1035 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries
, &sync_profiles
));
1036 EXPECT_EQ(2U, sync_entries
.size());
1039 TEST_F(ProfileSyncServiceAutofillTest
, HasNativeHasSyncNoMerge
) {
1040 AutofillEntry
native_entry(MakeAutofillEntry("native", "entry", 1));
1041 AutofillEntry
sync_entry(MakeAutofillEntry("sync", "entry", 2));
1043 std::vector
<AutofillEntry
> native_entries
;
1044 native_entries
.push_back(native_entry
);
1046 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).
1047 WillOnce(DoAll(SetArgumentPointee
<0>(native_entries
), Return(true)));
1049 std::vector
<AutofillEntry
> sync_entries
;
1050 sync_entries
.push_back(sync_entry
);
1052 AddAutofillHelper
<AutofillEntry
> add_autofill(this, sync_entries
);
1054 EXPECT_CALL(autofill_table_
, UpdateAutofillEntries(ElementsAre(sync_entry
))).
1055 WillOnce(Return(true));
1057 EXPECT_CALL(*personal_data_manager_
, Refresh());
1058 StartSyncService(add_autofill
.callback(), false, syncer::AUTOFILL
);
1059 ASSERT_TRUE(add_autofill
.success());
1061 std::set
<AutofillEntry
> expected_entries
;
1062 expected_entries
.insert(native_entry
);
1063 expected_entries
.insert(sync_entry
);
1065 std::vector
<AutofillEntry
> new_sync_entries
;
1066 std::vector
<AutofillProfile
> new_sync_profiles
;
1067 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries
,
1068 &new_sync_profiles
));
1069 std::set
<AutofillEntry
> new_sync_entries_set(new_sync_entries
.begin(),
1070 new_sync_entries
.end());
1072 EXPECT_TRUE(expected_entries
== new_sync_entries_set
);
1075 TEST_F(ProfileSyncServiceAutofillTest
, HasNativeHasSyncMergeEntry
) {
1076 AutofillEntry
native_entry(MakeAutofillEntry("merge", "entry", 1));
1077 AutofillEntry
sync_entry(MakeAutofillEntry("merge", "entry", 2));
1078 AutofillEntry
merged_entry(MakeAutofillEntry("merge", "entry", 1, 2));
1080 std::vector
<AutofillEntry
> native_entries
;
1081 native_entries
.push_back(native_entry
);
1082 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).
1083 WillOnce(DoAll(SetArgumentPointee
<0>(native_entries
), Return(true)));
1085 std::vector
<AutofillEntry
> sync_entries
;
1086 sync_entries
.push_back(sync_entry
);
1087 AddAutofillHelper
<AutofillEntry
> add_autofill(this, sync_entries
);
1089 EXPECT_CALL(autofill_table_
,
1090 UpdateAutofillEntries(ElementsAre(merged_entry
))).WillOnce(Return(true));
1091 EXPECT_CALL(*personal_data_manager_
, Refresh());
1092 StartSyncService(add_autofill
.callback(), false, syncer::AUTOFILL
);
1093 ASSERT_TRUE(add_autofill
.success());
1095 std::vector
<AutofillEntry
> new_sync_entries
;
1096 std::vector
<AutofillProfile
> new_sync_profiles
;
1097 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries
,
1098 &new_sync_profiles
));
1099 ASSERT_EQ(1U, new_sync_entries
.size());
1100 EXPECT_TRUE(merged_entry
== new_sync_entries
[0]);
1103 TEST_F(ProfileSyncServiceAutofillTest
, HasNativeHasSyncMergeProfile
) {
1104 AutofillProfile sync_profile
;
1105 autofill::test::SetProfileInfoWithGuid(&sync_profile
,
1106 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing",
1107 "Mitchell", "Morrison",
1108 "johnwayne@me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA",
1109 "91601", "US", "12345678910");
1111 AutofillProfile
* native_profile
= new AutofillProfile
;
1112 autofill::test::SetProfileInfoWithGuid(native_profile
,
1113 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing", "Alicia", "Saenz",
1114 "joewayne@me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL",
1115 "32801", "US", "19482937549");
1117 std::vector
<AutofillProfile
*> native_profiles
;
1118 native_profiles
.push_back(native_profile
);
1119 EXPECT_CALL(autofill_table_
, GetAutofillProfiles(_
)).
1120 WillOnce(DoAll(SetArgumentPointee
<0>(native_profiles
), Return(true)));
1122 std::vector
<AutofillProfile
> sync_profiles
;
1123 sync_profiles
.push_back(sync_profile
);
1124 AddAutofillHelper
<AutofillProfile
> add_autofill(this, sync_profiles
);
1126 EXPECT_CALL(autofill_table_
,
1127 UpdateAutofillProfile(MatchProfiles(sync_profile
))).
1128 WillOnce(Return(true));
1129 EXPECT_CALL(*personal_data_manager_
, Refresh());
1130 StartSyncService(add_autofill
.callback(), false, syncer::AUTOFILL_PROFILE
);
1131 ASSERT_TRUE(add_autofill
.success());
1133 std::vector
<AutofillProfile
> new_sync_profiles
;
1134 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode(
1135 &new_sync_profiles
));
1136 ASSERT_EQ(1U, new_sync_profiles
.size());
1137 EXPECT_EQ(0, sync_profile
.Compare(new_sync_profiles
[0]));
1140 TEST_F(ProfileSyncServiceAutofillTest
, HasNativeHasSyncMergeProfileCombine
) {
1141 AutofillProfile sync_profile
;
1142 autofill::test::SetProfileInfoWithGuid(&sync_profile
,
1143 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing",
1144 "Mitchell", "Morrison",
1145 "johnwayne@me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA",
1146 "91601", "US", "12345678910");
1148 AutofillProfile
* native_profile
= new AutofillProfile
;
1149 // Same address, but different names, phones and e-mails.
1150 autofill::test::SetProfileInfoWithGuid(native_profile
,
1151 "23355099-1170-4B71-8ED4-144470CC9EBF", "Billing", "Alicia", "Saenz",
1152 "joewayne@me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA",
1153 "91601", "US", "19482937549");
1155 AutofillProfile
expected_profile(sync_profile
);
1156 expected_profile
.OverwriteWithOrAddTo(*native_profile
, "en-US");
1158 std::vector
<AutofillProfile
*> native_profiles
;
1159 native_profiles
.push_back(native_profile
);
1160 EXPECT_CALL(autofill_table_
, GetAutofillProfiles(_
)).
1161 WillOnce(DoAll(SetArgumentPointee
<0>(native_profiles
), Return(true)));
1162 EXPECT_CALL(autofill_table_
,
1163 AddAutofillProfile(MatchProfiles(expected_profile
))).
1164 WillOnce(Return(true));
1165 EXPECT_CALL(autofill_table_
,
1166 RemoveAutofillProfile("23355099-1170-4B71-8ED4-144470CC9EBF")).
1167 WillOnce(Return(true));
1168 std::vector
<AutofillProfile
> sync_profiles
;
1169 sync_profiles
.push_back(sync_profile
);
1170 AddAutofillHelper
<AutofillProfile
> add_autofill(this, sync_profiles
);
1172 EXPECT_CALL(*personal_data_manager_
, Refresh());
1173 StartSyncService(add_autofill
.callback(), false, syncer::AUTOFILL_PROFILE
);
1174 ASSERT_TRUE(add_autofill
.success());
1176 std::vector
<AutofillProfile
> new_sync_profiles
;
1177 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode(
1178 &new_sync_profiles
));
1179 ASSERT_EQ(1U, new_sync_profiles
.size());
1180 // Check that key fields are the same.
1181 EXPECT_TRUE(new_sync_profiles
[0].IsSubsetOf(sync_profile
, "en-US"));
1182 // Check that multivalued fields of the synced back data include original
1185 IncludesField(new_sync_profiles
[0], sync_profile
, autofill::NAME_FULL
));
1186 EXPECT_TRUE(IncludesField(
1187 new_sync_profiles
[0], sync_profile
, autofill::EMAIL_ADDRESS
));
1188 EXPECT_TRUE(IncludesField(
1189 new_sync_profiles
[0], sync_profile
, autofill::PHONE_HOME_WHOLE_NUMBER
));
1192 TEST_F(ProfileSyncServiceAutofillTest
, MergeProfileWithDifferentGuid
) {
1193 AutofillProfile sync_profile
;
1195 autofill::test::SetProfileInfoWithGuid(&sync_profile
,
1196 "23355099-1170-4B71-8ED4-144470CC9EBE", "Billing",
1197 "Mitchell", "Morrison",
1198 "johnwayne@me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA",
1199 "91601", "US", "12345678910");
1201 std::string native_guid
= "EDC609ED-7EEE-4F27-B00C-423242A9C44B";
1202 AutofillProfile
* native_profile
= new AutofillProfile
;
1203 autofill::test::SetProfileInfoWithGuid(native_profile
,
1204 native_guid
.c_str(), "Billing",
1205 "Mitchell", "Morrison",
1206 "johnwayne@me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA",
1207 "91601", "US", "12345678910");
1209 std::vector
<AutofillProfile
*> native_profiles
;
1210 native_profiles
.push_back(native_profile
);
1211 EXPECT_CALL(autofill_table_
, GetAutofillProfiles(_
)).
1212 WillOnce(DoAll(SetArgumentPointee
<0>(native_profiles
), Return(true)));
1214 std::vector
<AutofillProfile
> sync_profiles
;
1215 sync_profiles
.push_back(sync_profile
);
1216 AddAutofillHelper
<AutofillProfile
> add_autofill(this, sync_profiles
);
1218 EXPECT_CALL(autofill_table_
, AddAutofillProfile(_
)).
1219 WillOnce(Return(true));
1220 EXPECT_CALL(autofill_table_
, RemoveAutofillProfile(native_guid
)).
1221 WillOnce(Return(true));
1222 EXPECT_CALL(*personal_data_manager_
, Refresh());
1223 StartSyncService(add_autofill
.callback(), false, syncer::AUTOFILL_PROFILE
);
1224 ASSERT_TRUE(add_autofill
.success());
1226 std::vector
<AutofillProfile
> new_sync_profiles
;
1227 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode(
1228 &new_sync_profiles
));
1229 ASSERT_EQ(1U, new_sync_profiles
.size());
1230 EXPECT_EQ(0, sync_profile
.Compare(new_sync_profiles
[0]));
1231 EXPECT_EQ(sync_profile
.guid(), new_sync_profiles
[0].guid());
1234 TEST_F(ProfileSyncServiceAutofillTest
, ProcessUserChangeAddEntry
) {
1235 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).WillOnce(Return(true));
1236 EXPECT_CALL(*personal_data_manager_
, Refresh());
1237 SetIdleChangeProcessorExpectations();
1238 CreateRootHelper
create_root(this, syncer::AUTOFILL
);
1239 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL
);
1240 ASSERT_TRUE(create_root
.success());
1242 AutofillEntry
added_entry(MakeAutofillEntry("added", "entry", 1));
1243 std::vector
<base::Time
> timestamps(added_entry
.timestamps());
1245 EXPECT_CALL(autofill_table_
, GetAutofillTimestamps(_
, _
, _
)).
1246 WillOnce(DoAll(SetArgumentPointee
<2>(timestamps
), Return(true)));
1248 AutofillChangeList changes
;
1249 changes
.push_back(AutofillChange(AutofillChange::ADD
, added_entry
.key()));
1251 web_data_service_
->OnAutofillEntriesChanged(changes
);
1253 std::vector
<AutofillEntry
> new_sync_entries
;
1254 std::vector
<AutofillProfile
> new_sync_profiles
;
1255 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries
,
1256 &new_sync_profiles
));
1257 ASSERT_EQ(1U, new_sync_entries
.size());
1258 EXPECT_TRUE(added_entry
== new_sync_entries
[0]);
1261 TEST_F(ProfileSyncServiceAutofillTest
, ProcessUserChangeAddProfile
) {
1262 EXPECT_CALL(autofill_table_
, GetAutofillProfiles(_
)).WillOnce(Return(true));
1263 EXPECT_CALL(*personal_data_manager_
, Refresh());
1264 SetIdleChangeProcessorExpectations();
1265 CreateRootHelper
create_root(this, syncer::AUTOFILL_PROFILE
);
1266 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL_PROFILE
);
1267 ASSERT_TRUE(create_root
.success());
1269 AutofillProfile added_profile
;
1270 autofill::test::SetProfileInfoWithGuid(&added_profile
,
1271 "D6ADA912-D374-4C0A-917D-F5C8EBE43011", "Josephine", "Alicia", "Saenz",
1272 "joewayne@me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL",
1273 "32801", "US", "19482937549");
1275 AutofillProfileChange
change(
1276 AutofillProfileChange::ADD
, added_profile
.guid(), &added_profile
);
1277 web_data_service_
->OnAutofillProfileChanged(change
);
1279 std::vector
<AutofillProfile
> new_sync_profiles
;
1280 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode(
1281 &new_sync_profiles
));
1282 ASSERT_EQ(1U, new_sync_profiles
.size());
1283 EXPECT_EQ(0, added_profile
.Compare(new_sync_profiles
[0]));
1286 TEST_F(ProfileSyncServiceAutofillTest
, ProcessUserChangeUpdateEntry
) {
1287 AutofillEntry
original_entry(MakeAutofillEntry("my", "entry", 1));
1288 std::vector
<AutofillEntry
> original_entries
;
1289 original_entries
.push_back(original_entry
);
1291 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).
1292 WillOnce(DoAll(SetArgumentPointee
<0>(original_entries
), Return(true)));
1293 EXPECT_CALL(*personal_data_manager_
, Refresh());
1294 CreateRootHelper
create_root(this, syncer::AUTOFILL
);
1295 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL
);
1296 ASSERT_TRUE(create_root
.success());
1298 AutofillEntry
updated_entry(MakeAutofillEntry("my", "entry", 1, 2));
1299 std::vector
<base::Time
> timestamps(updated_entry
.timestamps());
1301 EXPECT_CALL(autofill_table_
, GetAutofillTimestamps(_
, _
, _
)).
1302 WillOnce(DoAll(SetArgumentPointee
<2>(timestamps
), Return(true)));
1304 AutofillChangeList changes
;
1305 changes
.push_back(AutofillChange(AutofillChange::UPDATE
,
1306 updated_entry
.key()));
1307 web_data_service_
->OnAutofillEntriesChanged(changes
);
1309 std::vector
<AutofillEntry
> new_sync_entries
;
1310 std::vector
<AutofillProfile
> new_sync_profiles
;
1311 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries
,
1312 &new_sync_profiles
));
1313 ASSERT_EQ(1U, new_sync_entries
.size());
1314 EXPECT_TRUE(updated_entry
== new_sync_entries
[0]);
1318 TEST_F(ProfileSyncServiceAutofillTest
, ProcessUserChangeRemoveEntry
) {
1319 AutofillEntry
original_entry(MakeAutofillEntry("my", "entry", 1));
1320 std::vector
<AutofillEntry
> original_entries
;
1321 original_entries
.push_back(original_entry
);
1323 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).
1324 WillOnce(DoAll(SetArgumentPointee
<0>(original_entries
), Return(true)));
1325 EXPECT_CALL(*personal_data_manager_
, Refresh());
1326 CreateRootHelper
create_root(this, syncer::AUTOFILL
);
1327 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL
);
1328 ASSERT_TRUE(create_root
.success());
1330 AutofillChangeList changes
;
1331 changes
.push_back(AutofillChange(AutofillChange::REMOVE
,
1332 original_entry
.key()));
1333 web_data_service_
->OnAutofillEntriesChanged(changes
);
1335 std::vector
<AutofillEntry
> new_sync_entries
;
1336 std::vector
<AutofillProfile
> new_sync_profiles
;
1337 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&new_sync_entries
,
1338 &new_sync_profiles
));
1339 ASSERT_EQ(0U, new_sync_entries
.size());
1342 TEST_F(ProfileSyncServiceAutofillTest
, ProcessUserChangeRemoveProfile
) {
1343 AutofillProfile sync_profile
;
1344 autofill::test::SetProfileInfoWithGuid(&sync_profile
,
1345 "3BA5FA1B-1EC4-4BB3-9B57-EC92BE3C1A09", "Josephine", "Alicia", "Saenz",
1346 "joewayne@me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL",
1347 "32801", "US", "19482937549");
1348 AutofillProfile
* native_profile
= new AutofillProfile
;
1349 autofill::test::SetProfileInfoWithGuid(native_profile
,
1350 "3BA5FA1B-1EC4-4BB3-9B57-EC92BE3C1A09", "Josephine", "Alicia", "Saenz",
1351 "joewayne@me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL",
1352 "32801", "US", "19482937549");
1354 std::vector
<AutofillProfile
*> native_profiles
;
1355 native_profiles
.push_back(native_profile
);
1356 EXPECT_CALL(autofill_table_
, GetAutofillProfiles(_
)).
1357 WillOnce(DoAll(SetArgumentPointee
<0>(native_profiles
), Return(true)));
1359 std::vector
<AutofillProfile
> sync_profiles
;
1360 sync_profiles
.push_back(sync_profile
);
1361 AddAutofillHelper
<AutofillProfile
> add_autofill(this, sync_profiles
);
1362 EXPECT_CALL(*personal_data_manager_
, Refresh());
1363 StartSyncService(add_autofill
.callback(), false, syncer::AUTOFILL_PROFILE
);
1364 ASSERT_TRUE(add_autofill
.success());
1366 AutofillProfileChange
change(
1367 AutofillProfileChange::REMOVE
, sync_profile
.guid(), NULL
);
1368 web_data_service_
->OnAutofillProfileChanged(change
);
1370 std::vector
<AutofillProfile
> new_sync_profiles
;
1371 ASSERT_TRUE(GetAutofillProfilesFromSyncDBUnderProfileNode(
1372 &new_sync_profiles
));
1373 ASSERT_EQ(0U, new_sync_profiles
.size());
1376 // http://crbug.com/57884
1377 TEST_F(ProfileSyncServiceAutofillTest
, DISABLED_ServerChangeRace
) {
1378 // Once for MergeDataAndStartSyncing() and twice for ProcessSyncChanges(), via
1379 // LoadAutofillData().
1380 EXPECT_CALL(autofill_table_
, GetAllAutofillEntries(_
)).
1381 Times(3).WillRepeatedly(Return(true));
1382 // On the other hand Autofill and Autocomplete are separated now, so
1383 // GetAutofillProfiles() should not be called.
1384 EXPECT_CALL(autofill_table_
, GetAutofillProfiles(_
)).Times(0);
1385 EXPECT_CALL(autofill_table_
, UpdateAutofillEntries(_
)).
1386 WillRepeatedly(Return(true));
1387 EXPECT_CALL(*personal_data_manager_
, Refresh()).Times(3);
1388 CreateRootHelper
create_root(this, syncer::AUTOFILL
);
1389 StartSyncService(create_root
.callback(), false, syncer::AUTOFILL
);
1390 ASSERT_TRUE(create_root
.success());
1392 // (true, false) means we have to reset after |Signal|, init to unsignaled.
1393 scoped_ptr
<WaitableEvent
> wait_for_start(new WaitableEvent(true, false));
1394 scoped_ptr
<WaitableEvent
> wait_for_syncapi(new WaitableEvent(true, false));
1395 scoped_refptr
<FakeServerUpdater
> updater(new FakeServerUpdater(
1396 sync_service_
, &wait_for_start
, &wait_for_syncapi
));
1398 // This server side update will stall waiting for CommitWaiter.
1399 updater
->CreateNewEntry(MakeAutofillEntry("server", "entry", 1));
1400 wait_for_start
->Wait();
1402 AutofillEntry
syncapi_entry(MakeAutofillEntry("syncapi", "entry", 2));
1403 ASSERT_TRUE(AddAutofillSyncNode(syncapi_entry
));
1404 DVLOG(1) << "Syncapi update finished.";
1406 // If we reach here, it means syncapi succeeded and we didn't deadlock. Yay!
1407 // Signal FakeServerUpdater that it can complete.
1408 wait_for_syncapi
->Signal();
1410 // Make another entry to ensure nothing broke afterwards and wait for finish
1412 updater
->CreateNewEntryAndWait(MakeAutofillEntry("server2", "entry2", 3));
1414 std::vector
<AutofillEntry
> sync_entries
;
1415 std::vector
<AutofillProfile
> sync_profiles
;
1416 ASSERT_TRUE(GetAutofillEntriesFromSyncDB(&sync_entries
, &sync_profiles
));
1417 EXPECT_EQ(3U, sync_entries
.size());
1418 EXPECT_EQ(0U, sync_profiles
.size());
1419 for (size_t i
= 0; i
< sync_entries
.size(); i
++) {
1420 DVLOG(1) << "Entry " << i
<< ": " << sync_entries
[i
].key().name()
1421 << ", " << sync_entries
[i
].key().value();