Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions autofill/META.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
spec: https://html.spec.whatwg.org/multipage/form-control-infrastructure.html#autofill

27 changes: 27 additions & 0 deletions autofill/basic_form.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Basic Autofill Form Test</title>
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<script src="/resources/testdriver.js"></script>
<script src="/resources/testdriver-vendor.js"></script>
<script src="resources/autofill-bidi-helpers.js"></script>
</head>
<body>
<form id="test_form">
<input type="text" autocomplete="name" id="name_field">
</form>
<script>
promise_test(async t => {
const nameField = document.getElementById('name_field');

await triggerAutofill(nameField, {'name': 'Test User'});

assertElementHasValue('name_field', 'Test User');
}, 'Basic autofill on a name field');
</script>
</body>
</html>

73 changes: 73 additions & 0 deletions autofill/colocated-hidden-fields.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Colocated Hidden Fields Autofill Test</title>
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<script src="/resources/testdriver.js"></script>
<script src="/resources/testdriver-vendor.js"></script>
<script src="resources/autofill-bidi-helpers.js"></script>
<style>
div { margin: 20px; }
form { height: 200px; overflow: scroll; }
</style>
</head>
<body>
<form id="test_form">
<h2>Delivery Address</h2>
<div>
<label for="name">Name:</label>
<input type="text" id="name" name="shipping-name" autocomplete="shipping name">
</div>
<div>
<label for="street">Street:</label>
<input type="text" id="street" name="shipping-street" autocomplete="shipping address-line1">
</div>
<div>
<label for="city">City:</label>
<input type="text" id="city" name="shipping-city" autocomplete="shipping address-level2">
</div>
<div>
<label for="postalcode">Postal Code:</label>
<input type="text" id="postalcode" name="shipping-postalcode" autocomplete="shipping postal-code">
</div>
<div>
<label for="state">Province/State:</label>
<input type="text" id="state" name="shipping-state" autocomplete="shipping address-level1">
</div>
<div>
<label for="country">Country:</label>
<input type="text" id="country" name="shipping-country" autocomplete="shipping country">
</div>
</form>
<script>
/**
* This test checks autofilling works for fields that are not in the viewport
* but are in a visible state (e.g., in a scrollable container).
* This ensures that autofill works on smaller devices for long forms.
*/
promise_test(async t => {
const nameField = document.getElementById('name');

await triggerAutofill(nameField, {
'name': 'Max Mustermann',
'address-line1': '1 Main St',
'address-level2': 'North Pole',
'postal-code': 'H0H 0H0',
'address-level1': 'Ontario',
'country': 'CA'
});

// Assert visible field was filled
assertElementHasValue('name', 'Max Mustermann');

// Assert that fields scrolled out of view were also correctly autofilled
assertElementHasValue('postalcode', 'H0H 0H0');
assertElementHasValue('state', 'Ontario');
assertElementHasValue('country', 'CA');
}, 'Autofill fills fields not currently in viewport');
</script>
</body>
</html>

67 changes: 67 additions & 0 deletions autofill/full_address_form.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Full Address Autofill Test</title>
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<script src="/resources/testdriver.js"></script>
<script src="/resources/testdriver-vendor.js"></script>
<script src="resources/autofill-bidi-helpers.js"></script>
<style>
div { margin: 10px 0; }
label { display: inline-block; width: 100px; }
</style>
</head>
<body>
<form id="test_form">
<h2>Delivery Address</h2>
<div>
<label for="name">Name:</label>
<input type="text" id="name" name="shipping-name" autocomplete="shipping name">
</div>
<div>
<label for="street">Street:</label>
<input type="text" id="street" name="shipping-street" autocomplete="shipping address-line1">
</div>
<div>
<label for="city">City:</label>
<input type="text" id="city" name="shipping-city" autocomplete="shipping address-level2">
</div>
<div>
<label for="postalcode">Postal Code:</label>
<input type="text" id="postalcode" name="shipping-postalcode" autocomplete="shipping postal-code">
</div>
<div>
<label for="state">Province/State:</label>
<input type="text" id="state" name="shipping-state" autocomplete="shipping address-level1">
</div>
<div>
<label for="country">Country:</label>
<input type="text" id="country" name="shipping-country" autocomplete="shipping country">
</div>
</form>
<script>
promise_test(async t => {
const nameField = document.getElementById('name');

await triggerAutofill(nameField, {
'name': 'Max Mustermann',
'address-line1': '1 Main St',
'address-level2': 'Springfield',
'postal-code': 'H0H 0H0',
'address-level1': 'Ontario',
'country': 'CA'
});

assertElementHasValue('name', 'Max Mustermann');
assertElementHasValue('street', '1 Main St');
assertElementHasValue('city', 'Springfield');
assertElementHasValue('postalcode', 'H0H 0H0');
assertElementHasValue('state', 'Ontario');
assertElementHasValue('country', 'CA');
}, 'Autofill fills all address fields when triggered on name field');
</script>
</body>
</html>

93 changes: 93 additions & 0 deletions autofill/resources/autofill-bidi-helpers.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
/**
* Helper functions for autofill tests using WebDriver BiDi.
*
* These helpers use the WebDriver BiDi autofill.trigger command to test
* browser autofill behavior.
*
* BiDi API: https://w3c.github.io/webdriver-bidi/#module-autofill
*/

/**
* Trigger autofill on a form element using WebDriver BiDi.
*
* @param {Element} element - The form element to trigger autofill on
* @param {Object} data - Autofill data mapping autocomplete field names to values
* @returns {Promise} Resolves when autofill is complete
*
* @example
* await triggerAutofill(document.getElementById('name'), {
* 'name': 'John Doe',
* 'address-line1': '123 Main St',
* 'country': 'US'
* });
*/
async function triggerAutofill(element, data) {
if (!window.test_driver) {
throw new Error('test_driver not available');
}

// Convert data object to fields array format expected by BiDi
const fields = Object.entries(data).map(([name, value]) => ({
name: name,
value: value
}));

// Use the WebDriver BiDi autofill.trigger command via test_driver
return await test_driver.bidi.autofill.trigger(element, fields);
}

/**
* Assert that a form element has the expected value.
*
* @param {string} elementId - The ID of the element to check
* @param {string} expectedValue - The expected value
* @param {string} [message] - Optional assertion message
*/
function assertElementHasValue(elementId, expectedValue, message) {
const element = document.getElementById(elementId);
assert_not_equals(element, null, `Element with id '${elementId}' should exist`);
const msg = message || `Element '${elementId}' should have value '${expectedValue}'`;
assert_equals(element.value, expectedValue, msg);
}

/**
* Standard address data for testing.
*/
const DEFAULT_ADDRESS_DATA = {
'name': 'Max Mustermann',
'address-line1': '1 Main St',
'address-level2': 'Springfield',
'postal-code': 'H0H 0H0',
'address-level1': 'Ontario',
'country': 'CA'
};

/**
* Create a simple form with autofill fields for testing.
*
* @param {Object} fields - Object mapping field IDs to autocomplete values
* @returns {HTMLFormElement} The created form element
*
* @example
* const form = createAutofillForm({
* 'name': 'name',
* 'email': 'email'
* });
*/
function createAutofillForm(fields) {
const form = document.createElement('form');
form.id = 'test_form';

for (const [id, autocomplete] of Object.entries(fields)) {
const input = document.createElement('input');
input.type = 'text';
input.id = id;
input.name = id;
input.autocomplete = autocomplete;
form.appendChild(input);
}

document.body.appendChild(form);
return form;
}

69 changes: 69 additions & 0 deletions autofill/scoped-fields.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Scoped Autofill Fields Test</title>
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<script src="/resources/testdriver.js"></script>
<script src="/resources/testdriver-vendor.js"></script>
<script src="resources/autofill-bidi-helpers.js"></script>
</head>
<body>
<form id="test_form">
<input type="text" name="shipping-address" autocomplete="section-delivery shipping address-line1"
placeholder="Shipping address" id="shipping_address">
<input type="text" name="shipping-postal" autocomplete="section-delivery shipping postal-code"
placeholder="Shipping Postal Code" id="shipping_postal">

<input type="text" name="billing-address" autocomplete="section-payment billing address-line1"
placeholder="Billing address" id="billing_address">
<input type="text" name="billing-postal" autocomplete="section-payment billing postal-code"
placeholder="Billing Postal Code" id="billing_postal">
</form>
<script>
/**
* This test checks that the autofill is correctly scoped to the form sections.
* When autofill is triggered on a shipping field, only shipping fields should be filled.
*/
promise_test(async t => {
const shippingField = document.getElementById('shipping_address');

await triggerAutofill(shippingField, {
'address-line1': '1 Main St',
'postal-code': '12345'
});

// Assert shipping scope was correctly autofilled
assertElementHasValue('shipping_address', '1 Main St');
assertElementHasValue('shipping_postal', '12345');

// Assert billing scope was NOT autofilled
assertElementHasValue('billing_address', '');
assertElementHasValue('billing_postal', '');
}, 'Autofill respects section scoping - shipping only');

promise_test(async t => {
// Clear previous values
document.getElementById('shipping_address').value = '';
document.getElementById('shipping_postal').value = '';

const billingField = document.getElementById('billing_address');

await triggerAutofill(billingField, {
'address-line1': '456 Bill Ave',
'postal-code': '67890'
});

// Assert billing scope was correctly autofilled
assertElementHasValue('billing_address', '456 Bill Ave');
assertElementHasValue('billing_postal', '67890');

// Assert shipping scope was NOT autofilled (should still be empty)
assertElementHasValue('shipping_address', '');
assertElementHasValue('shipping_postal', '');
}, 'Autofill respects section scoping - billing only');
</script>
</body>
</html>

50 changes: 50 additions & 0 deletions autofill/select-input.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Select Input Autofill Test</title>
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<script src="/resources/testdriver.js"></script>
<script src="/resources/testdriver-vendor.js"></script>
<script src="resources/autofill-bidi-helpers.js"></script>
<style>
div { margin: 10px 0; }
label { display: inline-block; width: 100px; }
</style>
</head>
<body>
<form id="test_form">
<div>
<label for="street">Street:</label>
<input type="text" id="street" name="shipping-street" autocomplete="shipping address-line1">
</div>
<div>
<label for="country">Country:</label>
<select id="country" name="shipping-country" autocomplete="shipping country">
<option value="US">United States</option>
<option value="CA">Canada</option>
<option value="MX">Mexico</option>
<option value="DE">Germany</option>
</select>
</div>
</form>
<script>
/**
* This test checks autofilling select elements with country values.
*/
promise_test(async t => {
const streetField = document.getElementById('street');

await triggerAutofill(streetField, {
'address-line1': '1 Main St',
'country': 'CA'
});

assertElementHasValue('street', '1 Main St');
assertElementHasValue('country', 'CA');
}, 'Autofill correctly sets select element by value');
</script>
</body>
</html>

Loading