diff --git a/toolkit/components/passwordmgr/LoginManagerPrompter.jsm b/toolkit/components/passwordmgr/LoginManagerPrompter.jsm index 293a2f32dbbd..a7c9110837e5 100644 --- a/toolkit/components/passwordmgr/LoginManagerPrompter.jsm +++ b/toolkit/components/passwordmgr/LoginManagerPrompter.jsm @@ -1030,7 +1030,6 @@ LoginManagerPrompter.prototype = { ); let chromeDoc = browser.ownerDocument; - let currentNotification; let updateButtonStatus = element => { @@ -1126,6 +1125,12 @@ LoginManagerPrompter.prototype = { updateButtonLabel(); }; + let onKeyUp = e => { + if (e.key == "Enter") { + e.target.closest("popupnotification").button.doCommand(); + } + }; + let onVisibilityToggle = commandEvent => { let passwordField = chromeDoc.getElementById( "password-notification-password" @@ -1313,6 +1318,12 @@ LoginManagerPrompter.prototype = { chromeDoc .getElementById("password-notification-username") .addEventListener("input", onInput); + chromeDoc + .getElementById("password-notification-username") + .addEventListener("keyup", onKeyUp); + chromeDoc + .getElementById("password-notification-password") + .addEventListener("keyup", onKeyUp); chromeDoc .getElementById("password-notification-password") .addEventListener("input", onInput); @@ -1360,9 +1371,15 @@ LoginManagerPrompter.prototype = { chromeDoc .getElementById("password-notification-username") .removeEventListener("input", onInput); + chromeDoc + .getElementById("password-notification-username") + .removeEventListener("keyup", onKeyUp); chromeDoc .getElementById("password-notification-password") .removeEventListener("input", onInput); + chromeDoc + .getElementById("password-notification-password") + .removeEventListener("keyup", onKeyUp); chromeDoc .getElementById("password-notification-visibilityToggle") .removeEventListener("command", onVisibilityToggle); diff --git a/toolkit/components/passwordmgr/test/browser/browser_capture_doorhanger.js b/toolkit/components/passwordmgr/test/browser/browser_capture_doorhanger.js index e4a5834d2f1c..5243690b5bf1 100644 --- a/toolkit/components/passwordmgr/test/browser/browser_capture_doorhanger.js +++ b/toolkit/components/passwordmgr/test/browser/browser_capture_doorhanger.js @@ -830,6 +830,48 @@ add_task(async function test_recipeCaptureFields_ExistingLogin() { Services.logins.removeAllLogins(); }); +add_task(async function test_saveUsingEnter() { + async function testWithTextboxSelector(fieldSelector) { + let storageChangedPromise = TestUtils.topicObserved( + "passwordmgr-storage-changed", + (_, data) => data == "addLogin" + ); + + info("Waiting for form submit and doorhanger interaction"); + await testSubmittingLoginForm("subtst_notifications_1.html", async function( + fieldValues + ) { + is(fieldValues.username, "notifyu1", "Checking submitted username"); + is(fieldValues.password, "notifyp1", "Checking submitted password"); + let notif = await getCaptureDoorhangerThatMayOpen("password-save"); + ok(notif, "got notification popup"); + is( + Services.logins.getAllLogins().length, + 0, + "Should not have any logins yet" + ); + await checkDoorhangerUsernamePassword("notifyu1", "notifyp1"); + let notificationElement = PopupNotifications.panel.childNodes[0]; + let textbox = notificationElement.querySelector(fieldSelector); + textbox.focus(); + await EventUtils.synthesizeKey("KEY_Enter"); + }); + await storageChangedPromise; + + let logins = Services.logins.getAllLogins(); + is(logins.length, 1, "Should only have 1 login"); + let login = logins[0].QueryInterface(Ci.nsILoginMetaInfo); + is(login.username, "notifyu1", "Check the username used on the new entry"); + is(login.password, "notifyp1", "Check the password used on the new entry"); + is(login.timesUsed, 1, "Check times used on new entry"); + + Services.logins.removeAllLogins(); + } + + await testWithTextboxSelector("#password-notification-password"); + await testWithTextboxSelector("#password-notification-username"); +}); + add_task(async function test_noShowPasswordOnDismissal() { info("Check for no Show Password field when the doorhanger is dismissed");