Commit f8e757f6 authored by Siyu An's avatar Siyu An Committed by Commit Bot

[Autofill Offer] Add sync integration tests for the offer type

Offer data will be server-only data, so I figure we don't need two
clients integration tests.

Bug: 1093057
Change-Id: I8afb57ed49b7ab6d57071c331ea679fdf1928260
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2453351
Commit-Queue: Siyu An <siyua@chromium.org>
Reviewed-by: default avatarJan Krcal <jkrcal@chromium.org>
Reviewed-by: default avatarMarc Treib <treib@chromium.org>
Cr-Commit-Position: refs/heads/master@{#816337}
parent 7770990a
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/sync/test/integration/offer_helper.h"
#include "base/strings/string_number_conversions.h"
#include "components/autofill/core/browser/autofill_test_utils.h"
#include "components/autofill/core/browser/data_model/autofill_offer_data.h"
#include "components/autofill/core/browser/webdata/autofill_sync_bridge_util.h"
using autofill::AutofillOfferData;
using autofill::SetAutofillOfferSpecificsFromOfferData;
using autofill::test::GetCardLinkedOfferData1;
using sync_pb::AutofillOfferSpecifics;
using sync_pb::SyncEntity;
namespace offer_helper {
SyncEntity CreateDefaultSyncCardLinkedOffer() {
return CreateSyncCardLinkedOffer(GetCardLinkedOfferData1());
}
SyncEntity CreateSyncCardLinkedOffer(const AutofillOfferData& offer_data) {
SyncEntity entity;
entity.set_name(base::NumberToString(offer_data.offer_id));
entity.set_id_string(base::NumberToString(offer_data.offer_id));
entity.set_version(0); // Will be overridden by the fake server.
entity.set_ctime(12345);
entity.set_mtime(12345);
AutofillOfferSpecifics* offer_specifics =
entity.mutable_specifics()->mutable_autofill_offer();
SetAutofillOfferSpecificsFromOfferData(offer_data, offer_specifics);
return entity;
}
} // namespace offer_helper
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_SYNC_TEST_INTEGRATION_OFFER_HELPER_H_
#define CHROME_BROWSER_SYNC_TEST_INTEGRATION_OFFER_HELPER_H_
#include <string>
namespace autofill {
struct AutofillOfferData;
} // namespace autofill
namespace sync_pb {
class SyncEntity;
} // namespace sync_pb
namespace offer_helper {
sync_pb::SyncEntity CreateDefaultSyncCardLinkedOffer();
sync_pb::SyncEntity CreateSyncCardLinkedOffer(
const autofill::AutofillOfferData& offer_data);
} // namespace offer_helper
#endif // CHROME_BROWSER_SYNC_TEST_INTEGRATION_OFFER_HELPER_H_
......@@ -32,9 +32,11 @@ bool AreProgressMarkersEquivalent(const std::string& serialized1,
DCHECK(marker1.data_type_id() == marker2.data_type_id());
if (syncer::GetModelTypeFromSpecificsFieldNumber(marker1.data_type_id()) ==
syncer::AUTOFILL_WALLET_DATA) {
return fake_server::AreWalletDataProgressMarkersEquivalent(marker1,
marker2);
syncer::AUTOFILL_WALLET_DATA ||
syncer::GetModelTypeFromSpecificsFieldNumber(marker1.data_type_id()) ==
syncer::AUTOFILL_WALLET_OFFER) {
return fake_server::AreFullUpdateTypeDataProgressMarkersEquivalent(marker1,
marker2);
}
return marker1.SerializeAsString() == marker2.SerializeAsString();
}
......
......@@ -63,7 +63,7 @@ using wallet_helper::GetPersonalDataManager;
using wallet_helper::GetProfileWebDataService;
using wallet_helper::GetServerAddressesMetadata;
using wallet_helper::GetServerCardsMetadata;
using wallet_helper::GetWalletDataModelTypeState;
using wallet_helper::GetWalletModelTypeState;
using wallet_helper::kDefaultBillingAddressID;
using wallet_helper::kDefaultCardID;
using wallet_helper::kDefaultCreditCardCloudTokenDataID;
......@@ -110,62 +110,6 @@ class AutofillWebDataServiceConsumer : public WebDataServiceConsumer {
DISALLOW_COPY_AND_ASSIGN(AutofillWebDataServiceConsumer);
};
class WaitForWalletUpdateChecker : public StatusChangeChecker,
public syncer::SyncServiceObserver {
public:
WaitForWalletUpdateChecker(base::Time min_required_progress_marker_timestamp,
syncer::SyncService* service)
: min_required_progress_marker_timestamp_(
min_required_progress_marker_timestamp),
service_(service) {
scoped_observer_.Add(service);
}
bool IsExitConditionSatisfied(std::ostream* os) override {
// GetLastCycleSnapshot() returns by value, so make sure to capture it for
// iterator use.
const syncer::SyncCycleSnapshot snap =
service_->GetLastCycleSnapshotForDebugging();
const syncer::ProgressMarkerMap& progress_markers =
snap.download_progress_markers();
auto marker_it = progress_markers.find(syncer::AUTOFILL_WALLET_DATA);
if (marker_it == progress_markers.end()) {
*os << "Waiting for an updated Wallet progress marker timestamp "
<< min_required_progress_marker_timestamp_
<< "; actual: no progress marker in last sync cycle";
return false;
}
sync_pb::DataTypeProgressMarker progress_marker;
bool success = progress_marker.ParseFromString(marker_it->second);
DCHECK(success);
const base::Time actual_timestamp =
fake_server::FakeServer::GetWalletProgressMarkerTimestamp(
progress_marker);
*os << "Waiting for an updated Wallet progress marker timestamp "
<< min_required_progress_marker_timestamp_ << "; actual "
<< actual_timestamp;
return actual_timestamp >= min_required_progress_marker_timestamp_;
}
// syncer::SyncServiceObserver implementation.
void OnSyncCycleCompleted(syncer::SyncService* sync) override {
CheckExitCondition();
}
private:
const base::Time min_required_progress_marker_timestamp_;
const syncer::SyncService* const service_;
ScopedObserver<syncer::SyncService, syncer::SyncServiceObserver>
scoped_observer_{this};
DISALLOW_COPY_AND_ASSIGN(WaitForWalletUpdateChecker);
};
std::vector<std::unique_ptr<CreditCard>> GetServerCards(
scoped_refptr<autofill::AutofillWebDataService> service) {
AutofillWebDataServiceConsumer<std::vector<std::unique_ptr<CreditCard>>>
......@@ -264,7 +208,9 @@ class SingleClientWalletSyncTest : public SyncTest {
// Trigger a sync and wait for the new data to arrive.
TriggerSyncForModelTypes(
0, syncer::ModelTypeSet(syncer::AUTOFILL_WALLET_DATA));
return WaitForWalletUpdateChecker(now, GetSyncService(0)).Wait();
return FullUpdateTypeProgressMarkerChecker(now, GetSyncService(0),
syncer::AUTOFILL_WALLET_DATA)
.Wait();
}
void AdvanceAutofillClockByOneDay() {
......@@ -670,12 +616,14 @@ IN_PROC_BROWSER_TEST_F(SingleClientWalletSyncTest, EmptyUpdatesAreIgnored) {
EXPECT_EQ("data-1", cloud_token_data[0]->instrument_token);
// Trigger a sync and wait for the new data to arrive.
sync_pb::ModelTypeState state_before = GetWalletDataModelTypeState(0);
sync_pb::ModelTypeState state_before =
GetWalletModelTypeState(syncer::AUTOFILL_WALLET_DATA, 0);
ASSERT_TRUE(TriggerGetUpdatesAndWait());
// Check that the new progress marker is stored for empty updates. This is a
// regression check for crbug.com/924447.
sync_pb::ModelTypeState state_after = GetWalletDataModelTypeState(0);
sync_pb::ModelTypeState state_after =
GetWalletModelTypeState(syncer::AUTOFILL_WALLET_DATA, 0);
EXPECT_NE(state_before.progress_marker().token(),
state_after.progress_marker().token());
......
......@@ -213,13 +213,13 @@ void GetServerAddressesMetadataOnDBSequence(
->GetServerAddressesMetadata(addresses_metadata);
}
void GetWalletDataModelTypeStateOnDBSequence(
AutofillWebDataService* wds,
sync_pb::ModelTypeState* model_type_state) {
void GetModelTypeStateOnDBSequence(syncer::ModelType model_type,
AutofillWebDataService* wds,
sync_pb::ModelTypeState* model_type_state) {
DCHECK(wds->GetDBTaskRunner()->RunsTasksInCurrentSequence());
syncer::MetadataBatch metadata_batch;
AutofillTable::FromWebDatabase(wds->GetDatabase())
->GetAllSyncMetadata(syncer::AUTOFILL_WALLET_DATA, &metadata_batch);
->GetAllSyncMetadata(model_type, &metadata_batch);
*model_type_state = metadata_batch.GetModelTypeState();
}
......@@ -321,11 +321,14 @@ std::map<std::string, AutofillMetadata> GetServerAddressesMetadata(
return addresses_metadata;
}
sync_pb::ModelTypeState GetWalletDataModelTypeState(int profile) {
sync_pb::ModelTypeState GetWalletModelTypeState(syncer::ModelType model_type,
int profile) {
DCHECK(model_type == syncer::AUTOFILL_WALLET_DATA ||
model_type == syncer::AUTOFILL_WALLET_OFFER);
sync_pb::ModelTypeState result;
scoped_refptr<AutofillWebDataService> wds = GetProfileWebDataService(profile);
wds->GetDBTaskRunner()->PostTask(
FROM_HERE, base::BindOnce(&GetWalletDataModelTypeStateOnDBSequence,
FROM_HERE, base::BindOnce(&GetModelTypeStateOnDBSequence, model_type,
base::Unretained(wds.get()), &result));
WaitForCurrentTasksToComplete(wds->GetDBTaskRunner());
return result;
......@@ -669,3 +672,53 @@ bool AutofillWalletMetadataSizeChecker::IsExitConditionSatisfiedImpl() {
}
return true;
}
FullUpdateTypeProgressMarkerChecker::FullUpdateTypeProgressMarkerChecker(
base::Time min_required_progress_marker_timestamp,
syncer::SyncService* service,
syncer::ModelType model_type)
: min_required_progress_marker_timestamp_(
min_required_progress_marker_timestamp),
service_(service),
model_type_(model_type) {
scoped_observer_.Add(service);
}
FullUpdateTypeProgressMarkerChecker::~FullUpdateTypeProgressMarkerChecker() =
default;
bool FullUpdateTypeProgressMarkerChecker::IsExitConditionSatisfied(
std::ostream* os) {
// GetLastCycleSnapshot() returns by value, so make sure to capture it for
// iterator use.
const syncer::SyncCycleSnapshot snap =
service_->GetLastCycleSnapshotForDebugging();
const syncer::ProgressMarkerMap& progress_markers =
snap.download_progress_markers();
auto marker_it = progress_markers.find(model_type_);
if (marker_it == progress_markers.end()) {
*os << "Waiting for an updated progress marker timestamp "
<< min_required_progress_marker_timestamp_
<< "; actual: no progress marker in last sync cycle";
return false;
}
sync_pb::DataTypeProgressMarker progress_marker;
bool success = progress_marker.ParseFromString(marker_it->second);
DCHECK(success);
const base::Time actual_timestamp =
fake_server::FakeServer::GetProgressMarkerTimestamp(progress_marker);
*os << "Waiting for an updated progress marker timestamp "
<< min_required_progress_marker_timestamp_ << "; actual "
<< actual_timestamp;
return actual_timestamp >= min_required_progress_marker_timestamp_;
}
// syncer::SyncServiceObserver implementation.
void FullUpdateTypeProgressMarkerChecker::OnSyncCycleCompleted(
syncer::SyncService* sync) {
CheckExitCondition();
}
......@@ -27,6 +27,7 @@ class PersonalDataManager;
namespace sync_pb {
class SyncEntity;
class ModelType;
class ModelTypeState;
}
......@@ -79,7 +80,9 @@ std::map<std::string, autofill::AutofillMetadata> GetServerCardsMetadata(
std::map<std::string, autofill::AutofillMetadata> GetServerAddressesMetadata(
int profile);
sync_pb::ModelTypeState GetWalletDataModelTypeState(int profile);
// Function supports AUTOFILL_WALLET_DATA and AUTOFILL_WALLET_OFFER.
sync_pb::ModelTypeState GetWalletModelTypeState(syncer::ModelType type,
int profile);
void UnmaskServerCard(int profile,
const autofill::CreditCard& credit_card,
......@@ -189,4 +192,35 @@ class AutofillWalletMetadataSizeChecker
bool checking_exit_condition_in_flight_ = false;
};
// Checker to block until a new progress marker with correct timestamp is
// received.
class FullUpdateTypeProgressMarkerChecker : public StatusChangeChecker,
public syncer::SyncServiceObserver {
public:
FullUpdateTypeProgressMarkerChecker(
base::Time min_required_progress_marker_timestamp,
syncer::SyncService* service,
syncer::ModelType model_type);
~FullUpdateTypeProgressMarkerChecker() override;
FullUpdateTypeProgressMarkerChecker(
const FullUpdateTypeProgressMarkerChecker&) = delete;
FullUpdateTypeProgressMarkerChecker& operator=(
const FullUpdateTypeProgressMarkerChecker&) = delete;
// StatusChangeChecker:
bool IsExitConditionSatisfied(std::ostream* os) override;
// syncer::SyncServiceObserver:
void OnSyncCycleCompleted(syncer::SyncService* sync) override;
private:
const base::Time min_required_progress_marker_timestamp_;
const syncer::SyncService* const service_;
const syncer::ModelType model_type_;
ScopedObserver<syncer::SyncService, syncer::SyncServiceObserver>
scoped_observer_{this};
};
#endif // CHROME_BROWSER_SYNC_TEST_INTEGRATION_WALLET_HELPER_H_
......@@ -6852,6 +6852,8 @@ if (!is_fuchsia) {
"../browser/sync/test/integration/migration_waiter.h",
"../browser/sync/test/integration/migration_watcher.cc",
"../browser/sync/test/integration/migration_watcher.h",
"../browser/sync/test/integration/offer_helper.cc",
"../browser/sync/test/integration/offer_helper.h",
"../browser/sync/test/integration/passwords_helper.cc",
"../browser/sync/test/integration/passwords_helper.h",
"../browser/sync/test/integration/preferences_helper.cc",
......@@ -6964,6 +6966,7 @@ if (!is_fuchsia && !is_android) {
"../browser/sync/test/integration/single_client_extensions_sync_test.cc",
"../browser/sync/test/integration/single_client_history_delete_directives_sync_test.cc",
"../browser/sync/test/integration/single_client_nigori_sync_test.cc",
"../browser/sync/test/integration/single_client_offer_sync_test.cc",
"../browser/sync/test/integration/single_client_passwords_sync_test.cc",
"../browser/sync/test/integration/single_client_polling_sync_test.cc",
"../browser/sync/test/integration/single_client_preferences_sync_test.cc",
......
......@@ -38,7 +38,7 @@ namespace fake_server {
// is in-line with the server behavior and -- as it keeps changing -- allows
// integration tests to wait for a GetUpdates call to finish, even if they don't
// contain data updates.
bool AreWalletDataProgressMarkersEquivalent(
bool AreFullUpdateTypeDataProgressMarkersEquivalent(
const sync_pb::DataTypeProgressMarker& marker1,
const sync_pb::DataTypeProgressMarker& marker2);
......@@ -111,14 +111,24 @@ class FakeServer : public syncer::LoopbackServer::ObserverForTests {
//
// The returned value represents the timestamp of the write, such that any
// progress marker greater or equal to this timestamp must have processed the
// changes. See GetWalletProgressMarkerTimestamp() below.
// changes. See GetProgressMarkerTimestamp() below.
base::Time SetWalletData(
const std::vector<sync_pb::SyncEntity>& wallet_entities);
// Allows the caller to know the wallet timestamp corresponding to
// Sets the Autofill offer data to be served in following GetUpdates
// requests (any further GetUpdates response will be empty, indicating no
// change, if the client already has received |offer_entities|).
//
// The returned value represents the timestamp of the write, such that any
// progress marker greater or equal to this timestamp must have processed the
// changes. See GetProgressMarkerTimestamp() below.
base::Time SetOfferData(
const std::vector<sync_pb::SyncEntity>& offer_entities);
// Allows the caller to know the timestamp corresponding to
// |progress_marker| as annotated by the FakeServer during the GetUpdates
// request that returned the progress marker.
static base::Time GetWalletProgressMarkerTimestamp(
static base::Time GetProgressMarkerTimestamp(
const sync_pb::DataTypeProgressMarker& progress_marker);
// Modifies the entity on the server with the given |id|. The entity's
......@@ -297,6 +307,10 @@ class FakeServer : public syncer::LoopbackServer::ObserverForTests {
// the FakeServer handles those itself.
std::vector<sync_pb::SyncEntity> wallet_entities_;
// The LoopbackServer does not know how to handle offer data properly, so
// the FakeServer handles those itself.
std::vector<sync_pb::SyncEntity> offer_entities_;
// Creates WeakPtr versions of the current FakeServer. This must be the last
// data member!
base::WeakPtrFactory<FakeServer> weak_ptr_factory_{this};
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment