#include "components/autofill/core/browser/data_model/autofill_profile.h"
#include <algorithm>
#include <array>
#include <functional>
#include <map>
#include <memory>
#include <ostream>
#include <ranges>
#include <set>
#include <vector>
#include "base/feature_list.h"
#include "base/hash/sha1.h"
#include "base/i18n/case_conversion.h"
#include "base/i18n/char_iterator.h"
#include "base/logging.h"
#include "base/memory/raw_ptr.h"
#include "base/metrics/histogram_functions.h"
#include "base/metrics/histogram_macros.h"
#include "base/notreached.h"
#include "base/ranges/algorithm.h"
#include "base/strings/string_number_conversions.h"
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversion_utils.h"
#include "base/strings/utf_string_conversions.h"
#include "base/uuid.h"
#include "build/build_config.h"
#include "components/autofill/core/browser/autofill_address_util.h"
#include "components/autofill/core/browser/autofill_field.h"
#include "components/autofill/core/browser/autofill_type.h"
#include "components/autofill/core/browser/data_model/address.h"
#include "components/autofill/core/browser/data_model/autofill_profile_comparator.h"
#include "components/autofill/core/browser/data_model/autofill_structured_address_utils.h"
#include "components/autofill/core/browser/data_model/contact_info.h"
#include "components/autofill/core/browser/data_model/phone_number.h"
#include "components/autofill/core/browser/field_type_utils.h"
#include "components/autofill/core/browser/field_types.h"
#include "components/autofill/core/browser/geo/address_i18n.h"
#include "components/autofill/core/browser/geo/autofill_country.h"
#include "components/autofill/core/browser/geo/phone_number_i18n.h"
#include "components/autofill/core/browser/geo/state_names.h"
#include "components/autofill/core/browser/metrics/autofill_metrics.h"
#include "components/autofill/core/browser/profile_token_quality.h"
#include "components/autofill/core/browser/validation.h"
#include "components/autofill/core/common/autofill_clock.h"
#include "components/autofill/core/common/autofill_constants.h"
#include "components/autofill/core/common/autofill_features.h"
#include "components/autofill/core/common/autofill_l10n_util.h"
#include "components/autofill/core/common/form_field_data.h"
#include "components/strings/grit/components_strings.h"
#include "third_party/icu/source/common/unicode/uchar.h"
#include "third_party/icu/source/common/unicode/utypes.h"
#include "third_party/icu/source/i18n/unicode/translit.h"
#include "third_party/libaddressinput/chromium/addressinput_util.h"
#include "third_party/libaddressinput/src/cpp/include/libaddressinput/address_data.h"
#include "third_party/libaddressinput/src/cpp/include/libaddressinput/address_formatter.h"
#include "ui/base/l10n/l10n_util.h"
#if BUILDFLAG(IS_ANDROID)
#include "base/android/jni_android.h"
#include "base/android/jni_array.h"
#include "base/android/jni_string.h"
#include "components/autofill/android/main_autofill_jni_headers/AutofillProfile_jni.h"
#endif
AddressData;
AddressField;
namespace autofill {
namespace {
const std::array<FieldType, 7> kStructuredDataTypes = …;
FieldType GetStorableTypeCollapsingGroupsForPartialType(FieldType type) { … }
FieldType GetStorableTypeCollapsingGroups(FieldType type,
bool use_improved_labels_order) { … }
int SpecificityForType(FieldType type, bool use_improved_labels_order) { … }
void GetFieldsForDistinguishingProfiles(
const std::vector<FieldType>* suggested_fields,
FieldTypeSet excluded_fields,
std::vector<FieldType>* distinguishing_fields,
bool use_improved_labels_order) { … }
#if BUILDFLAG(IS_ANDROID)
AutofillProfile CreateStarterProfile(
const base::android::JavaParamRef<jobject>& jprofile,
JNIEnv* env,
const AutofillProfile* existing_profile) {
std::string guid = Java_AutofillProfile_getGUID(env, jprofile);
if (!existing_profile) {
AutofillProfile::RecordType record_type =
Java_AutofillProfile_getRecordType(env, jprofile);
AddressCountryCode country_code =
AddressCountryCode(Java_AutofillProfile_getCountryCode(env, jprofile));
AutofillProfile profile = AutofillProfile(record_type, country_code);
if (!guid.empty()) {
profile.set_guid(guid);
}
return profile;
}
CHECK_EQ(existing_profile->guid(), guid);
return *existing_profile;
}
#endif
}
AutofillProfile::AutofillProfile(const std::string& guid,
RecordType record_type,
AddressCountryCode country_code)
: … { … }
AutofillProfile::AutofillProfile(RecordType record_type,
AddressCountryCode country_code)
: … { … }
AutofillProfile::AutofillProfile(AddressCountryCode country_code)
: … { … }
AutofillProfile::AutofillProfile(const AutofillProfile& profile)
: … { … }
AutofillProfile::~AutofillProfile() = default;
AutofillProfile& AutofillProfile::operator=(const AutofillProfile& profile) { … }
#if BUILDFLAG(IS_ANDROID)
base::android::ScopedJavaLocalRef<jobject> AutofillProfile::CreateJavaObject(
const std::string& app_locale) const {
JNIEnv* env = base::android::AttachCurrentThread();
base::android::ScopedJavaLocalRef<jobject> jprofile =
Java_AutofillProfile_Constructor(
env, guid(), static_cast<jint>(record_type()), language_code());
for (FieldType type : GetDatabaseStoredTypesOfAutofillProfile()) {
auto status = static_cast<jint>(GetVerificationStatus(type));
if (type == NAME_FULL) {
Java_AutofillProfile_setInfo(env, jprofile, static_cast<jint>(type),
GetInfo(type, app_locale), status);
} else {
Java_AutofillProfile_setInfo(env, jprofile, static_cast<jint>(type),
GetRawInfo(type), status);
}
}
return jprofile;
}
AutofillProfile AutofillProfile::CreateFromJavaObject(
const base::android::JavaParamRef<jobject>& jprofile,
const AutofillProfile* existing_profile,
const std::string& app_locale) {
JNIEnv* env = base::android::AttachCurrentThread();
AutofillProfile profile =
CreateStarterProfile(jprofile, env, existing_profile);
std::vector<int> field_types =
Java_AutofillProfile_getFieldTypes(env, jprofile);
for (int int_field_type : field_types) {
FieldType field_type = ToSafeFieldType(int_field_type, NO_SERVER_DATA);
CHECK(field_type != NO_SERVER_DATA);
VerificationStatus status =
Java_AutofillProfile_getInfoStatus(env, jprofile, field_type);
std::u16string value =
Java_AutofillProfile_getInfo(env, jprofile, field_type);
if (value.empty()) {
continue;
}
if (field_type == NAME_FULL || field_type == ADDRESS_HOME_COUNTRY) {
profile.SetInfoWithVerificationStatus(field_type, value, app_locale,
status);
} else {
profile.SetRawInfoWithVerificationStatus(field_type, value, status);
}
}
profile.set_language_code(
Java_AutofillProfile_getLanguageCode(env, jprofile));
profile.FinalizeAfterImport();
return profile;
}
#endif
double AutofillProfile::GetRankingScore(base::Time current_time,
bool use_frecency) const { … }
bool AutofillProfile::HasGreaterRankingThan(const AutofillProfile* other,
base::Time comparison_time,
bool use_frecency) const { … }
void AutofillProfile::GetMatchingTypes(const std::u16string& text,
const std::string& app_locale,
FieldTypeSet* matching_types) const { … }
std::u16string AutofillProfile::GetRawInfo(FieldType type) const { … }
void AutofillProfile::SetRawInfoWithVerificationStatus(
FieldType type,
const std::u16string& value,
VerificationStatus status) { … }
void AutofillProfile::GetSupportedTypes(FieldTypeSet* supported_types) const { … }
FieldType AutofillProfile::GetStorableTypeOf(FieldType type) const { … }
bool AutofillProfile::IsEmpty(const std::string& app_locale) const { … }
bool AutofillProfile::IsPresentButInvalid(FieldType type) const { … }
int AutofillProfile::Compare(const AutofillProfile& profile) const { … }
bool AutofillProfile::EqualsForLegacySyncPurposes(
const AutofillProfile& profile) const { … }
bool AutofillProfile::EqualsForUpdatePurposes(
const AutofillProfile& new_profile) const { … }
bool AutofillProfile::operator==(const AutofillProfile& profile) const { … }
bool AutofillProfile::IsSubsetOf(const AutofillProfileComparator& comparator,
const AutofillProfile& profile) const { … }
bool AutofillProfile::IsSubsetOfForFieldSet(
const AutofillProfileComparator& comparator,
const AutofillProfile& profile,
const FieldTypeSet& types) const { … }
bool AutofillProfile::IsStrictSupersetOf(
const AutofillProfileComparator& comparator,
const AutofillProfile& profile) const { … }
AddressCountryCode AutofillProfile::GetAddressCountryCode() const { … }
bool AutofillProfile::IsAccountProfile() const { … }
void AutofillProfile::OverwriteDataFromForLegacySync(
const AutofillProfile& profile) { … }
bool AutofillProfile::MergeDataFrom(const AutofillProfile& profile,
const std::string& app_locale) { … }
void AutofillProfile::MergeFormGroupTokenQuality(
const FormGroup& merged_group,
const AutofillProfile& other_profile) { … }
void AutofillProfile::CreateDifferentiatingLabels(
const std::vector<raw_ptr<const AutofillProfile, VectorExperimental>>&
profiles,
const std::string& app_locale,
std::vector<std::u16string>* labels) { … }
void AutofillProfile::CreateInferredLabels(
const std::vector<raw_ptr<const AutofillProfile, VectorExperimental>>&
profiles,
const std::optional<FieldTypeSet> suggested_fields,
std::optional<FieldType> triggering_field_type,
FieldTypeSet excluded_fields,
size_t minimal_fields_shown,
const std::string& app_locale,
std::vector<std::u16string>* labels,
bool use_improved_labels_order) { … }
std::u16string AutofillProfile::ConstructInferredLabel(
base::span<const FieldType> included_fields,
size_t num_fields_to_use,
const std::string& app_locale) const { … }
void AutofillProfile::RecordAndLogUse() { … }
void AutofillProfile::LogVerificationStatuses() { … }
VerificationStatus AutofillProfile::GetVerificationStatusImpl(
const FieldType type) const { … }
std::u16string AutofillProfile::GetInfoImpl(
const AutofillType& type,
const std::string& app_locale) const { … }
bool AutofillProfile::SetInfoWithVerificationStatusImpl(
const AutofillType& type,
const std::u16string& value,
const std::string& app_locale,
VerificationStatus status) { … }
void AutofillProfile::CreateInferredLabelsHelper(
const std::vector<raw_ptr<const AutofillProfile, VectorExperimental>>&
profiles,
const std::list<size_t>& indices,
const std::vector<FieldType>& field_types,
size_t num_fields_to_include,
const std::string& app_locale,
std::vector<std::u16string>* labels) { … }
const FormGroup* AutofillProfile::FormGroupForType(FieldType type) const { … }
FormGroup* AutofillProfile::MutableFormGroupForType(FieldType type) { … }
bool AutofillProfile::EqualsSansGuid(const AutofillProfile& profile) const { … }
std::ostream& operator<<(std::ostream& os, const AutofillProfile& profile) { … }
bool AutofillProfile::FinalizeAfterImport() { … }
bool AutofillProfile::HasStructuredData() const { … }
AutofillProfile AutofillProfile::ConvertToAccountProfile() const { … }
FieldTypeSet AutofillProfile::FindInaccessibleProfileValues() const { … }
void AutofillProfile::ClearFields(const FieldTypeSet& fields) { … }
AutofillType AutofillProfile::GetFillingType(AutofillType field_type) const { … }
}