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.
5 #include "components/autofill/core/browser/form_structure.h"
7 #include "base/command_line.h"
8 #include "base/memory/scoped_ptr.h"
9 #include "base/metrics/field_trial.h"
10 #include "base/strings/string_util.h"
11 #include "base/strings/utf_string_conversions.h"
12 #include "components/autofill/core/common/autofill_switches.h"
13 #include "components/autofill/core/common/form_data.h"
14 #include "components/autofill/core/common/form_field_data.h"
15 #include "components/rappor/test_rappor_service.h"
16 #include "components/variations/entropy_provider.h"
17 #include "testing/gtest/include/gtest/gtest.h"
20 using base::ASCIIToUTF16
;
21 using rappor::TestRapporService
;
27 std::ostream
& operator<<(std::ostream
& os
, const FormData
& form
) {
28 os
<< base::UTF16ToUTF8(form
.name
)
35 for (std::vector
<FormFieldData
>::const_iterator iter
=
37 iter
!= form
.fields
.end(); ++iter
) {
45 } // namespace content
47 class FormStructureTest
: public testing::Test
{
49 static std::string
Hash64Bit(const std::string
& str
) {
50 return FormStructure::Hash64Bit(str
);
53 void SetUp() override
{
54 // By default this trial is enabled on tests.
55 EnableAutofillMetadataFieldTrial();
59 void DisableAutofillMetadataFieldTrial() {
60 field_trial_list_
.reset(NULL
);
64 void EnableAutofillMetadataFieldTrial() {
65 // Clear the existing |field_trial_list_| to avoid firing a DCHECK.
66 field_trial_list_
.reset(NULL
);
67 field_trial_list_
.reset(
68 new base::FieldTrialList(new metrics::SHA1EntropyProvider("foo")));
69 field_trial_
= base::FieldTrialList::CreateFieldTrial(
70 "AutofillFieldMetadata", "Enabled");
71 field_trial_
->group();
74 scoped_ptr
<base::FieldTrialList
> field_trial_list_
;
75 scoped_refptr
<base::FieldTrial
> field_trial_
;
78 TEST_F(FormStructureTest
, FieldCount
) {
79 scoped_ptr
<FormStructure
> form_structure
;
83 field
.label
= ASCIIToUTF16("username");
84 field
.name
= ASCIIToUTF16("username");
85 field
.form_control_type
= "text";
86 form
.fields
.push_back(field
);
88 field
.label
= ASCIIToUTF16("password");
89 field
.name
= ASCIIToUTF16("password");
90 field
.form_control_type
= "password";
91 form
.fields
.push_back(field
);
93 field
.label
= base::string16();
94 field
.name
= ASCIIToUTF16("Submit");
95 field
.form_control_type
= "submit";
96 form
.fields
.push_back(field
);
98 field
.label
= ASCIIToUTF16("address1");
99 field
.name
= ASCIIToUTF16("address1");
100 field
.form_control_type
= "text";
101 field
.should_autocomplete
= false;
102 form
.fields
.push_back(field
);
104 // The render process sends all fields to browser including fields with
106 form_structure
.reset(new FormStructure(form
));
107 EXPECT_EQ(4U, form_structure
->field_count());
110 TEST_F(FormStructureTest
, AutofillCount
) {
111 scoped_ptr
<FormStructure
> form_structure
;
115 field
.label
= ASCIIToUTF16("username");
116 field
.name
= ASCIIToUTF16("username");
117 field
.form_control_type
= "text";
118 form
.fields
.push_back(field
);
120 field
.label
= ASCIIToUTF16("password");
121 field
.name
= ASCIIToUTF16("password");
122 field
.form_control_type
= "password";
123 form
.fields
.push_back(field
);
125 field
.label
= ASCIIToUTF16("email");
126 field
.name
= ASCIIToUTF16("email");
127 field
.form_control_type
= "text";
128 form
.fields
.push_back(field
);
130 field
.label
= ASCIIToUTF16("city");
131 field
.name
= ASCIIToUTF16("city");
132 field
.form_control_type
= "text";
133 form
.fields
.push_back(field
);
135 field
.label
= ASCIIToUTF16("state");
136 field
.name
= ASCIIToUTF16("state");
137 field
.form_control_type
= "select-one";
138 form
.fields
.push_back(field
);
140 field
.label
= base::string16();
141 field
.name
= ASCIIToUTF16("Submit");
142 field
.form_control_type
= "submit";
143 form
.fields
.push_back(field
);
145 // Only text and select fields that are heuristically matched are counted.
146 form_structure
.reset(new FormStructure(form
));
147 form_structure
->DetermineHeuristicTypes();
148 EXPECT_EQ(3U, form_structure
->autofill_count());
150 // Add a field with should_autocomplete=false. This should not be considered a
152 field
.label
= ASCIIToUTF16("address1");
153 field
.name
= ASCIIToUTF16("address1");
154 field
.form_control_type
= "text";
155 field
.should_autocomplete
= false;
156 form
.fields
.push_back(field
);
158 form_structure
.reset(new FormStructure(form
));
159 form_structure
->DetermineHeuristicTypes();
160 EXPECT_EQ(4U, form_structure
->autofill_count());
163 TEST_F(FormStructureTest
, SourceURL
) {
165 form
.origin
= GURL("http://www.foo.com/");
166 FormStructure
form_structure(form
);
168 EXPECT_EQ(form
.origin
, form_structure
.source_url());
171 TEST_F(FormStructureTest
, IsAutofillable
) {
172 scoped_ptr
<FormStructure
> form_structure
;
175 // We need at least three text fields to be auto-fillable.
178 field
.label
= ASCIIToUTF16("username");
179 field
.name
= ASCIIToUTF16("username");
180 field
.form_control_type
= "text";
181 form
.fields
.push_back(field
);
183 field
.label
= ASCIIToUTF16("password");
184 field
.name
= ASCIIToUTF16("password");
185 field
.form_control_type
= "password";
186 form
.fields
.push_back(field
);
188 field
.label
= base::string16();
189 field
.name
= ASCIIToUTF16("Submit");
190 field
.form_control_type
= "submit";
191 form
.fields
.push_back(field
);
193 form_structure
.reset(new FormStructure(form
));
194 form_structure
->DetermineHeuristicTypes();
195 EXPECT_FALSE(form_structure
->IsAutofillable());
197 // We now have three text fields, but only two auto-fillable fields.
198 field
.label
= ASCIIToUTF16("First Name");
199 field
.name
= ASCIIToUTF16("firstname");
200 field
.form_control_type
= "text";
201 form
.fields
.push_back(field
);
203 field
.label
= ASCIIToUTF16("Last Name");
204 field
.name
= ASCIIToUTF16("lastname");
205 field
.form_control_type
= "text";
206 form
.fields
.push_back(field
);
208 form_structure
.reset(new FormStructure(form
));
209 form_structure
->DetermineHeuristicTypes();
210 EXPECT_FALSE(form_structure
->IsAutofillable());
212 // We now have three auto-fillable fields.
213 field
.label
= ASCIIToUTF16("Email");
214 field
.name
= ASCIIToUTF16("email");
215 field
.form_control_type
= "email";
216 form
.fields
.push_back(field
);
218 form_structure
.reset(new FormStructure(form
));
219 form_structure
->DetermineHeuristicTypes();
220 EXPECT_TRUE(form_structure
->IsAutofillable());
222 // The target cannot include http(s)://*/search...
223 form
.action
= GURL("http://google.com/search?q=hello");
224 form_structure
.reset(new FormStructure(form
));
225 form_structure
->DetermineHeuristicTypes();
226 EXPECT_FALSE(form_structure
->IsAutofillable());
228 // But search can be in the URL.
229 form
.action
= GURL("http://search.com/?q=hello");
230 form_structure
.reset(new FormStructure(form
));
231 form_structure
->DetermineHeuristicTypes();
232 EXPECT_TRUE(form_structure
->IsAutofillable());
235 TEST_F(FormStructureTest
, ShouldBeParsed
) {
236 scoped_ptr
<FormStructure
> form_structure
;
239 // We need at least three text fields to be parseable.
241 field
.label
= ASCIIToUTF16("username");
242 field
.name
= ASCIIToUTF16("username");
243 field
.form_control_type
= "text";
244 form
.fields
.push_back(field
);
246 FormFieldData checkable_field
;
247 checkable_field
.is_checkable
= true;
248 checkable_field
.name
= ASCIIToUTF16("radiobtn");
249 checkable_field
.form_control_type
= "radio";
250 form
.fields
.push_back(checkable_field
);
252 checkable_field
.name
= ASCIIToUTF16("checkbox");
253 checkable_field
.form_control_type
= "checkbox";
254 form
.fields
.push_back(checkable_field
);
256 // We have only one text field, should not be parsed.
257 form_structure
.reset(new FormStructure(form
));
258 EXPECT_FALSE(form_structure
->ShouldBeParsed());
260 // We now have three text fields, though only two are auto-fillable.
261 field
.label
= ASCIIToUTF16("First Name");
262 field
.name
= ASCIIToUTF16("firstname");
263 field
.form_control_type
= "text";
264 form
.fields
.push_back(field
);
266 field
.label
= ASCIIToUTF16("Last Name");
267 field
.name
= ASCIIToUTF16("lastname");
268 field
.form_control_type
= "text";
269 form
.fields
.push_back(field
);
271 form_structure
.reset(new FormStructure(form
));
272 EXPECT_TRUE(form_structure
->ShouldBeParsed());
274 form_structure
.reset(new FormStructure(form
));
275 EXPECT_FALSE(form_structure
->IsAutofillable());
276 EXPECT_TRUE(form_structure
->ShouldBeParsed());
278 // The target cannot include http(s)://*/search...
279 form
.action
= GURL("http://google.com/search?q=hello");
280 form_structure
.reset(new FormStructure(form
));
281 EXPECT_FALSE(form_structure
->ShouldBeParsed());
283 // But search can be in the URL.
284 form
.action
= GURL("http://search.com/?q=hello");
285 form_structure
.reset(new FormStructure(form
));
286 EXPECT_TRUE(form_structure
->ShouldBeParsed());
288 // The form need only have three fields, but at least one must be a text
292 field
.label
= ASCIIToUTF16("Email");
293 field
.name
= ASCIIToUTF16("email");
294 field
.form_control_type
= "email";
295 form
.fields
.push_back(field
);
297 field
.label
= ASCIIToUTF16("State");
298 field
.name
= ASCIIToUTF16("state");
299 field
.form_control_type
= "select-one";
300 form
.fields
.push_back(field
);
302 field
.label
= ASCIIToUTF16("Country");
303 field
.name
= ASCIIToUTF16("country");
304 field
.form_control_type
= "select-one";
305 form
.fields
.push_back(field
);
307 form_structure
.reset(new FormStructure(form
));
308 EXPECT_TRUE(form_structure
->ShouldBeParsed());
310 form
.fields
[0].form_control_type
= "select-one";
311 // Now, no text fields.
312 form_structure
.reset(new FormStructure(form
));
313 EXPECT_FALSE(form_structure
->ShouldBeParsed());
316 TEST_F(FormStructureTest
, HeuristicsContactInfo
) {
317 scoped_ptr
<FormStructure
> form_structure
;
321 field
.form_control_type
= "text";
323 field
.label
= ASCIIToUTF16("First Name");
324 field
.name
= ASCIIToUTF16("firstname");
325 form
.fields
.push_back(field
);
327 field
.label
= ASCIIToUTF16("Last Name");
328 field
.name
= ASCIIToUTF16("lastname");
329 form
.fields
.push_back(field
);
331 field
.label
= ASCIIToUTF16("Email");
332 field
.name
= ASCIIToUTF16("email");
333 form
.fields
.push_back(field
);
335 field
.label
= ASCIIToUTF16("Phone");
336 field
.name
= ASCIIToUTF16("phone");
337 form
.fields
.push_back(field
);
339 field
.label
= ASCIIToUTF16("Address");
340 field
.name
= ASCIIToUTF16("address");
341 form
.fields
.push_back(field
);
343 field
.label
= ASCIIToUTF16("City");
344 field
.name
= ASCIIToUTF16("city");
345 form
.fields
.push_back(field
);
347 field
.label
= ASCIIToUTF16("Zip code");
348 field
.name
= ASCIIToUTF16("zipcode");
349 form
.fields
.push_back(field
);
351 field
.label
= base::string16();
352 field
.name
= ASCIIToUTF16("Submit");
353 field
.form_control_type
= "submit";
354 form
.fields
.push_back(field
);
356 form_structure
.reset(new FormStructure(form
));
357 form_structure
->DetermineHeuristicTypes();
358 EXPECT_TRUE(form_structure
->IsAutofillable());
360 // Expect the correct number of fields.
361 ASSERT_EQ(8U, form_structure
->field_count());
362 ASSERT_EQ(7U, form_structure
->autofill_count());
365 EXPECT_EQ(NAME_FIRST
, form_structure
->field(0)->heuristic_type());
367 EXPECT_EQ(NAME_LAST
, form_structure
->field(1)->heuristic_type());
369 EXPECT_EQ(EMAIL_ADDRESS
, form_structure
->field(2)->heuristic_type());
371 EXPECT_EQ(PHONE_HOME_WHOLE_NUMBER
,
372 form_structure
->field(3)->heuristic_type());
374 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(4)->heuristic_type());
376 EXPECT_EQ(ADDRESS_HOME_CITY
, form_structure
->field(5)->heuristic_type());
378 EXPECT_EQ(ADDRESS_HOME_ZIP
, form_structure
->field(6)->heuristic_type());
380 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(7)->heuristic_type());
383 // Verify that we can correctly process the |autocomplete| attribute.
384 TEST_F(FormStructureTest
, HeuristicsAutocompleteAttribute
) {
385 scoped_ptr
<FormStructure
> form_structure
;
389 field
.form_control_type
= "text";
391 field
.label
= base::string16();
392 field
.name
= ASCIIToUTF16("field1");
393 field
.autocomplete_attribute
= "given-name";
394 form
.fields
.push_back(field
);
396 field
.label
= base::string16();
397 field
.name
= ASCIIToUTF16("field2");
398 field
.autocomplete_attribute
= "family-name";
399 form
.fields
.push_back(field
);
401 field
.label
= base::string16();
402 field
.name
= ASCIIToUTF16("field3");
403 field
.autocomplete_attribute
= "email";
404 form
.fields
.push_back(field
);
406 form_structure
.reset(new FormStructure(form
));
407 form_structure
->DetermineHeuristicTypes();
408 EXPECT_TRUE(form_structure
->IsAutofillable());
410 // Expect the correct number of fields.
411 ASSERT_EQ(3U, form_structure
->field_count());
412 ASSERT_EQ(3U, form_structure
->autofill_count());
414 EXPECT_EQ(HTML_TYPE_GIVEN_NAME
, form_structure
->field(0)->html_type());
415 EXPECT_EQ(HTML_TYPE_FAMILY_NAME
, form_structure
->field(1)->html_type());
416 EXPECT_EQ(HTML_TYPE_EMAIL
, form_structure
->field(2)->html_type());
417 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(0)->heuristic_type());
418 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(1)->heuristic_type());
419 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(2)->heuristic_type());
422 // Verify that we can correctly process the 'autocomplete' attribute for phone
423 // number types (especially phone prefixes and suffixes).
424 TEST_F(FormStructureTest
, HeuristicsAutocompleteAttributePhoneTypes
) {
425 scoped_ptr
<FormStructure
> form_structure
;
429 field
.form_control_type
= "text";
431 field
.label
= base::string16();
432 field
.name
= ASCIIToUTF16("field1");
433 field
.autocomplete_attribute
= "tel-local";
434 form
.fields
.push_back(field
);
436 field
.label
= base::string16();
437 field
.name
= ASCIIToUTF16("field2");
438 field
.autocomplete_attribute
= "tel-local-prefix";
439 form
.fields
.push_back(field
);
441 field
.label
= base::string16();
442 field
.name
= ASCIIToUTF16("field3");
443 field
.autocomplete_attribute
= "tel-local-suffix";
444 form
.fields
.push_back(field
);
446 form_structure
.reset(new FormStructure(form
));
447 form_structure
->DetermineHeuristicTypes();
448 EXPECT_TRUE(form_structure
->IsAutofillable());
450 // Expect the correct number of fields.
451 ASSERT_EQ(3U, form_structure
->field_count());
452 EXPECT_EQ(3U, form_structure
->autofill_count());
454 EXPECT_EQ(HTML_TYPE_TEL_LOCAL
, form_structure
->field(0)->html_type());
455 EXPECT_EQ(AutofillField::IGNORED
, form_structure
->field(0)->phone_part());
456 EXPECT_EQ(HTML_TYPE_TEL_LOCAL_PREFIX
, form_structure
->field(1)->html_type());
457 EXPECT_EQ(AutofillField::PHONE_PREFIX
,
458 form_structure
->field(1)->phone_part());
459 EXPECT_EQ(HTML_TYPE_TEL_LOCAL_SUFFIX
, form_structure
->field(2)->html_type());
460 EXPECT_EQ(AutofillField::PHONE_SUFFIX
,
461 form_structure
->field(2)->phone_part());
464 // If at least one field includes type hints in the 'autocomplete' attribute, we
465 // should not try to apply any other heuristics.
466 TEST_F(FormStructureTest
, AutocompleteAttributeOverridesOtherHeuristics
) {
467 scoped_ptr
<FormStructure
> form_structure
;
470 // Start with a regular contact form.
472 field
.form_control_type
= "text";
474 field
.label
= ASCIIToUTF16("First Name");
475 field
.name
= ASCIIToUTF16("firstname");
476 form
.fields
.push_back(field
);
478 field
.label
= ASCIIToUTF16("Last Name");
479 field
.name
= ASCIIToUTF16("lastname");
480 form
.fields
.push_back(field
);
482 field
.label
= ASCIIToUTF16("Email");
483 field
.name
= ASCIIToUTF16("email");
484 form
.fields
.push_back(field
);
486 form_structure
.reset(new FormStructure(form
));
487 form_structure
->DetermineHeuristicTypes();
488 EXPECT_TRUE(form_structure
->IsAutofillable());
489 EXPECT_TRUE(form_structure
->ShouldBeCrowdsourced());
491 ASSERT_EQ(3U, form_structure
->field_count());
492 ASSERT_EQ(3U, form_structure
->autofill_count());
494 EXPECT_EQ(NAME_FIRST
, form_structure
->field(0)->heuristic_type());
495 EXPECT_EQ(NAME_LAST
, form_structure
->field(1)->heuristic_type());
496 EXPECT_EQ(EMAIL_ADDRESS
, form_structure
->field(2)->heuristic_type());
498 // Now update the first form field to include an 'autocomplete' attribute.
499 form
.fields
.front().autocomplete_attribute
= "x-other";
500 form_structure
.reset(new FormStructure(form
));
501 form_structure
->DetermineHeuristicTypes();
502 EXPECT_FALSE(form_structure
->IsAutofillable());
503 EXPECT_FALSE(form_structure
->ShouldBeCrowdsourced());
505 ASSERT_EQ(3U, form_structure
->field_count());
506 ASSERT_EQ(0U, form_structure
->autofill_count());
508 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(0)->heuristic_type());
509 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(1)->heuristic_type());
510 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(2)->heuristic_type());
513 // Even with an 'autocomplete' attribute set, ShouldBeCrowdsourced() should
514 // return true if the structure contains a password field, since there are
515 // no local heuristics to depend upon in this case. Fields will still not be
516 // considered autofillable though.
517 TEST_F(FormStructureTest
, PasswordFormShouldBeCrowdsourced
) {
520 // Start with a regular contact form.
522 field
.form_control_type
= "text";
524 field
.label
= ASCIIToUTF16("First Name");
525 field
.name
= ASCIIToUTF16("firstname");
526 form
.fields
.push_back(field
);
528 field
.label
= ASCIIToUTF16("Last Name");
529 field
.name
= ASCIIToUTF16("lastname");
530 form
.fields
.push_back(field
);
532 field
.label
= ASCIIToUTF16("Email");
533 field
.name
= ASCIIToUTF16("email");
534 field
.autocomplete_attribute
= "username";
535 form
.fields
.push_back(field
);
537 field
.label
= ASCIIToUTF16("Password");
538 field
.name
= ASCIIToUTF16("Password");
539 field
.form_control_type
= "password";
540 form
.fields
.push_back(field
);
542 FormStructure
form_structure(form
);
543 form_structure
.DetermineHeuristicTypes();
544 EXPECT_TRUE(form_structure
.ShouldBeCrowdsourced());
547 // Verify that we can correctly process sections listed in the |autocomplete|
549 TEST_F(FormStructureTest
, HeuristicsAutocompleteAttributeWithSections
) {
553 field
.form_control_type
= "text";
555 // Some fields will have no section specified. These fall into the default
557 field
.autocomplete_attribute
= "email";
558 form
.fields
.push_back(field
);
560 // We allow arbitrary section names.
561 field
.autocomplete_attribute
= "section-foo email";
562 form
.fields
.push_back(field
);
564 // "shipping" and "billing" are special section tokens that don't require the
565 // "section-" prefix.
566 field
.autocomplete_attribute
= "shipping email";
567 form
.fields
.push_back(field
);
568 field
.autocomplete_attribute
= "billing email";
569 form
.fields
.push_back(field
);
571 // "shipping" and "billing" can be combined with other section names.
572 field
.autocomplete_attribute
= "section-foo shipping email";
573 form
.fields
.push_back(field
);
574 field
.autocomplete_attribute
= "section-foo billing email";
575 form
.fields
.push_back(field
);
577 // We don't do anything clever to try to coalesce sections; it's up to site
578 // authors to avoid typos.
579 field
.autocomplete_attribute
= "section--foo email";
580 form
.fields
.push_back(field
);
582 // "shipping email" and "section--shipping" email should be parsed as
583 // different sections. This is only an interesting test due to how we
584 // implement implicit section names from attributes like "shipping email"; see
585 // the implementation for more details.
586 field
.autocomplete_attribute
= "section--shipping email";
587 form
.fields
.push_back(field
);
589 // Credit card fields are implicitly in a separate section from other fields.
590 field
.autocomplete_attribute
= "section-foo cc-number";
591 form
.fields
.push_back(field
);
593 FormStructure
form_structure(form
);
594 form_structure
.DetermineHeuristicTypes();
595 EXPECT_TRUE(form_structure
.IsAutofillable());
597 // Expect the correct number of fields.
598 ASSERT_EQ(9U, form_structure
.field_count());
599 EXPECT_EQ(9U, form_structure
.autofill_count());
601 // All of the fields in this form should be parsed as belonging to different
603 std::set
<std::string
> section_names
;
604 for (size_t i
= 0; i
< 9; ++i
) {
605 section_names
.insert(form_structure
.field(i
)->section());
607 EXPECT_EQ(9U, section_names
.size());
610 // Verify that we can correctly process a degenerate section listed in the
611 // |autocomplete| attribute.
612 TEST_F(FormStructureTest
,
613 HeuristicsAutocompleteAttributeWithSectionsDegenerate
) {
617 field
.form_control_type
= "text";
619 // Some fields will have no section specified. These fall into the default
621 field
.autocomplete_attribute
= "email";
622 form
.fields
.push_back(field
);
624 // Specifying "section-" is equivalent to not specifying a section.
625 field
.autocomplete_attribute
= "section- email";
626 form
.fields
.push_back(field
);
628 // Invalid tokens should prevent us from setting a section name.
629 field
.autocomplete_attribute
= "garbage section-foo email";
630 form
.fields
.push_back(field
);
631 field
.autocomplete_attribute
= "garbage section-bar email";
632 form
.fields
.push_back(field
);
633 field
.autocomplete_attribute
= "garbage shipping email";
634 form
.fields
.push_back(field
);
635 field
.autocomplete_attribute
= "garbage billing email";
636 form
.fields
.push_back(field
);
638 FormStructure
form_structure(form
);
639 form_structure
.DetermineHeuristicTypes();
641 // Expect the correct number of fields.
642 ASSERT_EQ(6U, form_structure
.field_count());
643 EXPECT_EQ(2U, form_structure
.autofill_count());
645 // All of the fields in this form should be parsed as belonging to the same
647 std::set
<std::string
> section_names
;
648 for (size_t i
= 0; i
< 6; ++i
) {
649 section_names
.insert(form_structure
.field(i
)->section());
651 EXPECT_EQ(1U, section_names
.size());
654 // Verify that we can correctly process repeated sections listed in the
655 // |autocomplete| attribute.
656 TEST_F(FormStructureTest
, HeuristicsAutocompleteAttributeWithSectionsRepeated
) {
660 field
.form_control_type
= "text";
662 field
.autocomplete_attribute
= "section-foo email";
663 form
.fields
.push_back(field
);
664 field
.autocomplete_attribute
= "section-foo address-line1";
665 form
.fields
.push_back(field
);
667 FormStructure
form_structure(form
);
668 form_structure
.DetermineHeuristicTypes();
670 // Expect the correct number of fields.
671 ASSERT_EQ(2U, form_structure
.field_count());
672 EXPECT_EQ(2U, form_structure
.autofill_count());
674 // All of the fields in this form should be parsed as belonging to the same
676 std::set
<std::string
> section_names
;
677 for (size_t i
= 0; i
< 2; ++i
) {
678 section_names
.insert(form_structure
.field(i
)->section());
680 EXPECT_EQ(1U, section_names
.size());
683 // Verify that we do not override the author-specified sections from a form with
685 TEST_F(FormStructureTest
, HeuristicsDontOverrideAutocompleteAttributeSections
) {
689 field
.form_control_type
= "text";
691 field
.name
= ASCIIToUTF16("one");
692 field
.autocomplete_attribute
= "address-line1";
693 form
.fields
.push_back(field
);
694 field
.name
= base::string16();
695 field
.autocomplete_attribute
= "section-foo email";
696 form
.fields
.push_back(field
);
697 field
.name
= base::string16();
698 field
.autocomplete_attribute
= "name";
699 form
.fields
.push_back(field
);
700 field
.name
= ASCIIToUTF16("two");
701 field
.autocomplete_attribute
= "address-line1";
702 form
.fields
.push_back(field
);
704 FormStructure
form_structure(form
);
705 form_structure
.DetermineHeuristicTypes();
707 // Expect the correct number of fields.
708 ASSERT_EQ(4U, form_structure
.field_count());
709 EXPECT_EQ(4U, form_structure
.autofill_count());
711 // Normally, the two separate address fields would cause us to detect two
712 // separate sections; but because there is an author-specified section in this
713 // form, we do not apply these usual heuristics.
714 EXPECT_EQ(ASCIIToUTF16("one"), form_structure
.field(0)->name
);
715 EXPECT_EQ(ASCIIToUTF16("two"), form_structure
.field(3)->name
);
716 EXPECT_EQ(form_structure
.field(0)->section(),
717 form_structure
.field(3)->section());
720 TEST_F(FormStructureTest
, HeuristicsSample8
) {
721 scoped_ptr
<FormStructure
> form_structure
;
725 field
.form_control_type
= "text";
727 field
.label
= ASCIIToUTF16("Your First Name:");
728 field
.name
= ASCIIToUTF16("bill.first");
729 form
.fields
.push_back(field
);
731 field
.label
= ASCIIToUTF16("Your Last Name:");
732 field
.name
= ASCIIToUTF16("bill.last");
733 form
.fields
.push_back(field
);
735 field
.label
= ASCIIToUTF16("Street Address Line 1:");
736 field
.name
= ASCIIToUTF16("bill.street1");
737 form
.fields
.push_back(field
);
739 field
.label
= ASCIIToUTF16("Street Address Line 2:");
740 field
.name
= ASCIIToUTF16("bill.street2");
741 form
.fields
.push_back(field
);
743 field
.label
= ASCIIToUTF16("City");
744 field
.name
= ASCIIToUTF16("bill.city");
745 form
.fields
.push_back(field
);
747 field
.label
= ASCIIToUTF16("State (U.S.):");
748 field
.name
= ASCIIToUTF16("bill.state");
749 form
.fields
.push_back(field
);
751 field
.label
= ASCIIToUTF16("Zip/Postal Code:");
752 field
.name
= ASCIIToUTF16("BillTo.PostalCode");
753 form
.fields
.push_back(field
);
755 field
.label
= ASCIIToUTF16("Country:");
756 field
.name
= ASCIIToUTF16("bill.country");
757 form
.fields
.push_back(field
);
759 field
.label
= ASCIIToUTF16("Phone Number:");
760 field
.name
= ASCIIToUTF16("BillTo.Phone");
761 form
.fields
.push_back(field
);
763 field
.label
= base::string16();
764 field
.name
= ASCIIToUTF16("Submit");
765 field
.form_control_type
= "submit";
766 form
.fields
.push_back(field
);
768 form_structure
.reset(new FormStructure(form
));
769 form_structure
->DetermineHeuristicTypes();
770 EXPECT_TRUE(form_structure
->IsAutofillable());
771 ASSERT_EQ(10U, form_structure
->field_count());
772 ASSERT_EQ(9U, form_structure
->autofill_count());
775 EXPECT_EQ(NAME_FIRST
, form_structure
->field(0)->heuristic_type());
777 EXPECT_EQ(NAME_LAST
, form_structure
->field(1)->heuristic_type());
779 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(2)->heuristic_type());
781 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(3)->heuristic_type());
783 EXPECT_EQ(ADDRESS_HOME_CITY
, form_structure
->field(4)->heuristic_type());
785 EXPECT_EQ(ADDRESS_HOME_STATE
, form_structure
->field(5)->heuristic_type());
787 EXPECT_EQ(ADDRESS_HOME_ZIP
, form_structure
->field(6)->heuristic_type());
789 EXPECT_EQ(ADDRESS_HOME_COUNTRY
, form_structure
->field(7)->heuristic_type());
791 EXPECT_EQ(PHONE_HOME_WHOLE_NUMBER
,
792 form_structure
->field(8)->heuristic_type());
794 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(9)->heuristic_type());
797 TEST_F(FormStructureTest
, HeuristicsSample6
) {
798 scoped_ptr
<FormStructure
> form_structure
;
802 field
.form_control_type
= "text";
804 field
.label
= ASCIIToUTF16("E-mail address");
805 field
.name
= ASCIIToUTF16("email");
806 form
.fields
.push_back(field
);
808 field
.label
= ASCIIToUTF16("Full name");
809 field
.name
= ASCIIToUTF16("name");
810 form
.fields
.push_back(field
);
812 field
.label
= ASCIIToUTF16("Company");
813 field
.name
= ASCIIToUTF16("company");
814 form
.fields
.push_back(field
);
816 field
.label
= ASCIIToUTF16("Address");
817 field
.name
= ASCIIToUTF16("address");
818 form
.fields
.push_back(field
);
820 field
.label
= ASCIIToUTF16("City");
821 field
.name
= ASCIIToUTF16("city");
822 form
.fields
.push_back(field
);
824 field
.label
= ASCIIToUTF16("Zip Code");
825 field
.name
= ASCIIToUTF16("Home.PostalCode");
826 form
.fields
.push_back(field
);
828 field
.label
= base::string16();
829 field
.name
= ASCIIToUTF16("Submit");
830 field
.value
= ASCIIToUTF16("continue");
831 field
.form_control_type
= "submit";
832 form
.fields
.push_back(field
);
834 form_structure
.reset(new FormStructure(form
));
835 form_structure
->DetermineHeuristicTypes();
836 EXPECT_TRUE(form_structure
->IsAutofillable());
837 ASSERT_EQ(7U, form_structure
->field_count());
838 ASSERT_EQ(6U, form_structure
->autofill_count());
841 EXPECT_EQ(EMAIL_ADDRESS
, form_structure
->field(0)->heuristic_type());
843 EXPECT_EQ(NAME_FULL
, form_structure
->field(1)->heuristic_type());
845 EXPECT_EQ(COMPANY_NAME
, form_structure
->field(2)->heuristic_type());
847 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(3)->heuristic_type());
849 EXPECT_EQ(ADDRESS_HOME_CITY
, form_structure
->field(4)->heuristic_type());
851 EXPECT_EQ(ADDRESS_HOME_ZIP
, form_structure
->field(5)->heuristic_type());
853 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(6)->heuristic_type());
856 // Tests a sequence of FormFields where only labels are supplied to heuristics
857 // for matching. This works because FormFieldData labels are matched in the
858 // case that input element ids (or |name| fields) are missing.
859 TEST_F(FormStructureTest
, HeuristicsLabelsOnly
) {
860 scoped_ptr
<FormStructure
> form_structure
;
864 field
.form_control_type
= "text";
866 field
.label
= ASCIIToUTF16("First Name");
867 field
.name
= base::string16();
868 form
.fields
.push_back(field
);
870 field
.label
= ASCIIToUTF16("Last Name");
871 field
.name
= base::string16();
872 form
.fields
.push_back(field
);
874 field
.label
= ASCIIToUTF16("Email");
875 field
.name
= base::string16();
876 form
.fields
.push_back(field
);
878 field
.label
= ASCIIToUTF16("Phone");
879 field
.name
= base::string16();
880 form
.fields
.push_back(field
);
882 field
.label
= ASCIIToUTF16("Address");
883 field
.name
= base::string16();
884 form
.fields
.push_back(field
);
886 field
.label
= ASCIIToUTF16("Address");
887 field
.name
= base::string16();
888 form
.fields
.push_back(field
);
890 field
.label
= ASCIIToUTF16("Zip code");
891 field
.name
= base::string16();
892 form
.fields
.push_back(field
);
894 field
.label
= base::string16();
895 field
.name
= ASCIIToUTF16("Submit");
896 field
.form_control_type
= "submit";
897 form
.fields
.push_back(field
);
899 form_structure
.reset(new FormStructure(form
));
900 form_structure
->DetermineHeuristicTypes();
901 EXPECT_TRUE(form_structure
->IsAutofillable());
902 ASSERT_EQ(8U, form_structure
->field_count());
903 ASSERT_EQ(7U, form_structure
->autofill_count());
906 EXPECT_EQ(NAME_FIRST
, form_structure
->field(0)->heuristic_type());
908 EXPECT_EQ(NAME_LAST
, form_structure
->field(1)->heuristic_type());
910 EXPECT_EQ(EMAIL_ADDRESS
, form_structure
->field(2)->heuristic_type());
912 EXPECT_EQ(PHONE_HOME_WHOLE_NUMBER
,
913 form_structure
->field(3)->heuristic_type());
915 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(4)->heuristic_type());
917 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(5)->heuristic_type());
919 EXPECT_EQ(ADDRESS_HOME_ZIP
, form_structure
->field(6)->heuristic_type());
921 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(7)->heuristic_type());
924 TEST_F(FormStructureTest
, HeuristicsCreditCardInfo
) {
925 scoped_ptr
<FormStructure
> form_structure
;
929 field
.form_control_type
= "text";
931 field
.label
= ASCIIToUTF16("Name on Card");
932 field
.name
= ASCIIToUTF16("name_on_card");
933 form
.fields
.push_back(field
);
935 field
.label
= ASCIIToUTF16("Card Number");
936 field
.name
= ASCIIToUTF16("card_number");
937 form
.fields
.push_back(field
);
939 field
.label
= ASCIIToUTF16("Exp Month");
940 field
.name
= ASCIIToUTF16("ccmonth");
941 form
.fields
.push_back(field
);
943 field
.label
= ASCIIToUTF16("Exp Year");
944 field
.name
= ASCIIToUTF16("ccyear");
945 form
.fields
.push_back(field
);
947 field
.label
= ASCIIToUTF16("Verification");
948 field
.name
= ASCIIToUTF16("verification");
949 form
.fields
.push_back(field
);
951 field
.label
= base::string16();
952 field
.name
= ASCIIToUTF16("Submit");
953 field
.form_control_type
= "submit";
954 form
.fields
.push_back(field
);
956 form_structure
.reset(new FormStructure(form
));
957 form_structure
->DetermineHeuristicTypes();
958 EXPECT_TRUE(form_structure
->IsAutofillable());
959 ASSERT_EQ(6U, form_structure
->field_count());
960 ASSERT_EQ(5U, form_structure
->autofill_count());
963 EXPECT_EQ(CREDIT_CARD_NAME
, form_structure
->field(0)->heuristic_type());
964 // Credit card number.
965 EXPECT_EQ(CREDIT_CARD_NUMBER
, form_structure
->field(1)->heuristic_type());
966 // Credit card expiration month.
967 EXPECT_EQ(CREDIT_CARD_EXP_MONTH
, form_structure
->field(2)->heuristic_type());
968 // Credit card expiration year.
969 EXPECT_EQ(CREDIT_CARD_EXP_4_DIGIT_YEAR
,
970 form_structure
->field(3)->heuristic_type());
972 EXPECT_EQ(CREDIT_CARD_VERIFICATION_CODE
,
973 form_structure
->field(4)->heuristic_type());
975 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(5)->heuristic_type());
978 TEST_F(FormStructureTest
, HeuristicsCreditCardInfoWithUnknownCardField
) {
979 scoped_ptr
<FormStructure
> form_structure
;
983 field
.form_control_type
= "text";
985 field
.label
= ASCIIToUTF16("Name on Card");
986 field
.name
= ASCIIToUTF16("name_on_card");
987 form
.fields
.push_back(field
);
989 // This is not a field we know how to process. But we should skip over it
990 // and process the other fields in the card block.
991 field
.label
= ASCIIToUTF16("Card image");
992 field
.name
= ASCIIToUTF16("card_image");
993 form
.fields
.push_back(field
);
995 field
.label
= ASCIIToUTF16("Card Number");
996 field
.name
= ASCIIToUTF16("card_number");
997 form
.fields
.push_back(field
);
999 field
.label
= ASCIIToUTF16("Exp Month");
1000 field
.name
= ASCIIToUTF16("ccmonth");
1001 form
.fields
.push_back(field
);
1003 field
.label
= ASCIIToUTF16("Exp Year");
1004 field
.name
= ASCIIToUTF16("ccyear");
1005 form
.fields
.push_back(field
);
1007 field
.label
= ASCIIToUTF16("Verification");
1008 field
.name
= ASCIIToUTF16("verification");
1009 form
.fields
.push_back(field
);
1011 field
.label
= base::string16();
1012 field
.name
= ASCIIToUTF16("Submit");
1013 field
.form_control_type
= "submit";
1014 form
.fields
.push_back(field
);
1016 form_structure
.reset(new FormStructure(form
));
1017 form_structure
->DetermineHeuristicTypes();
1018 EXPECT_TRUE(form_structure
->IsAutofillable());
1019 ASSERT_EQ(7U, form_structure
->field_count());
1020 ASSERT_EQ(5U, form_structure
->autofill_count());
1022 // Credit card name.
1023 EXPECT_EQ(CREDIT_CARD_NAME
, form_structure
->field(0)->heuristic_type());
1024 // Credit card type. This is an unknown type but related to the credit card.
1025 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(1)->heuristic_type());
1026 // Credit card number.
1027 EXPECT_EQ(CREDIT_CARD_NUMBER
, form_structure
->field(2)->heuristic_type());
1028 // Credit card expiration month.
1029 EXPECT_EQ(CREDIT_CARD_EXP_MONTH
, form_structure
->field(3)->heuristic_type());
1030 // Credit card expiration year.
1031 EXPECT_EQ(CREDIT_CARD_EXP_4_DIGIT_YEAR
,
1032 form_structure
->field(4)->heuristic_type());
1034 EXPECT_EQ(CREDIT_CARD_VERIFICATION_CODE
,
1035 form_structure
->field(5)->heuristic_type());
1037 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(6)->heuristic_type());
1040 TEST_F(FormStructureTest
, ThreeAddressLines
) {
1041 scoped_ptr
<FormStructure
> form_structure
;
1044 FormFieldData field
;
1045 field
.form_control_type
= "text";
1047 field
.label
= ASCIIToUTF16("Address Line1");
1048 field
.name
= ASCIIToUTF16("Address");
1049 form
.fields
.push_back(field
);
1051 field
.label
= ASCIIToUTF16("Address Line2");
1052 field
.name
= ASCIIToUTF16("Address");
1053 form
.fields
.push_back(field
);
1055 field
.label
= ASCIIToUTF16("Address Line3");
1056 field
.name
= ASCIIToUTF16("Address");
1057 form
.fields
.push_back(field
);
1059 field
.label
= ASCIIToUTF16("City");
1060 field
.name
= ASCIIToUTF16("city");
1061 form
.fields
.push_back(field
);
1063 form_structure
.reset(new FormStructure(form
));
1064 form_structure
->DetermineHeuristicTypes();
1065 EXPECT_TRUE(form_structure
->IsAutofillable());
1066 ASSERT_EQ(4U, form_structure
->field_count());
1067 ASSERT_EQ(4U, form_structure
->autofill_count());
1070 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(0)->heuristic_type());
1072 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(1)->heuristic_type());
1074 EXPECT_EQ(ADDRESS_HOME_LINE3
, form_structure
->field(2)->heuristic_type());
1076 EXPECT_EQ(ADDRESS_HOME_CITY
, form_structure
->field(3)->heuristic_type());
1079 // Numbered address lines after line two are ignored.
1080 TEST_F(FormStructureTest
, SurplusAddressLinesIgnored
) {
1081 scoped_ptr
<FormStructure
> form_structure
;
1084 FormFieldData field
;
1085 field
.form_control_type
= "text";
1087 field
.label
= ASCIIToUTF16("Address Line1");
1088 field
.name
= ASCIIToUTF16("shipping.address.addressLine1");
1089 form
.fields
.push_back(field
);
1091 field
.label
= ASCIIToUTF16("Address Line2");
1092 field
.name
= ASCIIToUTF16("shipping.address.addressLine2");
1093 form
.fields
.push_back(field
);
1095 field
.label
= ASCIIToUTF16("Address Line3");
1096 field
.name
= ASCIIToUTF16("billing.address.addressLine3");
1097 form
.fields
.push_back(field
);
1099 field
.label
= ASCIIToUTF16("Address Line4");
1100 field
.name
= ASCIIToUTF16("billing.address.addressLine4");
1101 form
.fields
.push_back(field
);
1103 form_structure
.reset(new FormStructure(form
));
1104 form_structure
->DetermineHeuristicTypes();
1105 ASSERT_EQ(4U, form_structure
->field_count());
1106 ASSERT_EQ(3U, form_structure
->autofill_count());
1109 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(0)->heuristic_type());
1111 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(1)->heuristic_type());
1113 EXPECT_EQ(ADDRESS_HOME_LINE3
, form_structure
->field(2)->heuristic_type());
1114 // Address Line 4 (ignored).
1115 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(3)->heuristic_type());
1118 // This example comes from expedia.com where they used to use a "Suite" label
1119 // to indicate a suite or apartment number (the form has changed since this
1120 // test was written). We interpret this as address line 2. And the following
1121 // "Street address second line" we interpret as address line 3.
1122 // See http://crbug.com/48197 for details.
1123 TEST_F(FormStructureTest
, ThreeAddressLinesExpedia
) {
1124 scoped_ptr
<FormStructure
> form_structure
;
1127 FormFieldData field
;
1128 field
.form_control_type
= "text";
1130 field
.label
= ASCIIToUTF16("Street:");
1131 field
.name
= ASCIIToUTF16("FOPIH_RgWebCC_0_IHAddress_ads1");
1132 form
.fields
.push_back(field
);
1134 field
.label
= ASCIIToUTF16("Suite or Apt:");
1135 field
.name
= ASCIIToUTF16("FOPIH_RgWebCC_0_IHAddress_adap");
1136 form
.fields
.push_back(field
);
1138 field
.label
= ASCIIToUTF16("Street address second line");
1139 field
.name
= ASCIIToUTF16("FOPIH_RgWebCC_0_IHAddress_ads2");
1140 form
.fields
.push_back(field
);
1142 field
.label
= ASCIIToUTF16("City:");
1143 field
.name
= ASCIIToUTF16("FOPIH_RgWebCC_0_IHAddress_adct");
1144 form
.fields
.push_back(field
);
1146 form_structure
.reset(new FormStructure(form
));
1147 form_structure
->DetermineHeuristicTypes();
1148 EXPECT_TRUE(form_structure
->IsAutofillable());
1149 ASSERT_EQ(4U, form_structure
->field_count());
1150 EXPECT_EQ(4U, form_structure
->autofill_count());
1153 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(0)->heuristic_type());
1155 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(1)->heuristic_type());
1157 EXPECT_EQ(ADDRESS_HOME_LINE3
, form_structure
->field(2)->heuristic_type());
1159 EXPECT_EQ(ADDRESS_HOME_CITY
, form_structure
->field(3)->heuristic_type());
1162 // This example comes from ebay.com where the word "suite" appears in the label
1163 // and the name "address2" clearly indicates that this is the address line 2.
1164 // See http://crbug.com/48197 for details.
1165 TEST_F(FormStructureTest
, TwoAddressLinesEbay
) {
1166 scoped_ptr
<FormStructure
> form_structure
;
1169 FormFieldData field
;
1170 field
.form_control_type
= "text";
1172 field
.label
= ASCIIToUTF16("Address Line1");
1173 field
.name
= ASCIIToUTF16("address1");
1174 form
.fields
.push_back(field
);
1176 field
.label
= ASCIIToUTF16("Floor number, suite number, etc");
1177 field
.name
= ASCIIToUTF16("address2");
1178 form
.fields
.push_back(field
);
1180 field
.label
= ASCIIToUTF16("City:");
1181 field
.name
= ASCIIToUTF16("city");
1182 form
.fields
.push_back(field
);
1184 form_structure
.reset(new FormStructure(form
));
1185 form_structure
->DetermineHeuristicTypes();
1186 EXPECT_TRUE(form_structure
->IsAutofillable());
1187 ASSERT_EQ(3U, form_structure
->field_count());
1188 ASSERT_EQ(3U, form_structure
->autofill_count());
1191 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(0)->heuristic_type());
1193 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(1)->heuristic_type());
1195 EXPECT_EQ(ADDRESS_HOME_CITY
, form_structure
->field(2)->heuristic_type());
1198 TEST_F(FormStructureTest
, HeuristicsStateWithProvince
) {
1199 scoped_ptr
<FormStructure
> form_structure
;
1202 FormFieldData field
;
1203 field
.form_control_type
= "text";
1205 field
.label
= ASCIIToUTF16("Address Line1");
1206 field
.name
= ASCIIToUTF16("Address");
1207 form
.fields
.push_back(field
);
1209 field
.label
= ASCIIToUTF16("Address Line2");
1210 field
.name
= ASCIIToUTF16("Address");
1211 form
.fields
.push_back(field
);
1213 field
.label
= ASCIIToUTF16("State/Province/Region");
1214 field
.name
= ASCIIToUTF16("State");
1215 form
.fields
.push_back(field
);
1217 form_structure
.reset(new FormStructure(form
));
1218 form_structure
->DetermineHeuristicTypes();
1219 EXPECT_TRUE(form_structure
->IsAutofillable());
1220 ASSERT_EQ(3U, form_structure
->field_count());
1221 ASSERT_EQ(3U, form_structure
->autofill_count());
1224 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(0)->heuristic_type());
1226 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(1)->heuristic_type());
1228 EXPECT_EQ(ADDRESS_HOME_STATE
, form_structure
->field(2)->heuristic_type());
1231 // This example comes from lego.com's checkout page.
1232 TEST_F(FormStructureTest
, HeuristicsWithBilling
) {
1233 scoped_ptr
<FormStructure
> form_structure
;
1236 FormFieldData field
;
1237 field
.form_control_type
= "text";
1239 field
.label
= ASCIIToUTF16("First Name*:");
1240 field
.name
= ASCIIToUTF16("editBillingAddress$firstNameBox");
1241 form
.fields
.push_back(field
);
1243 field
.label
= ASCIIToUTF16("Last Name*:");
1244 field
.name
= ASCIIToUTF16("editBillingAddress$lastNameBox");
1245 form
.fields
.push_back(field
);
1247 field
.label
= ASCIIToUTF16("Company Name:");
1248 field
.name
= ASCIIToUTF16("editBillingAddress$companyBox");
1249 form
.fields
.push_back(field
);
1251 field
.label
= ASCIIToUTF16("Address*:");
1252 field
.name
= ASCIIToUTF16("editBillingAddress$addressLine1Box");
1253 form
.fields
.push_back(field
);
1255 field
.label
= ASCIIToUTF16("Apt/Suite :");
1256 field
.name
= ASCIIToUTF16("editBillingAddress$addressLine2Box");
1257 form
.fields
.push_back(field
);
1259 field
.label
= ASCIIToUTF16("City*:");
1260 field
.name
= ASCIIToUTF16("editBillingAddress$cityBox");
1261 form
.fields
.push_back(field
);
1263 field
.label
= ASCIIToUTF16("State/Province*:");
1264 field
.name
= ASCIIToUTF16("editBillingAddress$stateDropDown");
1265 form
.fields
.push_back(field
);
1267 field
.label
= ASCIIToUTF16("Country*:");
1268 field
.name
= ASCIIToUTF16("editBillingAddress$countryDropDown");
1269 form
.fields
.push_back(field
);
1271 field
.label
= ASCIIToUTF16("Postal Code*:");
1272 field
.name
= ASCIIToUTF16("editBillingAddress$zipCodeBox");
1273 form
.fields
.push_back(field
);
1275 field
.label
= ASCIIToUTF16("Phone*:");
1276 field
.name
= ASCIIToUTF16("editBillingAddress$phoneBox");
1277 form
.fields
.push_back(field
);
1279 field
.label
= ASCIIToUTF16("Email Address*:");
1280 field
.name
= ASCIIToUTF16("email$emailBox");
1281 form
.fields
.push_back(field
);
1283 form_structure
.reset(new FormStructure(form
));
1284 form_structure
->DetermineHeuristicTypes();
1285 EXPECT_TRUE(form_structure
->IsAutofillable());
1286 ASSERT_EQ(11U, form_structure
->field_count());
1287 ASSERT_EQ(11U, form_structure
->autofill_count());
1289 EXPECT_EQ(NAME_FIRST
, form_structure
->field(0)->heuristic_type());
1290 EXPECT_EQ(NAME_LAST
, form_structure
->field(1)->heuristic_type());
1291 EXPECT_EQ(COMPANY_NAME
, form_structure
->field(2)->heuristic_type());
1292 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(3)->heuristic_type());
1293 EXPECT_EQ(ADDRESS_HOME_LINE2
, form_structure
->field(4)->heuristic_type());
1294 EXPECT_EQ(ADDRESS_HOME_CITY
, form_structure
->field(5)->heuristic_type());
1295 EXPECT_EQ(ADDRESS_HOME_STATE
, form_structure
->field(6)->heuristic_type());
1296 EXPECT_EQ(ADDRESS_HOME_COUNTRY
, form_structure
->field(7)->heuristic_type());
1297 EXPECT_EQ(ADDRESS_HOME_ZIP
, form_structure
->field(8)->heuristic_type());
1298 EXPECT_EQ(PHONE_HOME_WHOLE_NUMBER
,
1299 form_structure
->field(9)->heuristic_type());
1300 EXPECT_EQ(EMAIL_ADDRESS
, form_structure
->field(10)->heuristic_type());
1303 TEST_F(FormStructureTest
, ThreePartPhoneNumber
) {
1304 scoped_ptr
<FormStructure
> form_structure
;
1307 FormFieldData field
;
1308 field
.form_control_type
= "text";
1310 field
.label
= ASCIIToUTF16("Phone:");
1311 field
.name
= ASCIIToUTF16("dayphone1");
1312 field
.max_length
= 0;
1313 form
.fields
.push_back(field
);
1315 field
.label
= ASCIIToUTF16("-");
1316 field
.name
= ASCIIToUTF16("dayphone2");
1317 field
.max_length
= 3; // Size of prefix is 3.
1318 form
.fields
.push_back(field
);
1320 field
.label
= ASCIIToUTF16("-");
1321 field
.name
= ASCIIToUTF16("dayphone3");
1322 field
.max_length
= 4; // Size of suffix is 4. If unlimited size is
1323 // passed, phone will be parsed as
1324 // <country code> - <area code> - <phone>.
1325 form
.fields
.push_back(field
);
1327 field
.label
= ASCIIToUTF16("ext.:");
1328 field
.name
= ASCIIToUTF16("dayphone4");
1329 field
.max_length
= 0;
1330 form
.fields
.push_back(field
);
1332 form_structure
.reset(new FormStructure(form
));
1333 form_structure
->DetermineHeuristicTypes();
1334 EXPECT_TRUE(form_structure
->IsAutofillable());
1335 ASSERT_EQ(4U, form_structure
->field_count());
1336 ASSERT_EQ(3U, form_structure
->autofill_count());
1339 EXPECT_EQ(PHONE_HOME_CITY_CODE
, form_structure
->field(0)->heuristic_type());
1340 // Phone number suffix.
1341 EXPECT_EQ(PHONE_HOME_NUMBER
,
1342 form_structure
->field(1)->heuristic_type());
1343 // Phone number suffix.
1344 EXPECT_EQ(PHONE_HOME_NUMBER
,
1345 form_structure
->field(2)->heuristic_type());
1347 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(3)->heuristic_type());
1350 TEST_F(FormStructureTest
, HeuristicsInfernoCC
) {
1351 scoped_ptr
<FormStructure
> form_structure
;
1354 FormFieldData field
;
1355 field
.form_control_type
= "text";
1357 field
.label
= ASCIIToUTF16("Name on Card");
1358 field
.name
= ASCIIToUTF16("name_on_card");
1359 form
.fields
.push_back(field
);
1361 field
.label
= ASCIIToUTF16("Address");
1362 field
.name
= ASCIIToUTF16("billing_address");
1363 form
.fields
.push_back(field
);
1365 field
.label
= ASCIIToUTF16("Card Number");
1366 field
.name
= ASCIIToUTF16("card_number");
1367 form
.fields
.push_back(field
);
1369 field
.label
= ASCIIToUTF16("Expiration Date");
1370 field
.name
= ASCIIToUTF16("expiration_month");
1371 form
.fields
.push_back(field
);
1373 field
.label
= ASCIIToUTF16("Expiration Year");
1374 field
.name
= ASCIIToUTF16("expiration_year");
1375 form
.fields
.push_back(field
);
1377 form_structure
.reset(new FormStructure(form
));
1378 form_structure
->DetermineHeuristicTypes();
1379 EXPECT_TRUE(form_structure
->IsAutofillable());
1381 // Expect the correct number of fields.
1382 ASSERT_EQ(5U, form_structure
->field_count());
1383 EXPECT_EQ(5U, form_structure
->autofill_count());
1386 EXPECT_EQ(CREDIT_CARD_NAME
, form_structure
->field(0)->heuristic_type());
1388 EXPECT_EQ(ADDRESS_HOME_LINE1
, form_structure
->field(1)->heuristic_type());
1390 EXPECT_EQ(CREDIT_CARD_NUMBER
, form_structure
->field(2)->heuristic_type());
1392 EXPECT_EQ(CREDIT_CARD_EXP_MONTH
, form_structure
->field(3)->heuristic_type());
1394 EXPECT_EQ(CREDIT_CARD_EXP_4_DIGIT_YEAR
,
1395 form_structure
->field(4)->heuristic_type());
1398 TEST_F(FormStructureTest
, CVCCodeClash
) {
1399 scoped_ptr
<FormStructure
> form_structure
;
1402 FormFieldData field
;
1403 field
.form_control_type
= "text";
1405 field
.label
= ASCIIToUTF16("Card number");
1406 field
.name
= ASCIIToUTF16("ccnumber");
1407 form
.fields
.push_back(field
);
1409 field
.label
= ASCIIToUTF16("First name");
1410 field
.name
= ASCIIToUTF16("first_name");
1411 form
.fields
.push_back(field
);
1413 field
.label
= ASCIIToUTF16("Last name");
1414 field
.name
= ASCIIToUTF16("last_name");
1415 form
.fields
.push_back(field
);
1417 field
.label
= ASCIIToUTF16("Expiration date");
1418 field
.name
= ASCIIToUTF16("ccexpiresmonth");
1419 form
.fields
.push_back(field
);
1421 field
.label
= base::string16();
1422 field
.name
= ASCIIToUTF16("ccexpiresyear");
1423 form
.fields
.push_back(field
);
1425 field
.label
= ASCIIToUTF16("cvc number");
1426 field
.name
= ASCIIToUTF16("csc");
1427 form
.fields
.push_back(field
);
1429 form_structure
.reset(new FormStructure(form
));
1430 form_structure
->DetermineHeuristicTypes();
1431 EXPECT_TRUE(form_structure
->IsAutofillable());
1433 // Expect the correct number of fields.
1434 ASSERT_EQ(6U, form_structure
->field_count());
1435 ASSERT_EQ(5U, form_structure
->autofill_count());
1438 EXPECT_EQ(CREDIT_CARD_NUMBER
, form_structure
->field(0)->heuristic_type());
1439 // First name, taken as name on card.
1440 EXPECT_EQ(CREDIT_CARD_NAME
, form_structure
->field(1)->heuristic_type());
1441 // Last name is not merged.
1442 EXPECT_EQ(UNKNOWN_TYPE
, form_structure
->field(2)->heuristic_type());
1444 EXPECT_EQ(CREDIT_CARD_EXP_MONTH
, form_structure
->field(3)->heuristic_type());
1446 EXPECT_EQ(CREDIT_CARD_EXP_4_DIGIT_YEAR
,
1447 form_structure
->field(4)->heuristic_type());
1449 EXPECT_EQ(CREDIT_CARD_VERIFICATION_CODE
,
1450 form_structure
->field(5)->heuristic_type());
1453 TEST_F(FormStructureTest
, EncodeQueryRequest
) {
1456 FormFieldData field
;
1457 field
.form_control_type
= "text";
1459 field
.label
= ASCIIToUTF16("Name on Card");
1460 field
.name
= ASCIIToUTF16("name_on_card");
1461 form
.fields
.push_back(field
);
1463 field
.label
= ASCIIToUTF16("Address");
1464 field
.name
= ASCIIToUTF16("billing_address");
1465 form
.fields
.push_back(field
);
1467 field
.label
= ASCIIToUTF16("Card Number");
1468 field
.name
= ASCIIToUTF16("card_number");
1469 form
.fields
.push_back(field
);
1471 field
.label
= ASCIIToUTF16("Expiration Date");
1472 field
.name
= ASCIIToUTF16("expiration_month");
1473 form
.fields
.push_back(field
);
1475 field
.label
= ASCIIToUTF16("Expiration Year");
1476 field
.name
= ASCIIToUTF16("expiration_year");
1477 form
.fields
.push_back(field
);
1479 // Add checkable field.
1480 FormFieldData checkable_field
;
1481 checkable_field
.is_checkable
= true;
1482 checkable_field
.label
= ASCIIToUTF16("Checkable1");
1483 checkable_field
.name
= ASCIIToUTF16("Checkable1");
1484 form
.fields
.push_back(checkable_field
);
1486 ScopedVector
<FormStructure
> forms
;
1487 forms
.push_back(new FormStructure(form
));
1488 std::vector
<std::string
> encoded_signatures
;
1489 std::string encoded_xml
;
1490 const char kSignature1
[] = "11337937696949187602";
1491 const char kResponse1
[] = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
1492 "<autofillquery clientversion=\"6.1.1715.1442/en (GGLL)\">"
1493 "<form signature=\"11337937696949187602\">"
1494 "<field signature=\"412125936\" name=\"name_on_card\" type=\"text\""
1495 " label=\"Name on Card\"/><field signature=\"1917667676\""
1496 " name=\"billing_address\" type=\"text\" label=\"Address\"/>"
1497 "<field signature=\"2226358947\" name=\"card_number\" type=\"text\""
1498 " label=\"Card Number\"/><field signature=\"747221617\""
1499 " name=\"expiration_month\" type=\"text\" label=\"Expiration Date\"/>"
1500 "<field signature=\"4108155786\" name=\"expiration_year\" type=\"text\""
1501 " label=\"Expiration Year\"/></form></autofillquery>";
1502 ASSERT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
1503 &encoded_signatures
,
1505 ASSERT_EQ(1U, encoded_signatures
.size());
1506 EXPECT_EQ(kSignature1
, encoded_signatures
[0]);
1507 EXPECT_EQ(kResponse1
, encoded_xml
);
1509 // Add the same form, only one will be encoded, so EncodeQueryRequest() should
1510 // return the same data.
1511 forms
.push_back(new FormStructure(form
));
1512 ASSERT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
1513 &encoded_signatures
,
1515 ASSERT_EQ(1U, encoded_signatures
.size());
1516 EXPECT_EQ(kSignature1
, encoded_signatures
[0]);
1517 EXPECT_EQ(kResponse1
, encoded_xml
);
1518 // Add 5 address fields - this should be still a valid form.
1519 for (size_t i
= 0; i
< 5; ++i
) {
1520 field
.label
= ASCIIToUTF16("Address");
1521 field
.name
= ASCIIToUTF16("address");
1522 form
.fields
.push_back(field
);
1525 forms
.push_back(new FormStructure(form
));
1526 ASSERT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
1527 &encoded_signatures
,
1529 ASSERT_EQ(2U, encoded_signatures
.size());
1530 EXPECT_EQ(kSignature1
, encoded_signatures
[0]);
1531 const char kSignature2
[] = "8308881815906226214";
1532 EXPECT_EQ(kSignature2
, encoded_signatures
[1]);
1533 const char kResponse2
[] = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
1534 "<autofillquery clientversion=\"6.1.1715.1442/en (GGLL)\">"
1535 "<form signature=\"11337937696949187602\"><field signature=\"412125936\""
1536 " name=\"name_on_card\" type=\"text\" label=\"Name on Card\"/>"
1537 "<field signature=\"1917667676\" name=\"billing_address\" type=\"text\""
1538 " label=\"Address\"/><field signature=\"2226358947\" name=\"card_number\""
1539 " type=\"text\" label=\"Card Number\"/>"
1540 "<field signature=\"747221617\" name=\"expiration_month\" type=\"text\""
1541 " label=\"Expiration Date\"/>"
1542 "<field signature=\"4108155786\" name=\"expiration_year\" type=\"text\""
1543 " label=\"Expiration Year\"/></form>"
1544 "<form signature=\"8308881815906226214\">"
1545 "<field signature=\"412125936\" name=\"name_on_card\" type=\"text\""
1546 " label=\"Name on Card\"/><field signature=\"1917667676\""
1547 " name=\"billing_address\" type=\"text\" label=\"Address\"/>"
1548 "<field signature=\"2226358947\" name=\"card_number\" type=\"text\""
1549 " label=\"Card Number\"/><field signature=\"747221617\""
1550 " name=\"expiration_month\" type=\"text\" label=\"Expiration Date\"/>"
1551 "<field signature=\"4108155786\" name=\"expiration_year\" type=\"text\""
1552 " label=\"Expiration Year\"/><field signature=\"509334676\" name=\"address\""
1553 " type=\"text\" label=\"Address\"/><field signature=\"509334676\""
1554 " name=\"address\" type=\"text\" label=\"Address\"/>"
1555 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1556 " label=\"Address\"/><field signature=\"509334676\" name=\"address\""
1557 " type=\"text\" label=\"Address\"/><field signature=\"509334676\""
1558 " name=\"address\" type=\"text\" label=\"Address\"/></form></autofillquery>";
1559 EXPECT_EQ(kResponse2
, encoded_xml
);
1561 FormData
malformed_form(form
);
1562 // Add 50 address fields - the form is not valid anymore, but previous ones
1563 // are. The result should be the same as in previous test.
1564 for (size_t i
= 0; i
< 50; ++i
) {
1565 field
.label
= ASCIIToUTF16("Address");
1566 field
.name
= ASCIIToUTF16("address");
1567 malformed_form
.fields
.push_back(field
);
1570 forms
.push_back(new FormStructure(malformed_form
));
1571 ASSERT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
1572 &encoded_signatures
,
1574 ASSERT_EQ(2U, encoded_signatures
.size());
1575 EXPECT_EQ(kSignature1
, encoded_signatures
[0]);
1576 EXPECT_EQ(kSignature2
, encoded_signatures
[1]);
1577 EXPECT_EQ(kResponse2
, encoded_xml
);
1579 // Check that we fail if there are only bad form(s).
1580 ScopedVector
<FormStructure
> bad_forms
;
1581 bad_forms
.push_back(new FormStructure(malformed_form
));
1582 EXPECT_FALSE(FormStructure::EncodeQueryRequest(bad_forms
.get(),
1583 &encoded_signatures
,
1585 EXPECT_EQ(0U, encoded_signatures
.size());
1586 EXPECT_EQ("", encoded_xml
);
1589 TEST_F(FormStructureTest
, EncodeUploadRequest
) {
1590 scoped_ptr
<FormStructure
> form_structure
;
1591 std::vector
<ServerFieldTypeSet
> possible_field_types
;
1593 form_structure
.reset(new FormStructure(form
));
1594 form_structure
->DetermineHeuristicTypes();
1596 FormFieldData field
;
1597 field
.form_control_type
= "text";
1599 field
.label
= ASCIIToUTF16("First Name");
1600 field
.name
= ASCIIToUTF16("firstname");
1601 form
.fields
.push_back(field
);
1602 possible_field_types
.push_back(ServerFieldTypeSet());
1603 possible_field_types
.back().insert(NAME_FIRST
);
1605 field
.label
= ASCIIToUTF16("Last Name");
1606 field
.name
= ASCIIToUTF16("lastname");
1607 form
.fields
.push_back(field
);
1608 possible_field_types
.push_back(ServerFieldTypeSet());
1609 possible_field_types
.back().insert(NAME_LAST
);
1611 field
.label
= ASCIIToUTF16("Email");
1612 field
.name
= ASCIIToUTF16("email");
1613 field
.form_control_type
= "email";
1614 form
.fields
.push_back(field
);
1615 possible_field_types
.push_back(ServerFieldTypeSet());
1616 possible_field_types
.back().insert(EMAIL_ADDRESS
);
1618 field
.label
= ASCIIToUTF16("Phone");
1619 field
.name
= ASCIIToUTF16("phone");
1620 field
.form_control_type
= "number";
1621 form
.fields
.push_back(field
);
1622 possible_field_types
.push_back(ServerFieldTypeSet());
1623 possible_field_types
.back().insert(PHONE_HOME_WHOLE_NUMBER
);
1625 field
.label
= ASCIIToUTF16("Country");
1626 field
.name
= ASCIIToUTF16("country");
1627 field
.form_control_type
= "select-one";
1628 form
.fields
.push_back(field
);
1629 possible_field_types
.push_back(ServerFieldTypeSet());
1630 possible_field_types
.back().insert(ADDRESS_HOME_COUNTRY
);
1632 // Add checkable field.
1633 FormFieldData checkable_field
;
1634 checkable_field
.is_checkable
= true;
1635 checkable_field
.label
= ASCIIToUTF16("Checkable1");
1636 checkable_field
.name
= ASCIIToUTF16("Checkable1");
1637 form
.fields
.push_back(checkable_field
);
1638 possible_field_types
.push_back(ServerFieldTypeSet());
1639 possible_field_types
.back().insert(ADDRESS_HOME_COUNTRY
);
1641 form_structure
.reset(new FormStructure(form
));
1643 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
1644 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
1645 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
1647 ServerFieldTypeSet available_field_types
;
1648 available_field_types
.insert(NAME_FIRST
);
1649 available_field_types
.insert(NAME_LAST
);
1650 available_field_types
.insert(ADDRESS_HOME_LINE1
);
1651 available_field_types
.insert(ADDRESS_HOME_LINE2
);
1652 available_field_types
.insert(ADDRESS_HOME_COUNTRY
);
1653 available_field_types
.insert(ADDRESS_BILLING_LINE1
);
1654 available_field_types
.insert(ADDRESS_BILLING_LINE2
);
1655 available_field_types
.insert(EMAIL_ADDRESS
);
1656 available_field_types
.insert(PHONE_HOME_WHOLE_NUMBER
);
1658 std::string encoded_xml
;
1659 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, false,
1660 std::string(), &encoded_xml
));
1661 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
1662 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
1663 " formsignature=\"8736493185895608956\" autofillused=\"false\""
1664 " datapresent=\"144200030e\">"
1665 "<field signature=\"3763331450\" name=\"firstname\" type=\"text\""
1666 " label=\"First Name\" autofilltype=\"3\"/>"
1667 "<field signature=\"3494530716\" name=\"lastname\" type=\"text\""
1668 " label=\"Last Name\" autofilltype=\"5\"/>"
1669 "<field signature=\"1029417091\" name=\"email\" type=\"email\""
1670 " label=\"Email\" autofilltype=\"9\"/>"
1671 "<field signature=\"466116101\" name=\"phone\" type=\"number\""
1672 " label=\"Phone\" autofilltype=\"14\"/>"
1673 "<field signature=\"2799270304\" name=\"country\""
1674 " type=\"select-one\" label=\"Country\" autofilltype=\"36\"/>"
1675 "</autofillupload>",
1677 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, true,
1678 std::string(), &encoded_xml
));
1679 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
1680 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
1681 " formsignature=\"8736493185895608956\" autofillused=\"true\""
1682 " datapresent=\"144200030e\">"
1683 "<field signature=\"3763331450\" name=\"firstname\" type=\"text\""
1684 " label=\"First Name\" autofilltype=\"3\"/>"
1685 "<field signature=\"3494530716\" name=\"lastname\" type=\"text\""
1686 " label=\"Last Name\" autofilltype=\"5\"/>"
1687 "<field signature=\"1029417091\" name=\"email\" type=\"email\""
1688 " label=\"Email\" autofilltype=\"9\"/>"
1689 "<field signature=\"466116101\" name=\"phone\" type=\"number\""
1690 " label=\"Phone\" autofilltype=\"14\"/>"
1691 "<field signature=\"2799270304\" name=\"country\""
1692 " type=\"select-one\" label=\"Country\" autofilltype=\"36\"/>"
1693 "</autofillupload>",
1696 // Add 2 address fields - this should be still a valid form.
1697 for (size_t i
= 0; i
< 2; ++i
) {
1698 field
.label
= ASCIIToUTF16("Address");
1699 field
.name
= ASCIIToUTF16("address");
1700 field
.form_control_type
= "text";
1701 form
.fields
.push_back(field
);
1702 possible_field_types
.push_back(ServerFieldTypeSet());
1703 possible_field_types
.back().insert(ADDRESS_HOME_LINE1
);
1704 possible_field_types
.back().insert(ADDRESS_HOME_LINE2
);
1705 possible_field_types
.back().insert(ADDRESS_BILLING_LINE1
);
1706 possible_field_types
.back().insert(ADDRESS_BILLING_LINE2
);
1709 form_structure
.reset(new FormStructure(form
));
1710 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
1711 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
1712 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
1714 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, false,
1715 std::string(), &encoded_xml
));
1716 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
1717 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
1718 " formsignature=\"7816485729218079147\" autofillused=\"false\""
1719 " datapresent=\"144200030e\">"
1720 "<field signature=\"3763331450\" name=\"firstname\" type=\"text\""
1721 " label=\"First Name\" autofilltype=\"3\"/>"
1722 "<field signature=\"3494530716\" name=\"lastname\" type=\"text\""
1723 " label=\"Last Name\" autofilltype=\"5\"/>"
1724 "<field signature=\"1029417091\" name=\"email\" type=\"email\""
1725 " label=\"Email\" autofilltype=\"9\"/>"
1726 "<field signature=\"466116101\" name=\"phone\" type=\"number\""
1727 " label=\"Phone\" autofilltype=\"14\"/>"
1728 "<field signature=\"2799270304\" name=\"country\""
1729 " type=\"select-one\" label=\"Country\" autofilltype=\"36\"/>"
1730 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1731 " label=\"Address\" autofilltype=\"30\"/>"
1732 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1733 " label=\"Address\" autofilltype=\"31\"/>"
1734 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1735 " label=\"Address\" autofilltype=\"37\"/>"
1736 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1737 " label=\"Address\" autofilltype=\"38\"/>"
1738 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1739 " label=\"Address\" autofilltype=\"30\"/>"
1740 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1741 " label=\"Address\" autofilltype=\"31\"/>"
1742 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1743 " label=\"Address\" autofilltype=\"37\"/>"
1744 "<field signature=\"509334676\" name=\"address\" type=\"text\""
1745 " label=\"Address\" autofilltype=\"38\"/></autofillupload>",
1748 // Add 50 address fields - now the form is invalid, as it has too many fields.
1749 for (size_t i
= 0; i
< 50; ++i
) {
1750 field
.label
= ASCIIToUTF16("Address");
1751 field
.name
= ASCIIToUTF16("address");
1752 field
.form_control_type
= "text";
1753 form
.fields
.push_back(field
);
1754 possible_field_types
.push_back(ServerFieldTypeSet());
1755 possible_field_types
.back().insert(ADDRESS_HOME_LINE1
);
1756 possible_field_types
.back().insert(ADDRESS_HOME_LINE2
);
1757 possible_field_types
.back().insert(ADDRESS_BILLING_LINE1
);
1758 possible_field_types
.back().insert(ADDRESS_BILLING_LINE2
);
1760 form_structure
.reset(new FormStructure(form
));
1761 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
1762 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
1763 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
1764 EXPECT_FALSE(form_structure
->EncodeUploadRequest(
1765 available_field_types
, false, std::string(), &encoded_xml
));
1768 TEST_F(FormStructureTest
,
1769 EncodeUploadRequestWithAdditionalPasswordFormSignature
) {
1770 scoped_ptr
<FormStructure
> form_structure
;
1771 std::vector
<ServerFieldTypeSet
> possible_field_types
;
1773 form_structure
.reset(new FormStructure(form
));
1774 form_structure
->DetermineHeuristicTypes();
1776 FormFieldData field
;
1777 field
.label
= ASCIIToUTF16("First Name");
1778 field
.name
= ASCIIToUTF16("firstname");
1779 field
.autocomplete_attribute
= "given-name";
1780 form
.fields
.push_back(field
);
1781 possible_field_types
.push_back(ServerFieldTypeSet());
1782 possible_field_types
.back().insert(NAME_FIRST
);
1784 field
.label
= ASCIIToUTF16("Last Name");
1785 field
.name
= ASCIIToUTF16("lastname");
1786 field
.autocomplete_attribute
= "family-name";
1787 form
.fields
.push_back(field
);
1788 possible_field_types
.push_back(ServerFieldTypeSet());
1789 possible_field_types
.back().insert(NAME_LAST
);
1791 field
.label
= ASCIIToUTF16("Email");
1792 field
.name
= ASCIIToUTF16("email");
1793 field
.form_control_type
= "email";
1794 field
.autocomplete_attribute
= "email";
1795 form
.fields
.push_back(field
);
1796 possible_field_types
.push_back(ServerFieldTypeSet());
1797 possible_field_types
.back().insert(EMAIL_ADDRESS
);
1799 field
.label
= ASCIIToUTF16("username");
1800 field
.name
= ASCIIToUTF16("username");
1801 field
.form_control_type
= "text";
1802 form
.fields
.push_back(field
);
1803 possible_field_types
.push_back(ServerFieldTypeSet());
1804 possible_field_types
.back().insert(USERNAME
);
1806 field
.label
= ASCIIToUTF16("password");
1807 field
.name
= ASCIIToUTF16("password");
1808 field
.form_control_type
= "password";
1809 form
.fields
.push_back(field
);
1810 possible_field_types
.push_back(ServerFieldTypeSet());
1811 possible_field_types
.back().insert(ACCOUNT_CREATION_PASSWORD
);
1813 form_structure
.reset(new FormStructure(form
));
1815 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
1816 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
1817 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
1819 ServerFieldTypeSet available_field_types
;
1820 available_field_types
.insert(NAME_FIRST
);
1821 available_field_types
.insert(NAME_LAST
);
1822 available_field_types
.insert(EMAIL_ADDRESS
);
1823 available_field_types
.insert(USERNAME
);
1824 available_field_types
.insert(ACCOUNT_CREATION_PASSWORD
);
1826 std::string encoded_xml
;
1827 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, true,
1828 "42", &encoded_xml
));
1830 "<?xml version=\"1.0\" encoding=\"UTF-8\"?><autofillupload "
1831 "clientversion=\"6.1.1715.1442/en (GGLL)\" "
1832 "formsignature=\"5810032074788446513\" autofillused=\"true\" "
1833 "datapresent=\"1440000000000000000802\" "
1834 "loginformsignature=\"42\"><field signature=\"4224610201\" "
1835 "name=\"firstname\" type=\"\" label=\"First Name\" "
1836 "autocomplete=\"given-name\" autofilltype=\"3\"/><field "
1837 "signature=\"2786066110\" name=\"lastname\" type=\"\" label=\"Last "
1838 "Name\" autocomplete=\"family-name\" autofilltype=\"5\"/><field "
1839 "signature=\"1029417091\" name=\"email\" type=\"email\" label=\"Email\" "
1840 "autocomplete=\"email\" autofilltype=\"9\"/><field "
1841 "signature=\"239111655\" name=\"username\" type=\"text\" "
1842 "label=\"username\" autocomplete=\"email\" autofilltype=\"86\"/><field "
1843 "signature=\"2051817934\" name=\"password\" type=\"password\" "
1844 "label=\"password\" autocomplete=\"email\" "
1845 "autofilltype=\"76\"/></autofillupload>",
1849 TEST_F(FormStructureTest
, EncodeUploadRequest_WithAutocomplete
) {
1850 scoped_ptr
<FormStructure
> form_structure
;
1851 std::vector
<ServerFieldTypeSet
> possible_field_types
;
1853 form_structure
.reset(new FormStructure(form
));
1854 form_structure
->DetermineHeuristicTypes();
1856 FormFieldData field
;
1857 field
.form_control_type
= "text";
1859 field
.label
= ASCIIToUTF16("First Name");
1860 field
.name
= ASCIIToUTF16("firstname");
1861 field
.autocomplete_attribute
= "given-name";
1862 form
.fields
.push_back(field
);
1863 possible_field_types
.push_back(ServerFieldTypeSet());
1864 possible_field_types
.back().insert(NAME_FIRST
);
1866 field
.label
= ASCIIToUTF16("Last Name");
1867 field
.name
= ASCIIToUTF16("lastname");
1868 field
.autocomplete_attribute
= "family-name";
1869 form
.fields
.push_back(field
);
1870 possible_field_types
.push_back(ServerFieldTypeSet());
1871 possible_field_types
.back().insert(NAME_LAST
);
1873 field
.label
= ASCIIToUTF16("Email");
1874 field
.name
= ASCIIToUTF16("email");
1875 field
.form_control_type
= "email";
1876 field
.autocomplete_attribute
= "email";
1877 form
.fields
.push_back(field
);
1878 possible_field_types
.push_back(ServerFieldTypeSet());
1879 possible_field_types
.back().insert(EMAIL_ADDRESS
);
1881 form_structure
.reset(new FormStructure(form
));
1883 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
1884 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
1885 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
1887 ServerFieldTypeSet available_field_types
;
1888 available_field_types
.insert(NAME_FIRST
);
1889 available_field_types
.insert(NAME_LAST
);
1890 available_field_types
.insert(EMAIL_ADDRESS
);
1892 std::string encoded_xml
;
1893 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, true,
1894 std::string(), &encoded_xml
));
1895 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
1896 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
1897 " formsignature=\"14746822798145140279\" autofillused=\"true\""
1898 " datapresent=\"1440\">"
1899 "<field signature=\"3763331450\" name=\"firstname\" type=\"text\""
1900 " label=\"First Name\" autocomplete=\"given-name\""
1901 " autofilltype=\"3\"/>"
1902 "<field signature=\"3494530716\" name=\"lastname\" type=\"text\""
1903 " label=\"Last Name\" autocomplete=\"family-name\""
1904 " autofilltype=\"5\"/><field signature=\"1029417091\""
1905 " name=\"email\" type=\"email\" label=\"Email\""
1906 " autocomplete=\"email\" autofilltype=\"9\"/></autofillupload>",
1910 TEST_F(FormStructureTest
, EncodeUploadRequest_WithLabels
) {
1911 scoped_ptr
<FormStructure
> form_structure
;
1912 std::vector
<ServerFieldTypeSet
> possible_field_types
;
1914 form_structure
.reset(new FormStructure(form
));
1915 form_structure
->DetermineHeuristicTypes();
1917 FormFieldData field
;
1918 field
.form_control_type
= "text";
1920 // No label for the first field.
1921 form
.fields
.push_back(field
);
1922 possible_field_types
.push_back(ServerFieldTypeSet());
1923 possible_field_types
.back().insert(NAME_FIRST
);
1925 field
.label
= ASCIIToUTF16("Last Name");
1926 form
.fields
.push_back(field
);
1927 possible_field_types
.push_back(ServerFieldTypeSet());
1928 possible_field_types
.back().insert(NAME_LAST
);
1930 field
.label
= ASCIIToUTF16("Email");
1931 form
.fields
.push_back(field
);
1932 possible_field_types
.push_back(ServerFieldTypeSet());
1933 possible_field_types
.back().insert(EMAIL_ADDRESS
);
1935 form_structure
.reset(new FormStructure(form
));
1937 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
1938 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
1939 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
1941 ServerFieldTypeSet available_field_types
;
1942 available_field_types
.insert(NAME_FIRST
);
1943 available_field_types
.insert(NAME_LAST
);
1944 available_field_types
.insert(EMAIL_ADDRESS
);
1946 std::string encoded_xml
;
1947 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, true,
1948 std::string(), &encoded_xml
));
1949 // Expected that the first field does not send the label but others do.
1950 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
1951 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
1952 " formsignature=\"6949133589768631292\" autofillused=\"true\""
1953 " datapresent=\"1440\">"
1954 "<field signature=\"1318412689\" type=\"text\" autofilltype=\"3\"/>"
1955 "<field signature=\"1318412689\" type=\"text\" label=\"Last Name\""
1956 " autofilltype=\"5\"/><field signature=\"1318412689\" type=\"text\""
1957 " label=\"Email\" autofilltype=\"9\"/></autofillupload>",
1961 TEST_F(FormStructureTest
, EncodeUploadRequestPartialMetadata
) {
1962 scoped_ptr
<FormStructure
> form_structure
;
1963 std::vector
<ServerFieldTypeSet
> possible_field_types
;
1965 form_structure
.reset(new FormStructure(form
));
1966 form_structure
->DetermineHeuristicTypes();
1968 FormFieldData field
;
1969 field
.form_control_type
= "text";
1971 // Some fields don't have "name" or "autocomplete" attributes, and some have
1974 form
.fields
.push_back(field
);
1975 possible_field_types
.push_back(ServerFieldTypeSet());
1976 possible_field_types
.back().insert(NAME_FIRST
);
1978 field
.label
= ASCIIToUTF16("Last Name");
1979 field
.name
= ASCIIToUTF16("lastname");
1980 field
.autocomplete_attribute
= "family-name";
1981 form
.fields
.push_back(field
);
1982 possible_field_types
.push_back(ServerFieldTypeSet());
1983 possible_field_types
.back().insert(NAME_LAST
);
1985 field
.label
= ASCIIToUTF16("Email");
1986 field
.form_control_type
= "email";
1987 field
.autocomplete_attribute
= "email";
1988 form
.fields
.push_back(field
);
1989 possible_field_types
.push_back(ServerFieldTypeSet());
1990 possible_field_types
.back().insert(EMAIL_ADDRESS
);
1992 form_structure
.reset(new FormStructure(form
));
1994 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
1995 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
1996 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
1998 ServerFieldTypeSet available_field_types
;
1999 available_field_types
.insert(NAME_FIRST
);
2000 available_field_types
.insert(NAME_LAST
);
2001 available_field_types
.insert(EMAIL_ADDRESS
);
2003 std::string encoded_xml
;
2004 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, true,
2005 std::string(), &encoded_xml
));
2006 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2007 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2008 " formsignature=\"13043654279838250996\" autofillused=\"true\""
2009 " datapresent=\"1440\"><field signature=\"1318412689\""
2010 " type=\"text\" autofilltype=\"3\"/>"
2011 "<field signature=\"3494530716\" name=\"lastname\" type=\"text\""
2012 " label=\"Last Name\" autocomplete=\"family-name\""
2013 " autofilltype=\"5\"/>"
2014 "<field signature=\"1545468175\" name=\"lastname\" type=\"email\""
2015 " label=\"Email\" autocomplete=\"email\" autofilltype=\"9\"/>"
2016 "</autofillupload>",
2020 // Sending field metadata to the server is disabled.
2021 TEST_F(FormStructureTest
, EncodeUploadRequest_DisabledMetadataTrial
) {
2022 DisableAutofillMetadataFieldTrial();
2024 scoped_ptr
<FormStructure
> form_structure
;
2025 std::vector
<ServerFieldTypeSet
> possible_field_types
;
2027 form_structure
.reset(new FormStructure(form
));
2028 form_structure
->DetermineHeuristicTypes();
2030 FormFieldData field
;
2031 field
.form_control_type
= "text";
2033 field
.label
= ASCIIToUTF16("First Name");
2034 field
.name
= ASCIIToUTF16("firstname");
2035 field
.autocomplete_attribute
= "given-name";
2036 form
.fields
.push_back(field
);
2037 possible_field_types
.push_back(ServerFieldTypeSet());
2038 possible_field_types
.back().insert(NAME_FIRST
);
2040 field
.label
= ASCIIToUTF16("Last Name");
2041 field
.name
= ASCIIToUTF16("lastname");
2042 field
.autocomplete_attribute
= "family-name";
2043 form
.fields
.push_back(field
);
2044 possible_field_types
.push_back(ServerFieldTypeSet());
2045 possible_field_types
.back().insert(NAME_LAST
);
2047 field
.label
= ASCIIToUTF16("Email");
2048 field
.name
= ASCIIToUTF16("email");
2049 field
.form_control_type
= "email";
2050 field
.autocomplete_attribute
= "email";
2051 form
.fields
.push_back(field
);
2052 possible_field_types
.push_back(ServerFieldTypeSet());
2053 possible_field_types
.back().insert(EMAIL_ADDRESS
);
2055 form_structure
.reset(new FormStructure(form
));
2057 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
2058 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
2059 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
2061 ServerFieldTypeSet available_field_types
;
2062 available_field_types
.insert(NAME_FIRST
);
2063 available_field_types
.insert(NAME_LAST
);
2064 available_field_types
.insert(EMAIL_ADDRESS
);
2066 std::string encoded_xml
;
2067 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, true,
2068 std::string(), &encoded_xml
));
2069 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2070 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2071 " formsignature=\"14746822798145140279\" autofillused=\"true\""
2072 " datapresent=\"1440\"><field signature=\"3763331450\""
2073 " autofilltype=\"3\"/><field signature=\"3494530716\""
2074 " autofilltype=\"5\"/><field signature=\"1029417091\""
2075 " autofilltype=\"9\"/></autofillupload>",
2079 TEST_F(FormStructureTest
, EncodeFieldAssignments
) {
2080 scoped_ptr
<FormStructure
> form_structure
;
2081 std::vector
<ServerFieldTypeSet
> possible_field_types
;
2083 form_structure
.reset(new FormStructure(form
));
2084 form_structure
->DetermineHeuristicTypes();
2086 FormFieldData field
;
2087 field
.form_control_type
= "text";
2089 field
.label
= ASCIIToUTF16("First Name");
2090 field
.name
= ASCIIToUTF16("firstname");
2091 form
.fields
.push_back(field
);
2092 possible_field_types
.push_back(ServerFieldTypeSet());
2093 possible_field_types
.back().insert(NAME_FIRST
);
2095 field
.label
= ASCIIToUTF16("Last Name");
2096 field
.name
= ASCIIToUTF16("lastname");
2097 form
.fields
.push_back(field
);
2098 possible_field_types
.push_back(ServerFieldTypeSet());
2099 possible_field_types
.back().insert(NAME_LAST
);
2101 field
.label
= ASCIIToUTF16("Email");
2102 field
.name
= ASCIIToUTF16("email");
2103 field
.form_control_type
= "email";
2104 form
.fields
.push_back(field
);
2105 possible_field_types
.push_back(ServerFieldTypeSet());
2106 possible_field_types
.back().insert(EMAIL_ADDRESS
);
2108 field
.label
= ASCIIToUTF16("Phone");
2109 field
.name
= ASCIIToUTF16("phone");
2110 field
.form_control_type
= "number";
2111 form
.fields
.push_back(field
);
2112 possible_field_types
.push_back(ServerFieldTypeSet());
2113 possible_field_types
.back().insert(PHONE_HOME_WHOLE_NUMBER
);
2115 field
.label
= ASCIIToUTF16("Country");
2116 field
.name
= ASCIIToUTF16("country");
2117 field
.form_control_type
= "select-one";
2118 form
.fields
.push_back(field
);
2119 possible_field_types
.push_back(ServerFieldTypeSet());
2120 possible_field_types
.back().insert(ADDRESS_HOME_COUNTRY
);
2122 // Add checkable field.
2123 FormFieldData checkable_field
;
2124 checkable_field
.is_checkable
= true;
2125 checkable_field
.label
= ASCIIToUTF16("Checkable1");
2126 checkable_field
.name
= ASCIIToUTF16("Checkable1");
2127 form
.fields
.push_back(checkable_field
);
2128 possible_field_types
.push_back(ServerFieldTypeSet());
2129 possible_field_types
.back().insert(ADDRESS_HOME_COUNTRY
);
2131 form_structure
.reset(new FormStructure(form
));
2133 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
2134 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
2135 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
2137 ServerFieldTypeSet available_field_types
;
2138 available_field_types
.insert(NAME_FIRST
);
2139 available_field_types
.insert(NAME_LAST
);
2140 available_field_types
.insert(ADDRESS_HOME_LINE1
);
2141 available_field_types
.insert(ADDRESS_HOME_LINE2
);
2142 available_field_types
.insert(ADDRESS_HOME_COUNTRY
);
2143 available_field_types
.insert(ADDRESS_BILLING_LINE1
);
2144 available_field_types
.insert(ADDRESS_BILLING_LINE2
);
2145 available_field_types
.insert(EMAIL_ADDRESS
);
2146 available_field_types
.insert(PHONE_HOME_WHOLE_NUMBER
);
2148 std::string encoded_xml
;
2149 EXPECT_TRUE(form_structure
->EncodeFieldAssignments(
2150 available_field_types
, &encoded_xml
));
2152 "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2153 "<fieldassignments formsignature=\"8736493185895608956\">"
2154 "<fields fieldid=\"3763331450\" fieldtype=\"3\" name=\"firstname\"/>"
2155 "<fields fieldid=\"3494530716\" fieldtype=\"5\" name=\"lastname\"/>"
2156 "<fields fieldid=\"1029417091\" fieldtype=\"9\" name=\"email\"/>"
2157 "<fields fieldid=\"466116101\" fieldtype=\"14\" name=\"phone\"/>"
2158 "<fields fieldid=\"2799270304\" fieldtype=\"36\" name=\"country\"/>"
2159 "<fields fieldid=\"3410250678\" fieldtype=\"36\" name=\"Checkable1\"/>"
2160 "</fieldassignments>",
2163 // Add 2 address fields - this should be still a valid form.
2164 for (size_t i
= 0; i
< 2; ++i
) {
2165 field
.label
= ASCIIToUTF16("Address");
2166 field
.name
= ASCIIToUTF16("address");
2167 field
.form_control_type
= "text";
2168 form
.fields
.push_back(field
);
2169 possible_field_types
.push_back(ServerFieldTypeSet());
2170 possible_field_types
.back().insert(ADDRESS_HOME_LINE1
);
2171 possible_field_types
.back().insert(ADDRESS_HOME_LINE2
);
2172 possible_field_types
.back().insert(ADDRESS_BILLING_LINE1
);
2173 possible_field_types
.back().insert(ADDRESS_BILLING_LINE2
);
2176 form_structure
.reset(new FormStructure(form
));
2177 ASSERT_EQ(form_structure
->field_count(), possible_field_types
.size());
2178 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
2179 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
2181 EXPECT_TRUE(form_structure
->EncodeFieldAssignments(
2182 available_field_types
, &encoded_xml
));
2184 "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2185 "<fieldassignments formsignature=\"7816485729218079147\">"
2186 "<fields fieldid=\"3763331450\" fieldtype=\"3\" name=\"firstname\"/>"
2187 "<fields fieldid=\"3494530716\" fieldtype=\"5\" name=\"lastname\"/>"
2188 "<fields fieldid=\"1029417091\" fieldtype=\"9\" name=\"email\"/>"
2189 "<fields fieldid=\"466116101\" fieldtype=\"14\" name=\"phone\"/>"
2190 "<fields fieldid=\"2799270304\" fieldtype=\"36\" name=\"country\"/>"
2191 "<fields fieldid=\"3410250678\" fieldtype=\"36\" name=\"Checkable1\"/>"
2192 "<fields fieldid=\"509334676\" fieldtype=\"30\" name=\"address\"/>"
2193 "<fields fieldid=\"509334676\" fieldtype=\"31\" name=\"address\"/>"
2194 "<fields fieldid=\"509334676\" fieldtype=\"37\" name=\"address\"/>"
2195 "<fields fieldid=\"509334676\" fieldtype=\"38\" name=\"address\"/>"
2196 "<fields fieldid=\"509334676\" fieldtype=\"30\" name=\"address\"/>"
2197 "<fields fieldid=\"509334676\" fieldtype=\"31\" name=\"address\"/>"
2198 "<fields fieldid=\"509334676\" fieldtype=\"37\" name=\"address\"/>"
2199 "<fields fieldid=\"509334676\" fieldtype=\"38\" name=\"address\"/>"
2200 "</fieldassignments>",
2204 // Check that we compute the "datapresent" string correctly for the given
2205 // |available_types|.
2206 TEST_F(FormStructureTest
, CheckDataPresence
) {
2209 FormFieldData field
;
2210 field
.form_control_type
= "text";
2212 field
.label
= ASCIIToUTF16("First Name");
2213 field
.name
= ASCIIToUTF16("first");
2214 form
.fields
.push_back(field
);
2216 field
.label
= ASCIIToUTF16("Last Name");
2217 field
.name
= ASCIIToUTF16("last");
2218 form
.fields
.push_back(field
);
2220 field
.label
= ASCIIToUTF16("Email");
2221 field
.name
= ASCIIToUTF16("email");
2222 form
.fields
.push_back(field
);
2224 FormStructure
form_structure(form
);
2226 ServerFieldTypeSet unknown_type
;
2227 unknown_type
.insert(UNKNOWN_TYPE
);
2228 for (size_t i
= 0; i
< form_structure
.field_count(); ++i
)
2229 form_structure
.field(i
)->set_possible_types(unknown_type
);
2231 // No available types.
2232 // datapresent should be "" == trimmmed(0x0000000000000000) ==
2233 // 0b0000000000000000000000000000000000000000000000000000000000000000
2234 ServerFieldTypeSet available_field_types
;
2236 std::string encoded_xml
;
2237 EXPECT_TRUE(form_structure
.EncodeUploadRequest(available_field_types
, false,
2238 std::string(), &encoded_xml
));
2239 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2240 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2241 " formsignature=\"6402244543831589061\" autofillused=\"false\""
2242 " datapresent=\"\">"
2243 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2244 " label=\"First Name\" autofilltype=\"1\"/>"
2245 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2246 " label=\"Last Name\" autofilltype=\"1\"/>"
2247 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2248 " label=\"Email\" autofilltype=\"1\"/></autofillupload>",
2251 // Only a few types available.
2252 // datapresent should be "1540000240" == trimmmed(0x1540000240000000) ==
2253 // 0b0001010101000000000000000000001001000000000000000000000000000000
2254 // The set bits are:
2258 // 9 == EMAIL_ADDRESS
2259 // 30 == ADDRESS_HOME_LINE1
2260 // 33 == ADDRESS_HOME_CITY
2261 available_field_types
.clear();
2262 available_field_types
.insert(NAME_FIRST
);
2263 available_field_types
.insert(NAME_LAST
);
2264 available_field_types
.insert(NAME_FULL
);
2265 available_field_types
.insert(EMAIL_ADDRESS
);
2266 available_field_types
.insert(ADDRESS_HOME_LINE1
);
2267 available_field_types
.insert(ADDRESS_HOME_CITY
);
2269 EXPECT_TRUE(form_structure
.EncodeUploadRequest(available_field_types
, false,
2270 std::string(), &encoded_xml
));
2271 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2272 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2273 " formsignature=\"6402244543831589061\" autofillused=\"false\""
2274 " datapresent=\"1540000240\">"
2275 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2276 " label=\"First Name\" autofilltype=\"1\"/>"
2277 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2278 " label=\"Last Name\" autofilltype=\"1\"/>"
2279 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2280 " label=\"Email\" autofilltype=\"1\"/></autofillupload>",
2283 // All supported non-credit card types available.
2284 // datapresent should be "1f7e000378000008" == trimmmed(0x1f7e000378000008) ==
2285 // 0b0001111101111110000000000000001101111000000000000000000000001000
2286 // The set bits are:
2290 // 6 == NAME_MIDDLE_INITIAL
2292 // 9 == EMAIL_ADDRESS
2293 // 10 == PHONE_HOME_NUMBER,
2294 // 11 == PHONE_HOME_CITY_CODE,
2295 // 12 == PHONE_HOME_COUNTRY_CODE,
2296 // 13 == PHONE_HOME_CITY_AND_NUMBER,
2297 // 14 == PHONE_HOME_WHOLE_NUMBER,
2298 // 30 == ADDRESS_HOME_LINE1
2299 // 31 == ADDRESS_HOME_LINE2
2300 // 33 == ADDRESS_HOME_CITY
2301 // 34 == ADDRESS_HOME_STATE
2302 // 35 == ADDRESS_HOME_ZIP
2303 // 36 == ADDRESS_HOME_COUNTRY
2304 // 60 == COMPANY_NAME
2305 available_field_types
.clear();
2306 available_field_types
.insert(NAME_FIRST
);
2307 available_field_types
.insert(NAME_MIDDLE
);
2308 available_field_types
.insert(NAME_LAST
);
2309 available_field_types
.insert(NAME_MIDDLE_INITIAL
);
2310 available_field_types
.insert(NAME_FULL
);
2311 available_field_types
.insert(EMAIL_ADDRESS
);
2312 available_field_types
.insert(PHONE_HOME_NUMBER
);
2313 available_field_types
.insert(PHONE_HOME_CITY_CODE
);
2314 available_field_types
.insert(PHONE_HOME_COUNTRY_CODE
);
2315 available_field_types
.insert(PHONE_HOME_CITY_AND_NUMBER
);
2316 available_field_types
.insert(PHONE_HOME_WHOLE_NUMBER
);
2317 available_field_types
.insert(ADDRESS_HOME_LINE1
);
2318 available_field_types
.insert(ADDRESS_HOME_LINE2
);
2319 available_field_types
.insert(ADDRESS_HOME_CITY
);
2320 available_field_types
.insert(ADDRESS_HOME_STATE
);
2321 available_field_types
.insert(ADDRESS_HOME_ZIP
);
2322 available_field_types
.insert(ADDRESS_HOME_COUNTRY
);
2323 available_field_types
.insert(COMPANY_NAME
);
2325 EXPECT_TRUE(form_structure
.EncodeUploadRequest(available_field_types
, false,
2326 std::string(), &encoded_xml
));
2327 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2328 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2329 " formsignature=\"6402244543831589061\" autofillused=\"false\""
2330 " datapresent=\"1f7e000378000008\">"
2331 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2332 " label=\"First Name\" autofilltype=\"1\"/>"
2333 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2334 " label=\"Last Name\" autofilltype=\"1\"/>"
2335 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2336 " label=\"Email\" autofilltype=\"1\"/></autofillupload>",
2339 // All supported credit card types available.
2340 // datapresent should be "0000000000001fc0" == trimmmed(0x0000000000001fc0) ==
2341 // 0b0000000000000000000000000000000000000000000000000001111111000000
2342 // The set bits are:
2343 // 51 == CREDIT_CARD_NAME
2344 // 52 == CREDIT_CARD_NUMBER
2345 // 53 == CREDIT_CARD_EXP_MONTH
2346 // 54 == CREDIT_CARD_EXP_2_DIGIT_YEAR
2347 // 55 == CREDIT_CARD_EXP_4_DIGIT_YEAR
2348 // 56 == CREDIT_CARD_EXP_DATE_2_DIGIT_YEAR
2349 // 57 == CREDIT_CARD_EXP_DATE_4_DIGIT_YEAR
2350 available_field_types
.clear();
2351 available_field_types
.insert(CREDIT_CARD_NAME
);
2352 available_field_types
.insert(CREDIT_CARD_NUMBER
);
2353 available_field_types
.insert(CREDIT_CARD_EXP_MONTH
);
2354 available_field_types
.insert(CREDIT_CARD_EXP_2_DIGIT_YEAR
);
2355 available_field_types
.insert(CREDIT_CARD_EXP_4_DIGIT_YEAR
);
2356 available_field_types
.insert(CREDIT_CARD_EXP_DATE_2_DIGIT_YEAR
);
2357 available_field_types
.insert(CREDIT_CARD_EXP_DATE_4_DIGIT_YEAR
);
2359 EXPECT_TRUE(form_structure
.EncodeUploadRequest(available_field_types
, false,
2360 std::string(), &encoded_xml
));
2361 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2362 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2363 " formsignature=\"6402244543831589061\" autofillused=\"false\""
2364 " datapresent=\"0000000000001fc0\">"
2365 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2366 " label=\"First Name\" autofilltype=\"1\"/>"
2367 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2368 " label=\"Last Name\" autofilltype=\"1\"/>"
2369 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2370 " label=\"Email\" autofilltype=\"1\"/></autofillupload>",
2373 // All supported types available.
2374 // datapresent should be "1f7e000378001fc8" == trimmmed(0x1f7e000378001fc8) ==
2375 // 0b0001111101111110000000000000001101111000000000000001111111001000
2376 // The set bits are:
2380 // 6 == NAME_MIDDLE_INITIAL
2382 // 9 == EMAIL_ADDRESS
2383 // 10 == PHONE_HOME_NUMBER,
2384 // 11 == PHONE_HOME_CITY_CODE,
2385 // 12 == PHONE_HOME_COUNTRY_CODE,
2386 // 13 == PHONE_HOME_CITY_AND_NUMBER,
2387 // 14 == PHONE_HOME_WHOLE_NUMBER,
2388 // 30 == ADDRESS_HOME_LINE1
2389 // 31 == ADDRESS_HOME_LINE2
2390 // 33 == ADDRESS_HOME_CITY
2391 // 34 == ADDRESS_HOME_STATE
2392 // 35 == ADDRESS_HOME_ZIP
2393 // 36 == ADDRESS_HOME_COUNTRY
2394 // 51 == CREDIT_CARD_NAME
2395 // 52 == CREDIT_CARD_NUMBER
2396 // 53 == CREDIT_CARD_EXP_MONTH
2397 // 54 == CREDIT_CARD_EXP_2_DIGIT_YEAR
2398 // 55 == CREDIT_CARD_EXP_4_DIGIT_YEAR
2399 // 56 == CREDIT_CARD_EXP_DATE_2_DIGIT_YEAR
2400 // 57 == CREDIT_CARD_EXP_DATE_4_DIGIT_YEAR
2401 // 60 == COMPANY_NAME
2402 available_field_types
.clear();
2403 available_field_types
.insert(NAME_FIRST
);
2404 available_field_types
.insert(NAME_MIDDLE
);
2405 available_field_types
.insert(NAME_LAST
);
2406 available_field_types
.insert(NAME_MIDDLE_INITIAL
);
2407 available_field_types
.insert(NAME_FULL
);
2408 available_field_types
.insert(EMAIL_ADDRESS
);
2409 available_field_types
.insert(PHONE_HOME_NUMBER
);
2410 available_field_types
.insert(PHONE_HOME_CITY_CODE
);
2411 available_field_types
.insert(PHONE_HOME_COUNTRY_CODE
);
2412 available_field_types
.insert(PHONE_HOME_CITY_AND_NUMBER
);
2413 available_field_types
.insert(PHONE_HOME_WHOLE_NUMBER
);
2414 available_field_types
.insert(ADDRESS_HOME_LINE1
);
2415 available_field_types
.insert(ADDRESS_HOME_LINE2
);
2416 available_field_types
.insert(ADDRESS_HOME_CITY
);
2417 available_field_types
.insert(ADDRESS_HOME_STATE
);
2418 available_field_types
.insert(ADDRESS_HOME_ZIP
);
2419 available_field_types
.insert(ADDRESS_HOME_COUNTRY
);
2420 available_field_types
.insert(CREDIT_CARD_NAME
);
2421 available_field_types
.insert(CREDIT_CARD_NUMBER
);
2422 available_field_types
.insert(CREDIT_CARD_EXP_MONTH
);
2423 available_field_types
.insert(CREDIT_CARD_EXP_2_DIGIT_YEAR
);
2424 available_field_types
.insert(CREDIT_CARD_EXP_4_DIGIT_YEAR
);
2425 available_field_types
.insert(CREDIT_CARD_EXP_DATE_2_DIGIT_YEAR
);
2426 available_field_types
.insert(CREDIT_CARD_EXP_DATE_4_DIGIT_YEAR
);
2427 available_field_types
.insert(COMPANY_NAME
);
2429 EXPECT_TRUE(form_structure
.EncodeUploadRequest(available_field_types
, false,
2430 std::string(), &encoded_xml
));
2431 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2432 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2433 " formsignature=\"6402244543831589061\" autofillused=\"false\""
2434 " datapresent=\"1f7e000378001fc8\">"
2435 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2436 " label=\"First Name\" autofilltype=\"1\"/>"
2437 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2438 " label=\"Last Name\" autofilltype=\"1\"/>"
2439 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2440 " label=\"Email\" autofilltype=\"1\"/></autofillupload>",
2444 TEST_F(FormStructureTest
, CheckMultipleTypes
) {
2445 // Throughout this test, datapresent should be
2446 // 0x1440000360000008 ==
2447 // 0b0001010001000000000000000000001101100000000000000000000000001000
2448 // The set bits are:
2451 // 9 == EMAIL_ADDRESS
2452 // 30 == ADDRESS_HOME_LINE1
2453 // 31 == ADDRESS_HOME_LINE2
2454 // 33 == ADDRESS_HOME_CITY
2455 // 34 == ADDRESS_HOME_STATE
2456 // 60 == COMPANY_NAME
2457 ServerFieldTypeSet available_field_types
;
2458 available_field_types
.insert(NAME_FIRST
);
2459 available_field_types
.insert(NAME_LAST
);
2460 available_field_types
.insert(EMAIL_ADDRESS
);
2461 available_field_types
.insert(ADDRESS_HOME_LINE1
);
2462 available_field_types
.insert(ADDRESS_HOME_LINE2
);
2463 available_field_types
.insert(ADDRESS_HOME_CITY
);
2464 available_field_types
.insert(ADDRESS_HOME_STATE
);
2465 available_field_types
.insert(COMPANY_NAME
);
2467 // Check that multiple types for the field are processed correctly.
2468 scoped_ptr
<FormStructure
> form_structure
;
2469 std::vector
<ServerFieldTypeSet
> possible_field_types
;
2472 FormFieldData field
;
2473 field
.form_control_type
= "text";
2475 field
.label
= ASCIIToUTF16("email");
2476 field
.name
= ASCIIToUTF16("email");
2477 form
.fields
.push_back(field
);
2478 possible_field_types
.push_back(ServerFieldTypeSet());
2479 possible_field_types
.back().insert(EMAIL_ADDRESS
);
2481 field
.label
= ASCIIToUTF16("First Name");
2482 field
.name
= ASCIIToUTF16("first");
2483 form
.fields
.push_back(field
);
2484 possible_field_types
.push_back(ServerFieldTypeSet());
2485 possible_field_types
.back().insert(NAME_FIRST
);
2487 field
.label
= ASCIIToUTF16("Last Name");
2488 field
.name
= ASCIIToUTF16("last");
2489 form
.fields
.push_back(field
);
2490 possible_field_types
.push_back(ServerFieldTypeSet());
2491 possible_field_types
.back().insert(NAME_LAST
);
2493 field
.label
= ASCIIToUTF16("Address");
2494 field
.name
= ASCIIToUTF16("address");
2495 form
.fields
.push_back(field
);
2496 possible_field_types
.push_back(ServerFieldTypeSet());
2497 possible_field_types
.back().insert(ADDRESS_HOME_LINE1
);
2499 form_structure
.reset(new FormStructure(form
));
2501 for (size_t i
= 0; i
< form_structure
->field_count(); ++i
)
2502 form_structure
->field(i
)->set_possible_types(possible_field_types
[i
]);
2503 std::string encoded_xml
;
2505 // Now we matched both fields singularly.
2506 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, false,
2507 std::string(), &encoded_xml
));
2508 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2509 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2510 " formsignature=\"18062476096658145866\" autofillused=\"false\""
2511 " datapresent=\"1440000360000008\">"
2512 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2513 " label=\"email\" autofilltype=\"9\"/>"
2514 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2515 " label=\"First Name\" autofilltype=\"3\"/>"
2516 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2517 " label=\"Last Name\" autofilltype=\"5\"/>"
2518 "<field signature=\"509334676\" name=\"address\" type=\"text\""
2519 " label=\"Address\" autofilltype=\"30\"/></autofillupload>",
2521 // Match third field as both first and last.
2522 possible_field_types
[2].insert(NAME_FIRST
);
2523 form_structure
->field(2)->set_possible_types(possible_field_types
[2]);
2524 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, false,
2525 std::string(), &encoded_xml
));
2526 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2527 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2528 " formsignature=\"18062476096658145866\" autofillused=\"false\""
2529 " datapresent=\"1440000360000008\">"
2530 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2531 " label=\"email\" autofilltype=\"9\"/>"
2532 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2533 " label=\"First Name\" autofilltype=\"3\"/>"
2534 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2535 " label=\"Last Name\" autofilltype=\"3\"/>"
2536 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2537 " label=\"Last Name\" autofilltype=\"5\"/>"
2538 "<field signature=\"509334676\" name=\"address\" type=\"text\""
2539 " label=\"Address\" autofilltype=\"30\"/></autofillupload>",
2541 possible_field_types
[3].insert(ADDRESS_HOME_LINE2
);
2542 form_structure
->field(form_structure
->field_count() - 1)->set_possible_types(
2543 possible_field_types
[form_structure
->field_count() - 1]);
2544 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, false,
2545 std::string(), &encoded_xml
));
2546 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2547 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2548 " formsignature=\"18062476096658145866\" autofillused=\"false\""
2549 " datapresent=\"1440000360000008\">"
2550 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2551 " label=\"email\" autofilltype=\"9\"/>"
2552 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2553 " label=\"First Name\" autofilltype=\"3\"/>"
2554 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2555 " label=\"Last Name\" autofilltype=\"3\"/>"
2556 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2557 " label=\"Last Name\" autofilltype=\"5\"/>"
2558 "<field signature=\"509334676\" name=\"address\" type=\"text\""
2559 " label=\"Address\" autofilltype=\"30\"/>"
2560 "<field signature=\"509334676\" name=\"address\" type=\"text\""
2561 " label=\"Address\" autofilltype=\"31\"/></autofillupload>",
2563 possible_field_types
[3].clear();
2564 possible_field_types
[3].insert(ADDRESS_HOME_LINE1
);
2565 possible_field_types
[3].insert(COMPANY_NAME
);
2566 form_structure
->field(form_structure
->field_count() - 1)->set_possible_types(
2567 possible_field_types
[form_structure
->field_count() - 1]);
2568 EXPECT_TRUE(form_structure
->EncodeUploadRequest(available_field_types
, false,
2569 std::string(), &encoded_xml
));
2570 EXPECT_EQ("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2571 "<autofillupload clientversion=\"6.1.1715.1442/en (GGLL)\""
2572 " formsignature=\"18062476096658145866\" autofillused=\"false\""
2573 " datapresent=\"1440000360000008\">"
2574 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2575 " label=\"email\" autofilltype=\"9\"/>"
2576 "<field signature=\"1089846351\" name=\"first\" type=\"text\""
2577 " label=\"First Name\" autofilltype=\"3\"/>"
2578 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2579 " label=\"Last Name\" autofilltype=\"3\"/>"
2580 "<field signature=\"2404144663\" name=\"last\" type=\"text\""
2581 " label=\"Last Name\" autofilltype=\"5\"/>"
2582 "<field signature=\"509334676\" name=\"address\" type=\"text\""
2583 " label=\"Address\" autofilltype=\"30\"/>"
2584 "<field signature=\"509334676\" name=\"address\" type=\"text\""
2585 " label=\"Address\" autofilltype=\"60\"/></autofillupload>",
2589 TEST_F(FormStructureTest
, CheckFormSignature
) {
2590 // Check that form signature is created correctly.
2591 scoped_ptr
<FormStructure
> form_structure
;
2594 FormFieldData field
;
2595 field
.form_control_type
= "text";
2597 field
.label
= ASCIIToUTF16("email");
2598 field
.name
= ASCIIToUTF16("email");
2599 form
.fields
.push_back(field
);
2601 field
.label
= ASCIIToUTF16("First Name");
2602 field
.name
= ASCIIToUTF16("first");
2603 form
.fields
.push_back(field
);
2605 // Checkable fields shouldn't affect the signature.
2606 field
.label
= ASCIIToUTF16("Select");
2607 field
.name
= ASCIIToUTF16("Select");
2608 field
.form_control_type
= "checkbox";
2609 field
.is_checkable
= true;
2610 form
.fields
.push_back(field
);
2612 form_structure
.reset(new FormStructure(form
));
2614 EXPECT_EQ(FormStructureTest::Hash64Bit(
2615 std::string("://&&email&first")),
2616 form_structure
->FormSignature());
2618 form
.origin
= GURL(std::string("http://www.facebook.com"));
2619 form_structure
.reset(new FormStructure(form
));
2620 EXPECT_EQ(FormStructureTest::Hash64Bit(
2621 std::string("http://www.facebook.com&&email&first")),
2622 form_structure
->FormSignature());
2624 form
.action
= GURL(std::string("https://login.facebook.com/path"));
2625 form_structure
.reset(new FormStructure(form
));
2626 EXPECT_EQ(FormStructureTest::Hash64Bit(
2627 std::string("https://login.facebook.com&&email&first")),
2628 form_structure
->FormSignature());
2630 form
.name
= ASCIIToUTF16("login_form");
2631 form_structure
.reset(new FormStructure(form
));
2632 EXPECT_EQ(FormStructureTest::Hash64Bit(
2633 std::string("https://login.facebook.com&login_form&email&first")),
2634 form_structure
->FormSignature());
2636 field
.is_checkable
= false;
2637 field
.label
= ASCIIToUTF16("Random Field label");
2638 field
.name
= ASCIIToUTF16("random1234");
2639 field
.form_control_type
= "text";
2640 form
.fields
.push_back(field
);
2641 field
.label
= ASCIIToUTF16("Random Field label2");
2642 field
.name
= ASCIIToUTF16("random12345");
2643 form
.fields
.push_back(field
);
2644 field
.label
= ASCIIToUTF16("Random Field label3");
2645 field
.name
= ASCIIToUTF16("1random12345678");
2646 form
.fields
.push_back(field
);
2647 field
.label
= ASCIIToUTF16("Random Field label3");
2648 field
.name
= ASCIIToUTF16("12345random");
2649 form
.fields
.push_back(field
);
2650 form_structure
.reset(new FormStructure(form
));
2651 EXPECT_EQ(FormStructureTest::Hash64Bit(
2652 std::string("https://login.facebook.com&login_form&email&first&"
2653 "random1234&random&1random&random")),
2654 form_structure
->FormSignature());
2657 TEST_F(FormStructureTest
, ToFormData
) {
2659 form
.name
= ASCIIToUTF16("the-name");
2660 form
.origin
= GURL("http://cool.com");
2661 form
.action
= form
.origin
.Resolve("/login");
2663 FormFieldData field
;
2664 field
.label
= ASCIIToUTF16("username");
2665 field
.name
= ASCIIToUTF16("username");
2666 field
.form_control_type
= "text";
2667 form
.fields
.push_back(field
);
2669 field
.label
= ASCIIToUTF16("password");
2670 field
.name
= ASCIIToUTF16("password");
2671 field
.form_control_type
= "password";
2672 form
.fields
.push_back(field
);
2674 field
.label
= base::string16();
2675 field
.name
= ASCIIToUTF16("Submit");
2676 field
.form_control_type
= "submit";
2677 form
.fields
.push_back(field
);
2679 EXPECT_TRUE(form
.SameFormAs(FormStructure(form
).ToFormData()));
2682 TEST_F(FormStructureTest
, SkipFieldTest
) {
2684 form
.name
= ASCIIToUTF16("the-name");
2685 form
.origin
= GURL("http://cool.com");
2686 form
.action
= form
.origin
.Resolve("/login");
2688 FormFieldData field
;
2689 field
.label
= ASCIIToUTF16("username");
2690 field
.name
= ASCIIToUTF16("username");
2691 field
.form_control_type
= "text";
2692 form
.fields
.push_back(field
);
2694 field
.label
= ASCIIToUTF16("select");
2695 field
.name
= ASCIIToUTF16("select");
2696 field
.form_control_type
= "checkbox";
2697 field
.is_checkable
= true;
2698 form
.fields
.push_back(field
);
2700 field
.label
= base::string16();
2701 field
.name
= ASCIIToUTF16("email");
2702 field
.form_control_type
= "text";
2703 field
.is_checkable
= false;
2704 form
.fields
.push_back(field
);
2706 ScopedVector
<FormStructure
> forms
;
2707 forms
.push_back(new FormStructure(form
));
2708 std::vector
<std::string
> encoded_signatures
;
2709 std::string encoded_xml
;
2711 const char kSignature
[] = "18006745212084723782";
2712 const char kResponse
[] = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2713 "<autofillquery clientversion=\"6.1.1715.1442/en (GGLL)\">"
2714 "<form signature=\"18006745212084723782\">"
2715 "<field signature=\"239111655\" name=\"username\" type=\"text\""
2716 " label=\"username\"/>"
2717 "<field signature=\"420638584\" name=\"email\" type=\"text\"/>"
2718 "</form></autofillquery>";
2719 ASSERT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
2720 &encoded_signatures
,
2722 ASSERT_EQ(1U, encoded_signatures
.size());
2723 EXPECT_EQ(kSignature
, encoded_signatures
[0]);
2724 EXPECT_EQ(kResponse
, encoded_xml
);
2727 TEST_F(FormStructureTest
, EncodeQueryRequest_WithLabels
) {
2729 form
.name
= ASCIIToUTF16("the-name");
2730 form
.origin
= GURL("http://cool.com");
2731 form
.action
= form
.origin
.Resolve("/login");
2733 FormFieldData field
;
2734 // No label on the first field.
2735 field
.name
= ASCIIToUTF16("username");
2736 field
.form_control_type
= "text";
2737 form
.fields
.push_back(field
);
2739 field
.label
= ASCIIToUTF16("Enter your Email address");
2740 field
.name
= ASCIIToUTF16("email");
2741 field
.form_control_type
= "text";
2742 form
.fields
.push_back(field
);
2744 field
.label
= ASCIIToUTF16("Enter your Password");
2745 field
.name
= ASCIIToUTF16("password");
2746 field
.form_control_type
= "password";
2747 form
.fields
.push_back(field
);
2749 ScopedVector
<FormStructure
> forms
;
2750 forms
.push_back(new FormStructure(form
));
2751 std::vector
<std::string
> encoded_signatures
;
2752 std::string encoded_xml
;
2754 const char kRequest
[] = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2755 "<autofillquery clientversion=\"6.1.1715.1442/en (GGLL)\">"
2756 "<form signature=\"13906559713264665730\">"
2757 "<field signature=\"239111655\" name=\"username\" type=\"text\"/>"
2758 "<field signature=\"420638584\" name=\"email\" type=\"text\""
2759 " label=\"Enter your Email address\"/>"
2760 "<field signature=\"2051817934\" name=\"password\" type=\"password\""
2761 " label=\"Enter your Password\"/></form></autofillquery>";
2762 EXPECT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
2763 &encoded_signatures
,
2765 EXPECT_EQ(kRequest
, encoded_xml
);
2768 // One name is missing from one field.
2769 TEST_F(FormStructureTest
, EncodeQueryRequest_MissingNames
) {
2771 // No name set for the form.
2772 form
.origin
= GURL("http://cool.com");
2773 form
.action
= form
.origin
.Resolve("/login");
2775 FormFieldData field
;
2776 field
.label
= ASCIIToUTF16("username");
2777 field
.name
= ASCIIToUTF16("username");
2778 field
.form_control_type
= "text";
2779 form
.fields
.push_back(field
);
2781 field
.label
= base::string16();
2782 // No name set for this field.
2783 field
.name
= ASCIIToUTF16("");
2784 field
.form_control_type
= "text";
2785 field
.is_checkable
= false;
2786 form
.fields
.push_back(field
);
2788 ScopedVector
<FormStructure
> forms
;
2789 forms
.push_back(new FormStructure(form
));
2790 std::vector
<std::string
> encoded_signatures
;
2791 std::string encoded_xml
;
2793 const char kSignature
[] = "16416961345885087496";
2794 const char kResponse
[] = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2795 "<autofillquery clientversion=\"6.1.1715.1442/en (GGLL)\">"
2796 "<form signature=\"16416961345885087496\">"
2797 "<field signature=\"239111655\" name=\"username\" type=\"text\""
2798 " label=\"username\"/><field signature=\"1318412689\" type=\"text\"/>"
2799 "</form></autofillquery>";
2800 ASSERT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
2801 &encoded_signatures
,
2803 ASSERT_EQ(1U, encoded_signatures
.size());
2804 EXPECT_EQ(kSignature
, encoded_signatures
[0]);
2805 EXPECT_EQ(kResponse
, encoded_xml
);
2808 // Sending field metadata to the server is disabled.
2809 TEST_F(FormStructureTest
, EncodeQueryRequest_DisabledMetadataTrial
) {
2810 DisableAutofillMetadataFieldTrial();
2813 // No name set for the form.
2814 form
.origin
= GURL("http://cool.com");
2815 form
.action
= form
.origin
.Resolve("/login");
2817 FormFieldData field
;
2818 field
.label
= ASCIIToUTF16("username");
2819 field
.name
= ASCIIToUTF16("username");
2820 field
.form_control_type
= "text";
2821 form
.fields
.push_back(field
);
2823 field
.label
= base::string16();
2824 field
.name
= ASCIIToUTF16("country");
2825 field
.form_control_type
= "text";
2826 field
.is_checkable
= false;
2827 form
.fields
.push_back(field
);
2829 ScopedVector
<FormStructure
> forms
;
2830 forms
.push_back(new FormStructure(form
));
2831 std::vector
<std::string
> encoded_signatures
;
2832 std::string encoded_xml
;
2834 const char kSignature
[] = "7635954436925888745";
2835 const char kResponse
[] = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
2836 "<autofillquery clientversion=\"6.1.1715.1442/en (GGLL)\">"
2837 "<form signature=\"7635954436925888745\">"
2838 "<field signature=\"239111655\"/>"
2839 "<field signature=\"3654076265\"/>"
2840 "</form></autofillquery>";
2841 ASSERT_TRUE(FormStructure::EncodeQueryRequest(forms
.get(),
2842 &encoded_signatures
,
2844 ASSERT_EQ(1U, encoded_signatures
.size());
2845 EXPECT_EQ(kSignature
, encoded_signatures
[0]);
2846 EXPECT_EQ(kResponse
, encoded_xml
);
2849 TEST_F(FormStructureTest
, PossibleValues
) {
2851 FormFieldData field
;
2852 field
.autocomplete_attribute
= "billing country";
2853 field
.option_contents
.push_back(ASCIIToUTF16("Down Under"));
2854 field
.option_values
.push_back(ASCIIToUTF16("AU"));
2855 field
.option_contents
.push_back(ASCIIToUTF16("Fr"));
2856 field
.option_values
.push_back(ASCIIToUTF16(""));
2857 field
.option_contents
.push_back(ASCIIToUTF16("Germany"));
2858 field
.option_values
.push_back(ASCIIToUTF16("GRMNY"));
2859 form_data
.fields
.push_back(field
);
2860 FormStructure
form_structure(form_data
);
2863 form_structure
.ParseFieldTypesFromAutocompleteAttributes(&unused
, &unused
);
2865 // All values in <option> value= or contents are returned, set to upper case.
2866 std::set
<base::string16
> possible_values
=
2867 form_structure
.PossibleValues(ADDRESS_BILLING_COUNTRY
);
2868 EXPECT_EQ(5U, possible_values
.size());
2869 EXPECT_EQ(1U, possible_values
.count(ASCIIToUTF16("AU")));
2870 EXPECT_EQ(1U, possible_values
.count(ASCIIToUTF16("FR")));
2871 EXPECT_EQ(1U, possible_values
.count(ASCIIToUTF16("DOWN UNDER")));
2872 EXPECT_EQ(1U, possible_values
.count(ASCIIToUTF16("GERMANY")));
2873 EXPECT_EQ(1U, possible_values
.count(ASCIIToUTF16("GRMNY")));
2874 EXPECT_EQ(0U, possible_values
.count(ASCIIToUTF16("Fr")));
2875 EXPECT_EQ(0U, possible_values
.count(ASCIIToUTF16("DE")));
2877 // No field for the given type; empty value set.
2878 EXPECT_EQ(0U, form_structure
.PossibleValues(ADDRESS_HOME_COUNTRY
).size());
2880 // A freeform input (<input>) allows any value (overriding other <select>s).
2881 FormFieldData freeform_field
;
2882 freeform_field
.autocomplete_attribute
= "billing country";
2883 form_data
.fields
.push_back(freeform_field
);
2884 FormStructure
form_structure2(form_data
);
2885 form_structure2
.ParseFieldTypesFromAutocompleteAttributes(&unused
, &unused
);
2886 EXPECT_EQ(0U, form_structure2
.PossibleValues(ADDRESS_BILLING_COUNTRY
).size());
2889 TEST_F(FormStructureTest
, ParseQueryResponse
) {
2890 TestRapporService rappor_service
;
2892 form
.origin
= GURL("http://foo.com");
2893 FormFieldData field
;
2894 field
.form_control_type
= "text";
2896 field
.label
= ASCIIToUTF16("fullname");
2897 field
.name
= ASCIIToUTF16("fullname");
2898 form
.fields
.push_back(field
);
2900 field
.label
= ASCIIToUTF16("address");
2901 field
.name
= ASCIIToUTF16("address");
2902 form
.fields
.push_back(field
);
2904 // Checkable fields should be ignored in parsing
2905 FormFieldData checkable_field
;
2906 checkable_field
.label
= ASCIIToUTF16("radio_button");
2907 checkable_field
.form_control_type
= "radio";
2908 checkable_field
.is_checkable
= true;
2909 form
.fields
.push_back(checkable_field
);
2911 ScopedVector
<FormStructure
> forms
;
2912 forms
.push_back(new FormStructure(form
));
2914 field
.label
= ASCIIToUTF16("email");
2915 field
.name
= ASCIIToUTF16("email");
2916 form
.fields
.push_back(field
);
2918 field
.label
= ASCIIToUTF16("password");
2919 field
.name
= ASCIIToUTF16("password");
2920 field
.form_control_type
= "password";
2921 form
.fields
.push_back(field
);
2923 forms
.push_back(new FormStructure(form
));
2925 std::string response
=
2926 "<autofillqueryresponse>"
2927 "<field autofilltype=\"7\" />"
2928 "<field autofilltype=\"30\" />"
2929 "<field autofilltype=\"9\" />"
2930 "<field autofilltype=\"0\" />"
2931 "</autofillqueryresponse>";
2933 FormStructure::ParseQueryResponse(response
, forms
.get(), &rappor_service
);
2935 ASSERT_GE(forms
[0]->field_count(), 2U);
2936 ASSERT_GE(forms
[1]->field_count(), 2U);
2937 EXPECT_EQ(7, forms
[0]->field(0)->server_type());
2938 EXPECT_EQ(30, forms
[0]->field(1)->server_type());
2939 EXPECT_EQ(9, forms
[1]->field(0)->server_type());
2940 EXPECT_EQ(0, forms
[1]->field(1)->server_type());
2942 // No RAPPOR metrics are logged in the case there is server data available for
2944 EXPECT_EQ(0, rappor_service
.GetReportsCount());
2947 // If user defined types are present, only parse password fields.
2948 TEST_F(FormStructureTest
, ParseQueryResponseAuthorDefinedTypes
) {
2949 TestRapporService rappor_service
;
2951 form
.origin
= GURL("http://foo.com");
2952 FormFieldData field
;
2954 field
.label
= ASCIIToUTF16("email");
2955 field
.name
= ASCIIToUTF16("email");
2956 field
.form_control_type
= "text";
2957 field
.autocomplete_attribute
= "email";
2958 form
.fields
.push_back(field
);
2960 field
.label
= ASCIIToUTF16("password");
2961 field
.name
= ASCIIToUTF16("password");
2962 field
.form_control_type
= "password";
2963 field
.autocomplete_attribute
= "new-password";
2964 form
.fields
.push_back(field
);
2966 ScopedVector
<FormStructure
> forms
;
2967 forms
.push_back(new FormStructure(form
));
2968 forms
.front()->DetermineHeuristicTypes();
2970 std::string response
=
2971 "<autofillqueryresponse>"
2972 "<field autofilltype=\"9\" />"
2973 "<field autofilltype=\"76\" />"
2974 "</autofillqueryresponse>";
2976 FormStructure::ParseQueryResponse(response
, forms
.get(), &rappor_service
);
2978 ASSERT_GE(forms
[0]->field_count(), 2U);
2979 EXPECT_EQ(NO_SERVER_DATA
, forms
[0]->field(0)->server_type());
2980 EXPECT_EQ(76, forms
[0]->field(1)->server_type());
2983 // If the server returns NO_SERVER_DATA for one of the forms, expect RAPPOR
2985 TEST_F(FormStructureTest
,
2986 ParseQueryResponse_RapporLogging_OneFormNoServerData
) {
2987 TestRapporService rappor_service
;
2989 form
.origin
= GURL("http://foo.com");
2990 FormFieldData field
;
2991 field
.form_control_type
= "text";
2993 field
.label
= ASCIIToUTF16("fullname");
2994 field
.name
= ASCIIToUTF16("fullname");
2995 form
.fields
.push_back(field
);
2997 field
.label
= ASCIIToUTF16("address");
2998 field
.name
= ASCIIToUTF16("address");
2999 form
.fields
.push_back(field
);
3001 ScopedVector
<FormStructure
> forms
;
3002 forms
.push_back(new FormStructure(form
));
3004 field
.label
= ASCIIToUTF16("email");
3005 field
.name
= ASCIIToUTF16("email");
3006 form
.fields
.push_back(field
);
3008 field
.label
= ASCIIToUTF16("password");
3009 field
.name
= ASCIIToUTF16("password");
3010 field
.form_control_type
= "password";
3011 form
.fields
.push_back(field
);
3013 forms
.push_back(new FormStructure(form
));
3015 std::string response
=
3016 "<autofillqueryresponse>"
3017 "<field autofilltype=\"0\" />"
3018 "<field autofilltype=\"0\" />"
3019 "<field autofilltype=\"9\" />"
3020 "<field autofilltype=\"0\" />"
3021 "</autofillqueryresponse>";
3023 FormStructure::ParseQueryResponse(response
, forms
.get(), &rappor_service
);
3025 EXPECT_EQ(1, rappor_service
.GetReportsCount());
3027 rappor::RapporType type
;
3028 EXPECT_TRUE(rappor_service
.GetRecordedSampleForMetric(
3029 "Autofill.QueryResponseHasNoServerDataForForm", &sample
, &type
));
3030 EXPECT_EQ("foo.com", sample
);
3031 EXPECT_EQ(rappor::ETLD_PLUS_ONE_RAPPOR_TYPE
, type
);
3034 // If the server returns NO_SERVER_DATA for both of the forms, expect RAPPOR
3036 TEST_F(FormStructureTest
,
3037 ParseQueryResponse_RapporLogging_AllFormsNoServerData
) {
3038 TestRapporService rappor_service
;
3040 form
.origin
= GURL("http://foo.com");
3041 FormFieldData field
;
3042 field
.form_control_type
= "text";
3044 field
.label
= ASCIIToUTF16("fullname");
3045 field
.name
= ASCIIToUTF16("fullname");
3046 form
.fields
.push_back(field
);
3048 field
.label
= ASCIIToUTF16("address");
3049 field
.name
= ASCIIToUTF16("address");
3050 form
.fields
.push_back(field
);
3052 ScopedVector
<FormStructure
> forms
;
3053 forms
.push_back(new FormStructure(form
));
3055 field
.label
= ASCIIToUTF16("email");
3056 field
.name
= ASCIIToUTF16("email");
3057 form
.fields
.push_back(field
);
3059 field
.label
= ASCIIToUTF16("password");
3060 field
.name
= ASCIIToUTF16("password");
3061 field
.form_control_type
= "password";
3062 form
.fields
.push_back(field
);
3064 forms
.push_back(new FormStructure(form
));
3066 std::string response
=
3067 "<autofillqueryresponse>"
3068 "<field autofilltype=\"0\" />"
3069 "<field autofilltype=\"0\" />"
3070 "<field autofilltype=\"0\" />"
3071 "<field autofilltype=\"0\" />"
3072 "</autofillqueryresponse>";
3074 FormStructure::ParseQueryResponse(response
, forms
.get(), &rappor_service
);
3076 // Even though both forms are logging to RAPPOR, there is only one sample for
3078 EXPECT_EQ(1, rappor_service
.GetReportsCount());
3080 rappor::RapporType type
;
3081 EXPECT_TRUE(rappor_service
.GetRecordedSampleForMetric(
3082 "Autofill.QueryResponseHasNoServerDataForForm", &sample
, &type
));
3083 EXPECT_EQ("foo.com", sample
);
3084 EXPECT_EQ(rappor::ETLD_PLUS_ONE_RAPPOR_TYPE
, type
);
3087 // If the server returns NO_SERVER_DATA for only some of the fields, expect no
3089 TEST_F(FormStructureTest
,
3090 ParseQueryResponse_RapporLogging_PartialNoServerData
) {
3091 TestRapporService rappor_service
;
3093 form
.origin
= GURL("http://foo.com");
3094 FormFieldData field
;
3095 field
.form_control_type
= "text";
3097 field
.label
= ASCIIToUTF16("fullname");
3098 field
.name
= ASCIIToUTF16("fullname");
3099 form
.fields
.push_back(field
);
3101 field
.label
= ASCIIToUTF16("address");
3102 field
.name
= ASCIIToUTF16("address");
3103 form
.fields
.push_back(field
);
3105 ScopedVector
<FormStructure
> forms
;
3106 forms
.push_back(new FormStructure(form
));
3108 field
.label
= ASCIIToUTF16("email");
3109 field
.name
= ASCIIToUTF16("email");
3110 form
.fields
.push_back(field
);
3112 field
.label
= ASCIIToUTF16("password");
3113 field
.name
= ASCIIToUTF16("password");
3114 field
.form_control_type
= "password";
3115 form
.fields
.push_back(field
);
3117 forms
.push_back(new FormStructure(form
));
3119 std::string response
=
3120 "<autofillqueryresponse>"
3121 "<field autofilltype=\"0\" />"
3122 "<field autofilltype=\"10\" />"
3123 "<field autofilltype=\"0\" />"
3124 "<field autofilltype=\"11\" />"
3125 "</autofillqueryresponse>";
3127 FormStructure::ParseQueryResponse(response
, forms
.get(), &rappor_service
);
3129 // No RAPPOR metrics are logged in the case there is at least some server data
3130 // available for all forms.
3131 EXPECT_EQ(0, rappor_service
.GetReportsCount());
3134 } // namespace autofill