1 // Copyright 2013 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 #ifndef COMPONENTS_AUTOFILL_CORE_BROWSER_FORM_STRUCTURE_H_ 6 #define COMPONENTS_AUTOFILL_CORE_BROWSER_FORM_STRUCTURE_H_ 7 8 #include <stddef.h> 9 10 #include <map> 11 #include <memory> 12 #include <set> 13 #include <string> 14 #include <utility> 15 #include <vector> 16 17 #include "base/gtest_prod_util.h" 18 #include "base/macros.h" 19 #include "base/optional.h" 20 #include "base/strings/string_piece.h" 21 #include "components/autofill/core/browser/autofill_field.h" 22 #include "components/autofill/core/browser/autofill_metrics.h" 23 #include "components/autofill/core/browser/autofill_type.h" 24 #include "components/autofill/core/browser/field_types.h" 25 #include "components/autofill/core/browser/form_types.h" 26 #include "components/autofill/core/browser/proto/api_v1.pb.h" 27 #include "components/autofill/core/common/mojom/autofill_types.mojom.h" 28 #include "components/autofill/core/common/renderer_id.h" 29 #include "url/gurl.h" 30 #include "url/origin.h" 31 32 enum UploadRequired { UPLOAD_NOT_REQUIRED, UPLOAD_REQUIRED, USE_UPLOAD_RATES }; 33 34 namespace base { 35 class TimeTicks; 36 } 37 38 namespace autofill { 39 40 class LogBuffer; 41 class LogManager; 42 43 // Password attributes (whether a password has special symbols, numeric, etc.) 44 enum class PasswordAttribute { 45 kHasLowercaseLetter, 46 kHasSpecialSymbol, 47 kPasswordAttributesCount 48 }; 49 50 // The structure of forms and fields, represented by their signatures, on a 51 // page. These are sequence containers to reflect their order in the DOM. 52 using FormAndFieldSignatures = 53 std::vector<std::pair<FormSignature, std::vector<FieldSignature>>>; 54 55 struct FormData; 56 struct FormDataPredictions; 57 58 class RandomizedEncoder; 59 60 // FormStructure stores a single HTML form together with the values entered 61 // in the fields along with additional information needed by Autofill. 62 class FormStructure { 63 public: 64 explicit FormStructure(const FormData& form); 65 virtual ~FormStructure(); 66 67 // Runs several heuristics against the form fields to determine their possible 68 // types. 69 void DetermineHeuristicTypes(LogManager* log_manager = nullptr); 70 71 // Encodes the proto |upload| request from this FormStructure, and stores 72 // the (single) FormSignature and the signatures of the fields to be uploaded 73 // in |encoded_signatures|. 74 // In some cases, a |login_form_signature| is included as part of the upload. 75 // This field is empty when sending upload requests for non-login forms. 76 bool EncodeUploadRequest( 77 const ServerFieldTypeSet& available_field_types, 78 bool form_was_autofilled, 79 const std::string& login_form_signature, 80 bool observed_submission, 81 autofill::AutofillUploadContents* upload, 82 std::vector<FormSignature>* encoded_signatures) const; 83 84 // Encodes the proto |query| request for the list of |forms| and their fields 85 // that are valid. The queried FormSignatures and FieldSignatures are stored 86 // in |queried_form_signatures| in the same order as in |query|. In case 87 // multiple FormStructures have the same FormSignature, only the first one is 88 // included in |query| and |queried_form_signatures|. 89 static bool EncodeQueryRequest( 90 const std::vector<FormStructure*>& forms, 91 autofill::AutofillPageQueryRequest* query, 92 std::vector<FormSignature>* queried_form_signatures); 93 94 // Parses `payload` as AutofillQueryResponse proto and calls 95 // ProcessQueryResponse(). 96 static void ParseApiQueryResponse( 97 base::StringPiece payload, 98 const std::vector<FormStructure*>& forms, 99 const std::vector<FormSignature>& queried_form_signatures, 100 AutofillMetrics::FormInteractionsUkmLogger*); 101 102 // Returns predictions using the details from the given |form_structures| and 103 // their fields' predicted types. 104 static std::vector<FormDataPredictions> GetFieldTypePredictions( 105 const std::vector<FormStructure*>& form_structures); 106 107 // Returns whether sending autofill field metadata to the server is enabled. 108 static bool IsAutofillFieldMetadataEnabled(); 109 110 // Creates FormStructure that has bare minimum information for uploading 111 // votes, namely form and field signatures. Warning: do not use for Autofill 112 // code, since it is likely missing some fields. 113 static std::unique_ptr<FormStructure> CreateForPasswordManagerUpload( 114 FormSignature form_signature, 115 const std::vector<FieldSignature>& field_signatures); 116 117 // Return the form signature as string. 118 std::string FormSignatureAsStr() const; 119 120 // Runs a quick heuristic to rule out forms that are obviously not 121 // auto-fillable, like google/yahoo/msn search, etc. 122 bool IsAutofillable() const; 123 124 // Returns whether |this| form represents a complete Credit Card form, which 125 // consists in having at least a credit card number field and an expiration 126 // field. 127 bool IsCompleteCreditCardForm() const; 128 129 // Resets |autofill_count_| and counts the number of auto-fillable fields. 130 // This is used when we receive server data for form fields. At that time, 131 // we may have more known fields than just the number of fields we matched 132 // heuristically. 133 void UpdateAutofillCount(); 134 135 // Returns true if this form matches the structural requirements for Autofill. 136 bool ShouldBeParsed(LogManager* log_manager = nullptr) const; 137 138 // Returns true if heuristic autofill type detection should be attempted for 139 // this form. 140 bool ShouldRunHeuristics() const; 141 142 // Returns true if we should query the crowd-sourcing server to determine this 143 // form's field types. If the form includes author-specified types, this will 144 // return false unless there are password fields in the form. If there are no 145 // password fields the assumption is that the author has expressed their 146 // intent and crowdsourced data should not be used to override this. Password 147 // fields are different because there is no way to specify password generation 148 // directly. 149 bool ShouldBeQueried() const; 150 151 // Returns true if we should upload Autofill votes for this form to the 152 // crowd-sourcing server. It is not applied for Password Manager votes. 153 bool ShouldBeUploaded() const; 154 155 // Sets the field types to be those set for |cached_form|. 156 void RetrieveFromCache(const FormStructure& cached_form, 157 const bool should_keep_cached_value, 158 const bool only_server_and_autofill_state); 159 160 // Logs quality metrics for |this|, which should be a user-submitted form. 161 // This method should only be called after the possible field types have been 162 // set for each field. |interaction_time| should be a timestamp corresponding 163 // to the user's first interaction with the form. |submission_time| should be 164 // a timestamp corresponding to the form's submission. |observed_submission| 165 // indicates whether this method is called as a result of observing a 166 // submission event (otherwise, it may be that an upload was triggered after 167 // a form was unfocused or a navigation occurred). 168 // TODO(sebsg): We log more than quality metrics. Maybe rename or split 169 // function? 170 void LogQualityMetrics( 171 const base::TimeTicks& load_time, 172 const base::TimeTicks& interaction_time, 173 const base::TimeTicks& submission_time, 174 AutofillMetrics::FormInteractionsUkmLogger* form_interactions_ukm_logger, 175 bool did_show_suggestions, 176 bool observed_submission) const; 177 178 // Log the quality of the heuristics and server predictions for this form 179 // structure, if autocomplete attributes are present on the fields (they are 180 // used as golden truths). 181 void LogQualityMetricsBasedOnAutocomplete( 182 AutofillMetrics::FormInteractionsUkmLogger* form_interactions_ukm_logger) 183 const; 184 185 // Classifies each field in |fields_| based upon its |autocomplete| attribute, 186 // if the attribute is available. The association is stored into the field's 187 // |heuristic_type|. 188 // Fills |has_author_specified_types_| with |true| if the attribute is 189 // available and neither empty nor set to the special values "on" or "off" for 190 // at least one field. 191 // Fills |has_author_specified_sections_| with |true| if the attribute 192 // specifies a section for at least one field. 193 void ParseFieldTypesFromAutocompleteAttributes(); 194 195 // Returns the values that can be filled into the form structure for the 196 // given type. For example, there's no way to fill in a value of "The Moon" 197 // into ADDRESS_HOME_STATE if the form only has a 198 // <select autocomplete="region"> with no "The Moon" option. Returns an 199 // empty set if the form doesn't reference the given type or if all inputs 200 // are accepted (e.g., <input type="text" autocomplete="region">). 201 // All returned values are standardized to upper case. 202 std::set<base::string16> PossibleValues(ServerFieldType type); 203 204 // Rationalize phone number fields in a given section, that is only fill 205 // the fields that are considered composing a first complete phone number. 206 void RationalizePhoneNumbersInSection(std::string section); 207 208 // Overrides server predictions with specific heuristic predictions: 209 // * NAME_LAST_SECOND heuristic predictions are unconditionally used. 210 void OverrideServerPredictionsWithHeuristics(); 211 212 const AutofillField* field(size_t index) const; 213 AutofillField* field(size_t index); 214 size_t field_count() const; 215 216 // Returns the number of fields that are part of the form signature and that 217 // are included in queries to the Autofill server. 218 size_t active_field_count() const; 219 220 // Returns the number of fields that are able to be autofilled. autofill_count()221 size_t autofill_count() const { return autofill_count_; } 222 223 // Used for iterating over the fields. begin()224 std::vector<std::unique_ptr<AutofillField>>::const_iterator begin() const { 225 return fields_.begin(); 226 } end()227 std::vector<std::unique_ptr<AutofillField>>::const_iterator end() const { 228 return fields_.end(); 229 } 230 form_name()231 const base::string16& form_name() const { return form_name_; } 232 id_attribute()233 const base::string16& id_attribute() const { return id_attribute_; } 234 name_attribute()235 const base::string16& name_attribute() const { return name_attribute_; } 236 source_url()237 const GURL& source_url() const { return source_url_; } 238 full_source_url()239 const GURL& full_source_url() const { return full_source_url_; } 240 target_url()241 const GURL& target_url() const { return target_url_; } 242 main_frame_origin()243 const url::Origin& main_frame_origin() const { return main_frame_origin_; } 244 button_titles()245 const ButtonTitleList& button_titles() const { return button_titles_; } 246 has_author_specified_types()247 bool has_author_specified_types() const { 248 return has_author_specified_types_; 249 } 250 has_author_specified_upi_vpa_hint()251 bool has_author_specified_upi_vpa_hint() const { 252 return has_author_specified_upi_vpa_hint_; 253 } 254 has_password_field()255 bool has_password_field() const { return has_password_field_; } 256 is_form_tag()257 bool is_form_tag() const { return is_form_tag_; } 258 set_submission_event(mojom::SubmissionIndicatorEvent submission_event)259 void set_submission_event(mojom::SubmissionIndicatorEvent submission_event) { 260 submission_event_ = submission_event; 261 } 262 set_upload_required(UploadRequired required)263 void set_upload_required(UploadRequired required) { 264 upload_required_ = required; 265 } upload_required()266 UploadRequired upload_required() const { return upload_required_; } 267 form_parsed_timestamp()268 base::TimeTicks form_parsed_timestamp() const { 269 return form_parsed_timestamp_; 270 } 271 all_fields_are_passwords()272 bool all_fields_are_passwords() const { return all_fields_are_passwords_; } 273 form_signature()274 const FormSignature form_signature() const { return form_signature_; } 275 set_form_signature(FormSignature signature)276 void set_form_signature(FormSignature signature) { 277 form_signature_ = signature; 278 } 279 280 // Returns a FormData containing the data this form structure knows about. 281 FormData ToFormData() const; 282 283 // Returns the possible form types. 284 std::set<FormType> GetFormTypes() const; 285 passwords_were_revealed()286 bool passwords_were_revealed() const { return passwords_were_revealed_; } set_passwords_were_revealed(bool passwords_were_revealed)287 void set_passwords_were_revealed(bool passwords_were_revealed) { 288 passwords_were_revealed_ = passwords_were_revealed; 289 } 290 set_password_attributes_vote(const std::pair<PasswordAttribute,bool> & vote)291 void set_password_attributes_vote( 292 const std::pair<PasswordAttribute, bool>& vote) { 293 password_attributes_vote_ = vote; 294 } 295 296 base::Optional<std::pair<PasswordAttribute, bool>> get_password_attributes_vote()297 get_password_attributes_vote() const { 298 return password_attributes_vote_; 299 } 300 set_password_length_vote(const size_t noisified_password_length)301 void set_password_length_vote(const size_t noisified_password_length) { 302 DCHECK(password_attributes_vote_.has_value()) 303 << "|password_length_vote_| doesn't make sense if " 304 "|password_attributes_vote_| has no value."; 305 password_length_vote_ = noisified_password_length; 306 } 307 get_password_length_vote()308 size_t get_password_length_vote() const { 309 DCHECK(password_attributes_vote_.has_value()) 310 << "|password_length_vote_| doesn't make sense if " 311 "|password_attributes_vote_| has no value."; 312 return password_length_vote_; 313 } 314 315 #if defined(UNIT_TEST) get_submission_event_for_testing()316 mojom::SubmissionIndicatorEvent get_submission_event_for_testing() const { 317 return submission_event_; 318 } 319 320 // Identify sections for the |fields_| for testing purposes. identify_sections_for_testing()321 void identify_sections_for_testing() { 322 ParseFieldTypesFromAutocompleteAttributes(); 323 IdentifySections(has_author_specified_sections_); 324 } 325 326 // Set the Overall field type for |fields_[field_index]| to |type| for testing 327 // purposes. set_overall_field_type_for_testing(size_t field_index,ServerFieldType type)328 void set_overall_field_type_for_testing(size_t field_index, 329 ServerFieldType type) { 330 if (field_index < fields_.size() && type > 0 && type < MAX_VALID_FIELD_TYPE) 331 fields_[field_index]->set_heuristic_type(type); 332 } 333 #endif 334 set_password_symbol_vote(int noisified_symbol)335 void set_password_symbol_vote(int noisified_symbol) { 336 DCHECK(password_attributes_vote_.has_value()) 337 << "password_symbol_vote_| doesn't make sense if " 338 "|password_attributes_vote_| has no value."; 339 password_symbol_vote_ = noisified_symbol; 340 } 341 get_password_symbol_vote()342 int get_password_symbol_vote() const { 343 DCHECK(password_attributes_vote_.has_value()) 344 << "|password_symbol_vote_| doesn't make sense if " 345 "|password_attributes_vote_| has no value"; 346 return password_symbol_vote_; 347 } 348 submission_source()349 mojom::SubmissionSource submission_source() const { 350 return submission_source_; 351 } set_submission_source(mojom::SubmissionSource submission_source)352 void set_submission_source(mojom::SubmissionSource submission_source) { 353 submission_source_ = submission_source; 354 } 355 356 // Returns an identifier that is used by the refill logic. Takes the first non 357 // empty of these or returns an empty string: 358 // - Form name 359 // - Name for Autofill of first field 360 base::string16 GetIdentifierForRefill() const; 361 developer_engagement_metrics()362 int developer_engagement_metrics() { return developer_engagement_metrics_; } 363 364 void set_randomized_encoder(std::unique_ptr<RandomizedEncoder> encoder); 365 set_is_rich_query_enabled(bool v)366 void set_is_rich_query_enabled(bool v) { is_rich_query_enabled_ = v; } 367 page_language()368 const std::string& page_language() const { return page_language_; } 369 set_page_language(std::string language)370 void set_page_language(std::string language) { 371 page_language_ = std::move(language); 372 } 373 value_from_dynamic_change_form()374 bool value_from_dynamic_change_form() const { 375 return value_from_dynamic_change_form_; 376 } 377 set_value_from_dynamic_change_form(bool v)378 void set_value_from_dynamic_change_form(bool v) { 379 value_from_dynamic_change_form_ = v; 380 } 381 unique_renderer_id()382 FormRendererId unique_renderer_id() const { return unique_renderer_id_; } 383 ShouldSkipFieldVisibleForTesting(const FormFieldData & field)384 bool ShouldSkipFieldVisibleForTesting(const FormFieldData& field) const { 385 return ShouldSkipField(field); 386 } 387 ProcessQueryResponseForTesting(const AutofillQueryResponse & response,const std::vector<FormStructure * > & forms,const std::vector<FormSignature> & queried_form_signatures,AutofillMetrics::FormInteractionsUkmLogger * form_interactions_ukm_logger)388 static void ProcessQueryResponseForTesting( 389 const AutofillQueryResponse& response, 390 const std::vector<FormStructure*>& forms, 391 const std::vector<FormSignature>& queried_form_signatures, 392 AutofillMetrics::FormInteractionsUkmLogger* 393 form_interactions_ukm_logger) { 394 ProcessQueryResponse(response, forms, queried_form_signatures, 395 form_interactions_ukm_logger); 396 } 397 398 private: 399 friend class AutofillMergeTest; 400 friend class FormStructureTestImpl; 401 friend class ParameterizedFormStructureTest; 402 FRIEND_TEST_ALL_PREFIXES(AutofillDownloadTest, QueryAndUploadTest); 403 FRIEND_TEST_ALL_PREFIXES(FormStructureTestImpl, FindLongestCommonPrefix); 404 FRIEND_TEST_ALL_PREFIXES(FormStructureTestImpl, FindLongestCommonAffixLength); 405 FRIEND_TEST_ALL_PREFIXES(FormStructureTestImpl, IsValidParseableName); 406 FRIEND_TEST_ALL_PREFIXES(ParameterizedFormStructureTest, 407 RationalizePhoneNumber_RunsOncePerSection); 408 409 class SectionedFieldsIndexes { 410 public: 411 SectionedFieldsIndexes(); 412 ~SectionedFieldsIndexes(); 413 LastFieldIndex()414 size_t LastFieldIndex() const { 415 if (sectioned_indexes.empty()) 416 return (size_t)-1; // Shouldn't happen. 417 return sectioned_indexes.back().back(); 418 } 419 AddFieldIndex(const size_t index,bool is_new_section)420 void AddFieldIndex(const size_t index, bool is_new_section) { 421 if (is_new_section || Empty()) { 422 sectioned_indexes.push_back(std::vector<size_t>(1, index)); 423 return; 424 } 425 sectioned_indexes.back().push_back(index); 426 } 427 WalkForwardToTheNextSection()428 void WalkForwardToTheNextSection() { current_section_ptr++; } 429 IsFinished()430 bool IsFinished() const { 431 return current_section_ptr >= sectioned_indexes.size(); 432 } 433 CurrentIndex()434 size_t CurrentIndex() const { return CurrentSection()[0]; } 435 CurrentSection()436 std::vector<size_t> CurrentSection() const { 437 if (current_section_ptr < sectioned_indexes.size()) 438 return sectioned_indexes[current_section_ptr]; 439 return std::vector<size_t>(1, (size_t)-1); // To handle edge cases. 440 } 441 Reset()442 void Reset() { current_section_ptr = 0; } 443 Empty()444 bool Empty() const { return sectioned_indexes.empty(); } 445 446 private: 447 // A vector of sections. Each section is a vector of some of the indexes 448 // that belong to the same section. The sections and indexes are sorted by 449 // their order of appearance on the form. 450 std::vector<std::vector<size_t>> sectioned_indexes; 451 // Points to a vector of indexes that belong to the same section. 452 size_t current_section_ptr = 0; 453 }; 454 455 // Parses the field types from the server query response. |forms| must be the 456 // same as the one passed to EncodeQueryRequest when constructing the query. 457 // |form_interactions_ukm_logger| is used to provide logs to UKM and can be 458 // null in tests. 459 static void ProcessQueryResponse( 460 const AutofillQueryResponse& response, 461 const std::vector<FormStructure*>& forms, 462 const std::vector<FormSignature>& queried_form_signatures, 463 AutofillMetrics::FormInteractionsUkmLogger* form_interactions_ukm_logger); 464 465 FormStructure(FormSignature form_signature, 466 const std::vector<FieldSignature>& field_signatures); 467 468 // A function to fine tune the credit cards related predictions. For example: 469 // lone credit card fields in an otherwise non-credit-card related form is 470 // unlikely to be correct, the function will override that prediction. 471 void RationalizeCreditCardFieldPredictions(); 472 473 // The rationalization is based on the visible fields, but should be applied 474 // to the hidden select fields. This is because hidden 'select' fields are 475 // also autofilled to take care of the synthetic fields. 476 void ApplyRationalizationsToHiddenSelects( 477 size_t field_index, 478 ServerFieldType new_type, 479 AutofillMetrics::FormInteractionsUkmLogger*); 480 481 // Returns true if we can replace server predictions with the heuristics one. 482 bool HeuristicsPredictionsAreApplicable(size_t upper_index, 483 size_t lower_index, 484 ServerFieldType first_type, 485 ServerFieldType second_type); 486 487 // Applies upper type to upper field, and lower type to lower field, and 488 // applies the rationalization also to hidden select fields if necessary. 489 void ApplyRationalizationsToFields( 490 size_t upper_index, 491 size_t lower_index, 492 ServerFieldType upper_type, 493 ServerFieldType lower_type, 494 AutofillMetrics::FormInteractionsUkmLogger*); 495 496 // Returns true if the fields_[index] server type should be rationalized to 497 // ADDRESS_HOME_COUNTRY. 498 bool FieldShouldBeRationalizedToCountry(size_t index); 499 500 // Set fields_[|field_index|] to |new_type| and log this change. 501 void ApplyRationalizationsToFieldAndLog( 502 size_t field_index, 503 ServerFieldType new_type, 504 AutofillMetrics::FormInteractionsUkmLogger* form_interactions_ukm_logger); 505 506 // Two or three fields predicted as the whole address should be address lines 507 // 1, 2 and 3 instead. 508 void RationalizeAddressLineFields( 509 SectionedFieldsIndexes* sections_of_address_indexes, 510 AutofillMetrics::FormInteractionsUkmLogger*); 511 512 // Rationalize state and country interdependently. 513 void RationalizeAddressStateCountry( 514 SectionedFieldsIndexes* sections_of_state_indexes, 515 SectionedFieldsIndexes* sections_of_country_indexes, 516 AutofillMetrics::FormInteractionsUkmLogger*); 517 518 // Tunes the fields with identical predictions. 519 void RationalizeRepeatedFields(AutofillMetrics::FormInteractionsUkmLogger*); 520 521 // Filters out fields that don't meet the relationship ruleset for their type 522 // defined in |type_relationships_rules_|. 523 void RationalizeTypeRelationships(); 524 525 // A helper function to review the predictions and do appropriate adjustments 526 // when it considers necessary. 527 void RationalizeFieldTypePredictions(); 528 529 void EncodeFormForQuery( 530 autofill::AutofillPageQueryRequest::Form* query_form, 531 std::vector<FormSignature>* queried_form_signatures) const; 532 533 void EncodeFormForUpload( 534 autofill::AutofillUploadContents* upload, 535 std::vector<FormSignature>* encoded_signatures) const; 536 537 // Returns true if the form has no fields, or too many. 538 bool IsMalformed() const; 539 540 // Classifies each field in |fields_| into a logical section. 541 // Sections are identified by the heuristic (or by the heuristic and the 542 // autocomplete section attribute, if defined when feature flag 543 // kAutofillUseNewSectioningMethod is enabled) that a logical section should 544 // not include multiple fields of the same autofill type (with some 545 // exceptions, as described in the implementation). Credit card fields also, 546 // have a single separate section from address fields. 547 // If |has_author_specified_sections| is true, only the second pass -- 548 // distinguishing credit card sections from non-credit card ones -- is made. 549 void IdentifySections(bool has_author_specified_sections); 550 551 // Returns true if field should be skipped when talking to Autofill server. 552 bool ShouldSkipField(const FormFieldData& field) const; 553 554 // Further processes the extracted |fields_|. 555 void ProcessExtractedFields(); 556 557 // Tries to set |parseable_name| fields by stripping the given offsets from 558 // both sides of the |name| fields. 559 // Sets |parseable_name| to |name| if the sum of offsets is bigger than 560 // |name|. 561 // Sets all |parseable_name| to |name| without modification and returns 562 // false if a name fails the |IsValidParseableName()| check after stripping. 563 bool SetStrippedParseableNames(size_t offset_left, size_t offset_right); 564 565 // Returns true if |string| is a valid parseable_name. Current criterion 566 // is the |autofill::kParseableNameValidationRe| regex. 567 static bool IsValidParseableName(base::string16 string); 568 569 // Returns the length of the longest common prefix found within |strings| 570 // if |findCommonSuffix| is false. Otherwise returns longest common suffix. 571 static size_t FindLongestCommonAffixLength( 572 const std::vector<base::StringPiece16>& strings, 573 bool findCommonSuffix = false); 574 575 // Returns the longest common prefix found within |strings|. Strings below a 576 // threshold length defined by |kMinCommonNamePrefixLength| are excluded 577 // when performing this check; this is needed because an exceptional 578 // field may be missing a prefix which is otherwise consistently applied. 579 // For instance, a framework may only apply a prefix to those fields 580 // which are bound when POSTing. 581 // 582 // Soon to be replaced by FindLongestCommonPrefixLength 583 static base::string16 FindLongestCommonPrefix( 584 const std::vector<base::string16>& strings); 585 586 // The language detected for this form's page, prior to any translations 587 // performed by Chrome. 588 std::string page_language_; 589 590 // The id attribute of the form. 591 base::string16 id_attribute_; 592 593 // The name attribute of the form. 594 base::string16 name_attribute_; 595 596 // The name of the form. 597 base::string16 form_name_; 598 599 // The titles of form's buttons. 600 ButtonTitleList button_titles_; 601 602 // The type of the event that was taken as an indication that the form has 603 // been successfully submitted. 604 mojom::SubmissionIndicatorEvent submission_event_ = 605 mojom::SubmissionIndicatorEvent::NONE; 606 607 // The source URL (excluding the query parameters and fragment identifiers). 608 GURL source_url_; 609 610 // The full source URL including query parameters and fragment identifiers. 611 GURL full_source_url_; 612 613 // The target URL. 614 GURL target_url_; 615 616 // The origin of the main frame of this form. 617 url::Origin main_frame_origin_; 618 619 // The number of fields able to be auto-filled. 620 size_t autofill_count_ = 0; 621 622 // A vector of all the input fields in the form. 623 std::vector<std::unique_ptr<AutofillField>> fields_; 624 625 // The number of fields that are part of the form signature and that are 626 // included in queries to the Autofill server. 627 size_t active_field_count_ = 0; 628 629 // Whether the server expects us to always upload, never upload, or default 630 // to the stored upload rates. 631 UploadRequired upload_required_ = USE_UPLOAD_RATES; 632 633 // Whether the form includes any field types explicitly specified by the site 634 // author, via the |autocompletetype| attribute. 635 bool has_author_specified_types_ = false; 636 637 // Whether the form includes any sections explicitly specified by the site 638 // author, via the autocomplete attribute. 639 bool has_author_specified_sections_ = false; 640 641 // Whether the form includes a field that explicitly sets it autocomplete 642 // type to "upi-vpa". 643 bool has_author_specified_upi_vpa_hint_ = false; 644 645 // Whether the form was parsed for autocomplete attribute, thus assigning 646 // the real values of |has_author_specified_types_| and 647 // |has_author_specified_sections_|. 648 bool was_parsed_for_autocomplete_attributes_ = false; 649 650 // True if the form contains at least one password field. 651 bool has_password_field_ = false; 652 653 // True if the form is a <form>. 654 bool is_form_tag_ = true; 655 656 // True if the form is made of unowned fields (i.e., not within a <form> tag) 657 // in what appears to be a checkout flow. This attribute is only calculated 658 // and used if features::kAutofillRestrictUnownedFieldsToFormlessCheckout is 659 // enabled, to prevent heuristics from running on formless non-checkout. 660 bool is_formless_checkout_ = false; 661 662 // True if all form fields are password fields. 663 bool all_fields_are_passwords_ = false; 664 665 // The unique signature for this form, composed of the target url domain, 666 // the form name, and the form field names in a 64-bit hash. 667 FormSignature form_signature_; 668 669 // The timestamp (not wallclock time) when this form was initially parsed. 670 base::TimeTicks form_parsed_timestamp_; 671 672 // If phone number rationalization has been performed for a given section. 673 std::map<std::string, bool> phone_rationalized_; 674 675 // True iff the form is a password form and the user has seen the password 676 // value before accepting the prompt to save. Used for crowdsourcing. 677 bool passwords_were_revealed_ = false; 678 679 // The vote about password attributes (e.g. whether the password has a numeric 680 // character). 681 base::Optional<std::pair<PasswordAttribute, bool>> password_attributes_vote_; 682 683 // If |password_attribute_vote_| contains (kHasSpecialSymbol, true), this 684 // field contains nosified information about a special symbol in a 685 // user-created password stored as ASCII code. The default value of 0 686 // indicates that no symbol was set. 687 int password_symbol_vote_ = 0; 688 689 // Noisified password length for crowdsourcing. If |password_attributes_vote_| 690 // has no value, |password_length_vote_| should be ignored. 691 size_t password_length_vote_; 692 693 // Used to record whether developer has used autocomplete markup or 694 // UPI-VPA hints, This is a bitmask of DeveloperEngagementMetric and set in 695 // DetermineHeuristicTypes(). 696 int developer_engagement_metrics_ = 0; 697 698 mojom::SubmissionSource submission_source_ = mojom::SubmissionSource::NONE; 699 700 // The randomized encoder to use to encode form metadata during upload. 701 // If this is nullptr, no randomized metadata will be sent. 702 std::unique_ptr<RandomizedEncoder> randomized_encoder_; 703 704 // True iff queries encoded from this form structure should include rich 705 // form/field metadata. 706 bool is_rich_query_enabled_ = false; 707 708 bool value_from_dynamic_change_form_ = false; 709 710 FormRendererId unique_renderer_id_; 711 712 DISALLOW_COPY_AND_ASSIGN(FormStructure); 713 }; 714 715 LogBuffer& operator<<(LogBuffer& buffer, const FormStructure& form); 716 std::ostream& operator<<(std::ostream& buffer, const FormStructure& form); 717 718 } // namespace autofill 719 720 #endif // COMPONENTS_AUTOFILL_CORE_BROWSER_FORM_STRUCTURE_H_ 721