Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(64)

Side by Side Diff: components/autofill/core/browser/form_structure.cc

Issue 659793005: [Password Generation] Always query password forms via Autofill (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: More tests Created 6 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "components/autofill/core/browser/form_structure.h" 5 #include "components/autofill/core/browser/form_structure.h"
6 6
7 #include <utility> 7 #include <utility>
8 8
9 #include "base/basictypes.h" 9 #include "base/basictypes.h"
10 #include "base/command_line.h" 10 #include "base/command_line.h"
(...skipping 334 matching lines...) Expand 10 before | Expand all | Expand 10 after
345 345
346 } // namespace 346 } // namespace
347 347
348 FormStructure::FormStructure(const FormData& form) 348 FormStructure::FormStructure(const FormData& form)
349 : form_name_(form.name), 349 : form_name_(form.name),
350 source_url_(form.origin), 350 source_url_(form.origin),
351 target_url_(form.action), 351 target_url_(form.action),
352 autofill_count_(0), 352 autofill_count_(0),
353 active_field_count_(0), 353 active_field_count_(0),
354 upload_required_(USE_UPLOAD_RATES), 354 upload_required_(USE_UPLOAD_RATES),
355 has_author_specified_types_(false) { 355 has_author_specified_types_(false),
356 has_password_field_(false) {
356 // Copy the form fields. 357 // Copy the form fields.
357 std::map<base::string16, size_t> unique_names; 358 std::map<base::string16, size_t> unique_names;
358 for (std::vector<FormFieldData>::const_iterator field = 359 for (std::vector<FormFieldData>::const_iterator field =
359 form.fields.begin(); 360 form.fields.begin();
360 field != form.fields.end(); ++field) { 361 field != form.fields.end(); ++field) {
361 if (!ShouldSkipField(*field)) { 362 if (!ShouldSkipField(*field)) {
362 // Add all supported form fields (including with empty names) to the 363 // Add all supported form fields (including with empty names) to the
363 // signature. This is a requirement for Autofill servers. 364 // signature. This is a requirement for Autofill servers.
364 form_signature_field_names_.append("&"); 365 form_signature_field_names_.append("&");
365 form_signature_field_names_.append(StripDigitsIfRequired(field->name)); 366 form_signature_field_names_.append(StripDigitsIfRequired(field->name));
366 367
367 ++active_field_count_; 368 ++active_field_count_;
368 } 369 }
369 370
371 if (field->form_control_type == "password")
372 has_password_field_ = true;
373
370 // Generate a unique name for this field by appending a counter to the name. 374 // Generate a unique name for this field by appending a counter to the name.
371 // Make sure to prepend the counter with a non-numeric digit so that we are 375 // Make sure to prepend the counter with a non-numeric digit so that we are
372 // guaranteed to avoid collisions. 376 // guaranteed to avoid collisions.
373 if (!unique_names.count(field->name)) 377 if (!unique_names.count(field->name))
374 unique_names[field->name] = 1; 378 unique_names[field->name] = 1;
375 else 379 else
376 ++unique_names[field->name]; 380 ++unique_names[field->name];
377 base::string16 unique_name = field->name + base::ASCIIToUTF16("_") + 381 base::string16 unique_name = field->name + base::ASCIIToUTF16("_") +
378 base::IntToString16(unique_names[field->name]); 382 base::IntToString16(unique_names[field->name]);
379 fields_.push_back(new AutofillField(*field, unique_name)); 383 fields_.push_back(new AutofillField(*field, unique_name));
(...skipping 173 matching lines...) Expand 10 before | Expand all | Expand 10 after
553 &upload_required); 557 &upload_required);
554 buzz::XmlParser parser(&parse_handler); 558 buzz::XmlParser parser(&parse_handler);
555 parser.Parse(response_xml.c_str(), response_xml.length(), true); 559 parser.Parse(response_xml.c_str(), response_xml.length(), true);
556 if (!parse_handler.succeeded()) 560 if (!parse_handler.succeeded())
557 return; 561 return;
558 562
559 metric_logger.LogServerQueryMetric(AutofillMetrics::QUERY_RESPONSE_PARSED); 563 metric_logger.LogServerQueryMetric(AutofillMetrics::QUERY_RESPONSE_PARSED);
560 564
561 bool heuristics_detected_fillable_field = false; 565 bool heuristics_detected_fillable_field = false;
562 bool query_response_overrode_heuristics = false; 566 bool query_response_overrode_heuristics = false;
567 bool non_password_field_processed = false;
563 568
564 // Copy the field types into the actual form. 569 // Copy the field types into the actual form.
565 std::vector<AutofillServerFieldInfo>::iterator current_info = 570 std::vector<AutofillServerFieldInfo>::iterator current_info =
566 field_infos.begin(); 571 field_infos.begin();
567 for (std::vector<FormStructure*>::const_iterator iter = forms.begin(); 572 for (std::vector<FormStructure*>::const_iterator iter = forms.begin();
568 iter != forms.end(); ++iter) { 573 iter != forms.end(); ++iter) {
569 FormStructure* form = *iter; 574 FormStructure* form = *iter;
570 form->upload_required_ = upload_required; 575 form->upload_required_ = upload_required;
571 576
572 for (std::vector<AutofillField*>::iterator field = form->fields_.begin(); 577 for (std::vector<AutofillField*>::iterator field = form->fields_.begin();
573 field != form->fields_.end(); ++field) { 578 field != form->fields_.end(); ++field) {
574 if (form->ShouldSkipField(**field)) 579 if (form->ShouldSkipField(**field))
575 continue; 580 continue;
576 581
577 // In some cases *successful* response does not return all the fields. 582 // In some cases *successful* response does not return all the fields.
578 // Quit the update of the types then. 583 // Quit the update of the types then.
579 if (current_info == field_infos.end()) 584 if (current_info == field_infos.end())
580 break; 585 break;
581 586
582 // UNKNOWN_TYPE is reserved for use by the client. 587 if (form->ShouldSkipProcessingNonPasswordFields()) {
583 DCHECK_NE(current_info->field_type, UNKNOWN_TYPE); 588 // Heuristic values can be ignored for password fields as Autofill
589 // doesn't handle them. UMA stats can also be skipped in that case.
590 if ((*field)->Type().group() == PASSWORD_FIELD)
591 (*field)->set_server_type(current_info->field_type);
592 } else {
593 non_password_field_processed = true;
Ilya Sherman 2014/10/24 01:24:45 Wait, where do you check that a non-password field
Garrett Casto 2014/10/24 21:13:09 I agree that the name doesn't do a great job of ex
584 594
585 ServerFieldType heuristic_type = (*field)->heuristic_type(); 595 // UNKNOWN_TYPE is reserved for use by the client.
586 if (heuristic_type != UNKNOWN_TYPE) 596 DCHECK_NE(current_info->field_type, UNKNOWN_TYPE);
587 heuristics_detected_fillable_field = true;
588 597
589 (*field)->set_server_type(current_info->field_type); 598 ServerFieldType heuristic_type = (*field)->heuristic_type();
590 if (heuristic_type != (*field)->Type().GetStorableType()) 599 if (heuristic_type != UNKNOWN_TYPE)
591 query_response_overrode_heuristics = true; 600 heuristics_detected_fillable_field = true;
592 601
593 // Copy default value into the field if available. 602 (*field)->set_server_type(current_info->field_type);
594 if (!current_info->default_value.empty()) 603 if (heuristic_type != (*field)->Type().GetStorableType())
595 (*field)->set_default_value(current_info->default_value); 604 query_response_overrode_heuristics = true;
605
606 // Copy default value into the field if available.
607 if (!current_info->default_value.empty())
608 (*field)->set_default_value(current_info->default_value);
609 }
596 610
597 ++current_info; 611 ++current_info;
598 } 612 }
599 613
600 form->UpdateAutofillCount(); 614 form->UpdateAutofillCount();
601 form->IdentifySections(false); 615 form->IdentifySections(false);
602 } 616 }
603 617
604 AutofillMetrics::ServerQueryMetric metric; 618 // Only log metrics if response was for non-password fields, since password
605 if (query_response_overrode_heuristics) { 619 // fields don't have local heuristics to measure.
606 if (heuristics_detected_fillable_field) { 620 if (non_password_field_processed) {
607 metric = AutofillMetrics::QUERY_RESPONSE_OVERRODE_LOCAL_HEURISTICS; 621 AutofillMetrics::ServerQueryMetric metric;
622 if (query_response_overrode_heuristics) {
623 if (heuristics_detected_fillable_field) {
624 metric = AutofillMetrics::QUERY_RESPONSE_OVERRODE_LOCAL_HEURISTICS;
625 } else {
626 metric = AutofillMetrics::QUERY_RESPONSE_WITH_NO_LOCAL_HEURISTICS;
627 }
608 } else { 628 } else {
609 metric = AutofillMetrics::QUERY_RESPONSE_WITH_NO_LOCAL_HEURISTICS; 629 metric = AutofillMetrics::QUERY_RESPONSE_MATCHED_LOCAL_HEURISTICS;
610 } 630 }
611 } else { 631 metric_logger.LogServerQueryMetric(metric);
612 metric = AutofillMetrics::QUERY_RESPONSE_MATCHED_LOCAL_HEURISTICS;
613 } 632 }
614 metric_logger.LogServerQueryMetric(metric);
615 } 633 }
616 634
617 // static 635 // static
618 void FormStructure::GetFieldTypePredictions( 636 void FormStructure::GetFieldTypePredictions(
619 const std::vector<FormStructure*>& form_structures, 637 const std::vector<FormStructure*>& form_structures,
620 std::vector<FormDataPredictions>* forms) { 638 std::vector<FormDataPredictions>* forms) {
621 forms->clear(); 639 forms->clear();
622 forms->reserve(form_structures.size()); 640 forms->reserve(form_structures.size());
623 for (size_t i = 0; i < form_structures.size(); ++i) { 641 for (size_t i = 0; i < form_structures.size(); ++i) {
624 FormStructure* form_structure = form_structures[i]; 642 FormStructure* form_structure = form_structures[i];
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after
699 bool has_text_field = false; 717 bool has_text_field = false;
700 for (std::vector<AutofillField*>::const_iterator it = begin(); 718 for (std::vector<AutofillField*>::const_iterator it = begin();
701 it != end() && !has_text_field; ++it) { 719 it != end() && !has_text_field; ++it) {
702 has_text_field |= (*it)->form_control_type != "select-one"; 720 has_text_field |= (*it)->form_control_type != "select-one";
703 } 721 }
704 722
705 return has_text_field; 723 return has_text_field;
706 } 724 }
707 725
708 bool FormStructure::ShouldBeCrowdsourced() const { 726 bool FormStructure::ShouldBeCrowdsourced() const {
709 return !has_author_specified_types_ && ShouldBeParsed(); 727 return (has_password_field_ || !has_author_specified_types_) &&
728 ShouldBeParsed();
729 }
730
731 bool FormStructure::ShouldSkipProcessingNonPasswordFields() const {
Ilya Sherman 2014/10/24 01:24:45 This method name is pretty long and, IMO, still a
Garrett Casto 2014/10/24 21:13:09 Done.
732 return has_password_field_ && has_author_specified_types_;
710 } 733 }
711 734
712 void FormStructure::UpdateFromCache(const FormStructure& cached_form) { 735 void FormStructure::UpdateFromCache(const FormStructure& cached_form) {
713 // Map from field signatures to cached fields. 736 // Map from field signatures to cached fields.
714 std::map<std::string, const AutofillField*> cached_fields; 737 std::map<std::string, const AutofillField*> cached_fields;
715 for (size_t i = 0; i < cached_form.field_count(); ++i) { 738 for (size_t i = 0; i < cached_form.field_count(); ++i) {
716 const AutofillField* field = cached_form.field(i); 739 const AutofillField* field = cached_form.field(i);
717 cached_fields[field->FieldSignature()] = field; 740 cached_fields[field->FieldSignature()] = field;
718 } 741 }
719 742
(...skipping 508 matching lines...) Expand 10 before | Expand all | Expand 10 after
1228 field != fields_.end(); ++field) { 1251 field != fields_.end(); ++field) {
1229 FieldTypeGroup field_type_group = (*field)->Type().group(); 1252 FieldTypeGroup field_type_group = (*field)->Type().group();
1230 if (field_type_group == CREDIT_CARD) 1253 if (field_type_group == CREDIT_CARD)
1231 (*field)->set_section((*field)->section() + "-cc"); 1254 (*field)->set_section((*field)->section() + "-cc");
1232 else 1255 else
1233 (*field)->set_section((*field)->section() + "-default"); 1256 (*field)->set_section((*field)->section() + "-default");
1234 } 1257 }
1235 } 1258 }
1236 1259
1237 } // namespace autofill 1260 } // namespace autofill
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698