OLD | NEW |
---|---|
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_field.h" | 5 #include "components/autofill/core/browser/form_field.h" |
6 | 6 |
7 #include <stddef.h> | 7 #include <stddef.h> |
8 #include <string> | 8 #include <string> |
9 #include <utility> | 9 #include <utility> |
10 | 10 |
(...skipping 22 matching lines...) Expand all Loading... | |
33 // Ignore fields marked as presentational. See | 33 // Ignore fields marked as presentational. See |
34 // http://www.w3.org/TR/wai-aria/roles#presentation | 34 // http://www.w3.org/TR/wai-aria/roles#presentation |
35 return field->is_checkable || | 35 return field->is_checkable || |
36 field->role == FormFieldData::ROLE_ATTRIBUTE_PRESENTATION; | 36 field->role == FormFieldData::ROLE_ATTRIBUTE_PRESENTATION; |
37 } | 37 } |
38 | 38 |
39 } // namespace | 39 } // namespace |
40 | 40 |
41 // static | 41 // static |
42 void FormField::ParseFormFields(const std::vector<AutofillField*>& fields, | 42 void FormField::ParseFormFields(const std::vector<AutofillField*>& fields, |
43 bool is_unowned_form, | |
43 ServerFieldTypeMap* map) { | 44 ServerFieldTypeMap* map) { |
44 // Set up a working copy of the fields to be processed. | 45 // Set up a working copy of the fields to be processed. |
45 std::vector<AutofillField*> remaining_fields(fields.size()); | 46 std::vector<AutofillField*> remaining_fields(fields.size()); |
46 std::copy(fields.begin(), fields.end(), remaining_fields.begin()); | 47 std::copy(fields.begin(), fields.end(), remaining_fields.begin()); |
47 | 48 |
48 remaining_fields.erase( | 49 remaining_fields.erase( |
49 std::remove_if(remaining_fields.begin(), remaining_fields.end(), | 50 std::remove_if(remaining_fields.begin(), remaining_fields.end(), |
50 ShouldBeIgnored), | 51 ShouldBeIgnored), |
51 remaining_fields.end()); | 52 remaining_fields.end()); |
52 | 53 |
54 ServerFieldTypeMap saved_map = *map; | |
55 size_t email_count = 0; | |
56 size_t count = 0; | |
57 | |
53 // Email pass. | 58 // Email pass. |
54 ParseFormFieldsPass(EmailField::Parse, &remaining_fields, map); | 59 email_count += ParseFormFieldsPass(EmailField::Parse, &remaining_fields, map); |
60 count += email_count; | |
55 | 61 |
56 // Phone pass. | 62 // Phone pass. |
57 ParseFormFieldsPass(PhoneField::Parse, &remaining_fields, map); | 63 count += ParseFormFieldsPass(PhoneField::Parse, &remaining_fields, map); |
58 | 64 |
59 // Address pass. | 65 // Address pass. |
60 ParseFormFieldsPass(AddressField::Parse, &remaining_fields, map); | 66 count += ParseFormFieldsPass(AddressField::Parse, &remaining_fields, map); |
61 | 67 |
62 // Credit card pass. | 68 // Credit card pass. |
63 ParseFormFieldsPass(CreditCardField::Parse, &remaining_fields, map); | 69 count += ParseFormFieldsPass(CreditCardField::Parse, &remaining_fields, map); |
64 | 70 |
65 // Name pass. | 71 // Name pass. |
66 ParseFormFieldsPass(NameField::Parse, &remaining_fields, map); | 72 count += ParseFormFieldsPass(NameField::Parse, &remaining_fields, map); |
73 | |
74 // Do not autofill a form if there are less than 3 recognized fields. | |
75 // Otherwise it is very easy to have false positives. http://crbug.com/447332 | |
76 size_t kThreshold = 3; | |
77 bool ignore_parsing = (count < kThreshold); | |
Evan Stade
2015/01/21 22:52:49
nit: no parens
| |
78 // For <form> tags, make an exception for email fields, which are commonly the | |
79 // only recognized field on account registration sites. | |
80 if (!is_unowned_form) | |
Evan Stade
2015/01/21 22:52:49
&= is a confusing operator. How about:
bool shoul
Lei Zhang
2015/01/22 08:07:37
Done.
| |
81 ignore_parsing &= (email_count == 0); | |
82 if (ignore_parsing) | |
83 *map = saved_map; | |
67 } | 84 } |
68 | 85 |
69 // static | 86 // static |
70 bool FormField::ParseField(AutofillScanner* scanner, | 87 bool FormField::ParseField(AutofillScanner* scanner, |
71 const base::string16& pattern, | 88 const base::string16& pattern, |
72 AutofillField** match) { | 89 AutofillField** match) { |
73 return ParseFieldSpecifics(scanner, pattern, MATCH_DEFAULT, match); | 90 return ParseFieldSpecifics(scanner, pattern, MATCH_DEFAULT, match); |
74 } | 91 } |
75 | 92 |
76 // static | 93 // static |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
123 } | 140 } |
124 | 141 |
125 return false; | 142 return false; |
126 } | 143 } |
127 | 144 |
128 // static | 145 // static |
129 bool FormField::Match(const AutofillField* field, | 146 bool FormField::Match(const AutofillField* field, |
130 const base::string16& pattern, | 147 const base::string16& pattern, |
131 int match_type) { | 148 int match_type) { |
132 if ((match_type & FormField::MATCH_LABEL) && | 149 if ((match_type & FormField::MATCH_LABEL) && |
133 autofill::MatchesPattern(field->label, pattern)) { | 150 MatchesPattern(field->label, pattern)) { |
134 return true; | 151 return true; |
135 } | 152 } |
136 | 153 |
137 if ((match_type & FormField::MATCH_NAME) && | 154 if ((match_type & FormField::MATCH_NAME) && |
138 autofill::MatchesPattern(field->name, pattern)) { | 155 MatchesPattern(field->name, pattern)) { |
139 return true; | 156 return true; |
140 } | 157 } |
141 | 158 |
142 if ((match_type & FormField::MATCH_VALUE) && | 159 if ((match_type & FormField::MATCH_VALUE) && |
143 autofill::MatchesPattern(field->value, pattern)) { | 160 MatchesPattern(field->value, pattern)) { |
144 return true; | 161 return true; |
145 } | 162 } |
146 | 163 |
147 return false; | 164 return false; |
148 } | 165 } |
149 | 166 |
150 // static | 167 // static |
151 void FormField::ParseFormFieldsPass(ParseFunction parse, | 168 size_t FormField::ParseFormFieldsPass(ParseFunction parse, |
152 std::vector<AutofillField*>* fields, | 169 std::vector<AutofillField*>* fields, |
153 ServerFieldTypeMap* map) { | 170 ServerFieldTypeMap* map) { |
154 // Store unmatched fields for further processing by the caller. | 171 // Store unmatched fields for further processing by the caller. |
155 std::vector<AutofillField*> remaining_fields; | 172 std::vector<AutofillField*> remaining_fields; |
156 | 173 |
174 ScopedVector<FormField> form_fields; | |
175 size_t field_count = 0; | |
157 AutofillScanner scanner(*fields); | 176 AutofillScanner scanner(*fields); |
158 while (!scanner.IsEnd()) { | 177 while (!scanner.IsEnd()) { |
159 scoped_ptr<FormField> form_field(parse(&scanner)); | 178 scoped_ptr<FormField> form_field(parse(&scanner)); |
160 if (!form_field) { | 179 if (!form_field) { |
161 remaining_fields.push_back(scanner.Cursor()); | 180 remaining_fields.push_back(scanner.Cursor()); |
162 scanner.Advance(); | 181 scanner.Advance(); |
163 continue; | 182 continue; |
164 } | 183 } |
165 | 184 |
185 field_count += form_field->FieldCount(); | |
Evan Stade
2015/01/21 22:52:49
instead of adding this function, couldn't you more
Lei Zhang
2015/01/22 08:07:37
Isn't it possible for functions like AddressField:
Evan Stade
2015/01/22 17:17:05
perhaps... but you could check the size of |map| a
Lei Zhang
2015/01/22 23:14:15
Sounds better, done.
| |
186 form_fields.push_back(form_field.release()); | |
187 } | |
188 | |
189 for (const auto& form_field : form_fields) { | |
Evan Stade
2015/01/22 17:17:05
why is this a separate loop now?
also, I think au
Lei Zhang
2015/01/22 23:14:15
I was experimenting with different ways to count f
| |
166 // Add entries into the map for each field type found in |form_field|. | 190 // Add entries into the map for each field type found in |form_field|. |
167 bool ok = form_field->ClassifyField(map); | 191 bool ok = form_field->ClassifyField(map); |
168 DCHECK(ok); | 192 DCHECK(ok); |
169 } | 193 } |
170 | 194 |
171 std::swap(*fields, remaining_fields); | 195 std::swap(*fields, remaining_fields); |
196 return field_count; | |
172 } | 197 } |
173 | 198 |
174 bool FormField::MatchesFormControlType(const std::string& type, | 199 bool FormField::MatchesFormControlType(const std::string& type, |
175 int match_type) { | 200 int match_type) { |
176 if ((match_type & MATCH_TEXT) && type == "text") | 201 if ((match_type & MATCH_TEXT) && type == "text") |
177 return true; | 202 return true; |
178 | 203 |
179 if ((match_type & MATCH_EMAIL) && type == "email") | 204 if ((match_type & MATCH_EMAIL) && type == "email") |
180 return true; | 205 return true; |
181 | 206 |
182 if ((match_type & MATCH_TELEPHONE) && type == "tel") | 207 if ((match_type & MATCH_TELEPHONE) && type == "tel") |
183 return true; | 208 return true; |
184 | 209 |
185 if ((match_type & MATCH_SELECT) && type == "select-one") | 210 if ((match_type & MATCH_SELECT) && type == "select-one") |
186 return true; | 211 return true; |
187 | 212 |
188 if ((match_type & MATCH_TEXT_AREA) && type == "textarea") | 213 if ((match_type & MATCH_TEXT_AREA) && type == "textarea") |
189 return true; | 214 return true; |
190 | 215 |
191 if ((match_type & MATCH_PASSWORD) && type == "password") | 216 if ((match_type & MATCH_PASSWORD) && type == "password") |
192 return true; | 217 return true; |
193 | 218 |
194 return false; | 219 return false; |
195 } | 220 } |
196 | 221 |
197 } // namespace autofill | 222 } // namespace autofill |
OLD | NEW |