mirror of
https://github.com/bitwarden/browser
synced 2025-12-17 16:53:34 +00:00
[PM-5189] Refactoring implementation
This commit is contained in:
@@ -53,8 +53,8 @@ type OverlayBackgroundExtensionMessage = {
|
||||
sender?: string;
|
||||
details?: AutofillPageDetails;
|
||||
overlayElement?: string;
|
||||
forceCloseOverlay?: boolean;
|
||||
isOverlayHidden?: boolean;
|
||||
forceCloseAutofillInlineMenu?: boolean;
|
||||
isAutofillInlineMenuHidden?: boolean;
|
||||
setTransparentOverlay?: boolean;
|
||||
isFieldCurrentlyFocused?: boolean;
|
||||
isFieldCurrentlyFilling?: boolean;
|
||||
@@ -97,13 +97,13 @@ type OverlayBackgroundExtensionMessageHandlers = {
|
||||
autofillOverlayElementClosed: ({ message }: BackgroundMessageParam) => void;
|
||||
autofillOverlayAddNewVaultItem: ({ message, sender }: BackgroundOnMessageHandlerParams) => void;
|
||||
getInlineMenuVisibilitySetting: () => void;
|
||||
checkAutofillOverlayMenuFocused: () => void;
|
||||
focusAutofillOverlayMenuList: () => void;
|
||||
updateAutofillOverlayMenuPosition: ({
|
||||
checkAutofillInlineMenuFocused: () => void;
|
||||
focusAutofillInlineMenuList: () => void;
|
||||
updateAutofillInlineMenuPosition: ({
|
||||
message,
|
||||
sender,
|
||||
}: BackgroundOnMessageHandlerParams) => Promise<void>;
|
||||
updateAutofillOverlayMenuHidden: ({ message, sender }: BackgroundOnMessageHandlerParams) => void;
|
||||
updateAutofillInlineMenuHidden: ({ message, sender }: BackgroundOnMessageHandlerParams) => void;
|
||||
updateFocusedFieldData: ({ message, sender }: BackgroundOnMessageHandlerParams) => void;
|
||||
updateIsFieldCurrentlyFocused: ({ message }: BackgroundMessageParam) => void;
|
||||
checkIsFieldCurrentlyFocused: () => boolean;
|
||||
@@ -134,7 +134,7 @@ type OverlayButtonPortMessageHandlers = {
|
||||
closeAutofillInlineMenu: ({ port }: PortConnectionParam) => void;
|
||||
forceCloseAutofillOverlay: ({ port }: PortConnectionParam) => void;
|
||||
overlayPageBlurred: () => void;
|
||||
redirectOverlayFocusOut: ({ message, port }: PortOnMessageHandlerParams) => void;
|
||||
redirectInlineMenuFocusOut: ({ message, port }: PortOnMessageHandlerParams) => void;
|
||||
updateOverlayPageColorScheme: () => void;
|
||||
};
|
||||
|
||||
@@ -147,7 +147,7 @@ type OverlayListPortMessageHandlers = {
|
||||
fillSelectedListItem: ({ message, port }: PortOnMessageHandlerParams) => void;
|
||||
addNewVaultItem: ({ port }: PortConnectionParam) => void;
|
||||
viewSelectedCipher: ({ message, port }: PortOnMessageHandlerParams) => void;
|
||||
redirectOverlayFocusOut: ({ message, port }: PortOnMessageHandlerParams) => void;
|
||||
redirectInlineMenuFocusOut: ({ message, port }: PortOnMessageHandlerParams) => void;
|
||||
updateAutofillOverlayListHeight: ({ message, port }: PortOnMessageHandlerParams) => void;
|
||||
};
|
||||
|
||||
|
||||
@@ -564,7 +564,7 @@ describe("OverlayBackground", () => {
|
||||
expect(BrowserApi.tabSendMessage).not.toHaveBeenCalledWith(sender.tab, {
|
||||
command: "openAutofillInlineMenu",
|
||||
isFocusingFieldElement: false,
|
||||
isOpeningFullOverlay: false,
|
||||
isOpeningFullAutofillInlineMenu: false,
|
||||
authStatus: AuthenticationStatus.Unlocked,
|
||||
});
|
||||
});
|
||||
@@ -668,13 +668,13 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("checkAutofillOverlayMenuFocused message handler", () => {
|
||||
describe("checkAutofillInlineMenuFocused message handler", () => {
|
||||
beforeEach(async () => {
|
||||
await initOverlayElementPorts();
|
||||
});
|
||||
|
||||
it("will check if the overlay list is focused if the list port is open", () => {
|
||||
sendMockExtensionMessage({ command: "checkAutofillOverlayMenuFocused" });
|
||||
sendMockExtensionMessage({ command: "checkAutofillInlineMenuFocused" });
|
||||
|
||||
expect(listPortSpy.postMessage).toHaveBeenCalledWith({
|
||||
command: "checkAutofillOverlayListFocused",
|
||||
@@ -687,7 +687,7 @@ describe("OverlayBackground", () => {
|
||||
it("will check if the overlay button is focused if the list port is not open", () => {
|
||||
overlayBackground["overlayListPort"] = undefined;
|
||||
|
||||
sendMockExtensionMessage({ command: "checkAutofillOverlayMenuFocused" });
|
||||
sendMockExtensionMessage({ command: "checkAutofillInlineMenuFocused" });
|
||||
|
||||
expect(buttonPortSpy.postMessage).toHaveBeenCalledWith({
|
||||
command: "checkAutofillOverlayButtonFocused",
|
||||
@@ -698,8 +698,8 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("focusAutofillOverlayMenuList message handler", () => {
|
||||
it("will send a `focusOverlayMenuList` message to the overlay list port", async () => {
|
||||
describe("focusAutofillInlineMenuList message handler", () => {
|
||||
it("will send a `focusInlineMenuList` message to the overlay list port", async () => {
|
||||
await initOverlayElementPorts({
|
||||
initList: true,
|
||||
initButton: false,
|
||||
@@ -707,13 +707,13 @@ describe("OverlayBackground", () => {
|
||||
initListMessageConnectorSpy: false,
|
||||
});
|
||||
|
||||
sendMockExtensionMessage({ command: "focusAutofillOverlayMenuList" });
|
||||
sendMockExtensionMessage({ command: "focusAutofillInlineMenuList" });
|
||||
|
||||
expect(listPortSpy.postMessage).toHaveBeenCalledWith({ command: "focusOverlayMenuList" });
|
||||
expect(listPortSpy.postMessage).toHaveBeenCalledWith({ command: "focusInlineMenuList" });
|
||||
});
|
||||
});
|
||||
|
||||
describe("updateAutofillOverlayMenuPosition message handler", () => {
|
||||
describe("updateAutofillInlineMenuPosition message handler", () => {
|
||||
let sender: MockProxy<chrome.runtime.MessageSender>;
|
||||
|
||||
beforeEach(async () => {
|
||||
@@ -731,7 +731,7 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
|
||||
it("ignores updating the position if the overlay element type is not provided", () => {
|
||||
sendMockExtensionMessage({ command: "updateAutofillOverlayMenuPosition" }, sender);
|
||||
sendMockExtensionMessage({ command: "updateAutofillInlineMenuPosition" }, sender);
|
||||
|
||||
expect(listPortSpy.postMessage).not.toHaveBeenCalledWith({
|
||||
command: "updateIframePosition",
|
||||
@@ -749,7 +749,7 @@ describe("OverlayBackground", () => {
|
||||
|
||||
sendMockExtensionMessage(
|
||||
{
|
||||
command: "updateAutofillOverlayMenuPosition",
|
||||
command: "updateAutofillInlineMenuPosition",
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
},
|
||||
sender,
|
||||
@@ -770,7 +770,7 @@ describe("OverlayBackground", () => {
|
||||
|
||||
sendMockExtensionMessage(
|
||||
{
|
||||
command: "updateAutofillOverlayMenuPosition",
|
||||
command: "updateAutofillInlineMenuPosition",
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
},
|
||||
sender,
|
||||
@@ -791,7 +791,7 @@ describe("OverlayBackground", () => {
|
||||
|
||||
sendMockExtensionMessage(
|
||||
{
|
||||
command: "updateAutofillOverlayMenuPosition",
|
||||
command: "updateAutofillInlineMenuPosition",
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
},
|
||||
sender,
|
||||
@@ -812,7 +812,7 @@ describe("OverlayBackground", () => {
|
||||
|
||||
sendMockExtensionMessage(
|
||||
{
|
||||
command: "updateAutofillOverlayMenuPosition",
|
||||
command: "updateAutofillInlineMenuPosition",
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
},
|
||||
sender,
|
||||
@@ -831,7 +831,7 @@ describe("OverlayBackground", () => {
|
||||
|
||||
sendMockExtensionMessage(
|
||||
{
|
||||
command: "updateAutofillOverlayMenuPosition",
|
||||
command: "updateAutofillInlineMenuPosition",
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
},
|
||||
sender,
|
||||
@@ -851,7 +851,10 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
|
||||
it("sets the `display` CSS value on the overlay button and list", () => {
|
||||
const message = { command: "updateAutofillOverlayMenuHidden", isOverlayHidden: true };
|
||||
const message = {
|
||||
command: "updateAutofillInlineMenuHidden",
|
||||
isAutofillInlineMenuHidden: true,
|
||||
};
|
||||
|
||||
sendMockExtensionMessage(message);
|
||||
|
||||
@@ -871,7 +874,7 @@ describe("OverlayBackground", () => {
|
||||
|
||||
it("sets the `opacity` CSS value on the overlay button and list", () => {
|
||||
const message = {
|
||||
command: "updateAutofillOverlayMenuHidden",
|
||||
command: "updateAutofillInlineMenuHidden",
|
||||
setTransparentOverlay: true,
|
||||
};
|
||||
|
||||
@@ -998,7 +1001,7 @@ describe("OverlayBackground", () => {
|
||||
{
|
||||
command: "openAutofillInlineMenu",
|
||||
isFocusingFieldElement: true,
|
||||
isOpeningFullOverlay: false,
|
||||
isOpeningFullAutofillInlineMenu: false,
|
||||
authStatus: AuthenticationStatus.Unlocked,
|
||||
},
|
||||
{ frameId: 0 },
|
||||
@@ -1036,7 +1039,7 @@ describe("OverlayBackground", () => {
|
||||
|
||||
describe("handlePortOnConnect", () => {
|
||||
beforeEach(() => {
|
||||
jest.spyOn(overlayBackground as any, "updateOverlayMenuPosition").mockImplementation();
|
||||
jest.spyOn(overlayBackground as any, "updateInlineMenuPosition").mockImplementation();
|
||||
jest.spyOn(overlayBackground as any, "getAuthStatus").mockImplementation();
|
||||
jest.spyOn(overlayBackground as any, "getTranslations").mockImplementation();
|
||||
jest.spyOn(overlayBackground as any, "getOverlayCipherData").mockImplementation();
|
||||
@@ -1066,7 +1069,7 @@ describe("OverlayBackground", () => {
|
||||
expect(chrome.runtime.getURL).toHaveBeenCalledWith("overlay/list.css");
|
||||
expect(overlayBackground["getTranslations"]).toHaveBeenCalled();
|
||||
expect(overlayBackground["getOverlayCipherData"]).toHaveBeenCalled();
|
||||
expect(overlayBackground["updateOverlayMenuPosition"]).toHaveBeenCalledWith(
|
||||
expect(overlayBackground["updateInlineMenuPosition"]).toHaveBeenCalledWith(
|
||||
{ overlayElement: AutofillOverlayElement.List },
|
||||
listPortSpy.sender,
|
||||
);
|
||||
@@ -1086,7 +1089,7 @@ describe("OverlayBackground", () => {
|
||||
expect(overlayBackground["getAuthStatus"]).toHaveBeenCalled();
|
||||
expect(chrome.runtime.getURL).toHaveBeenCalledWith("overlay/button.css");
|
||||
expect(overlayBackground["getTranslations"]).toHaveBeenCalled();
|
||||
expect(overlayBackground["updateOverlayMenuPosition"]).toHaveBeenCalledWith(
|
||||
expect(overlayBackground["updateInlineMenuPosition"]).toHaveBeenCalledWith(
|
||||
{ overlayElement: AutofillOverlayElement.Button },
|
||||
buttonPortSpy.sender,
|
||||
);
|
||||
@@ -1176,7 +1179,7 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
|
||||
describe("forceCloseAutofillOverlay", () => {
|
||||
it("sends a `closeOverlay` message to the sender tab with a `forceCloseOverlay` flag of `true` set", () => {
|
||||
it("sends a `closeOverlay` message to the sender tab with a `forceCloseAutofillInlineMenu` flag of `true` set", () => {
|
||||
jest.spyOn(BrowserApi, "tabSendMessage");
|
||||
|
||||
sendPortMessage(buttonMessageConnectorPortSpy, {
|
||||
@@ -1205,14 +1208,14 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("redirectOverlayFocusOut", () => {
|
||||
describe("redirectInlineMenuFocusOut", () => {
|
||||
beforeEach(() => {
|
||||
jest.spyOn(BrowserApi, "tabSendMessageData");
|
||||
});
|
||||
|
||||
it("ignores the redirect message if the direction is not provided", () => {
|
||||
sendPortMessage(buttonMessageConnectorPortSpy, {
|
||||
command: "redirectOverlayFocusOut",
|
||||
command: "redirectInlineMenuFocusOut",
|
||||
portKey,
|
||||
});
|
||||
|
||||
@@ -1221,14 +1224,14 @@ describe("OverlayBackground", () => {
|
||||
|
||||
it("sends the redirect message if the direction is provided", () => {
|
||||
sendPortMessage(buttonMessageConnectorPortSpy, {
|
||||
command: "redirectOverlayFocusOut",
|
||||
command: "redirectInlineMenuFocusOut",
|
||||
direction: RedirectFocusDirection.Next,
|
||||
portKey,
|
||||
});
|
||||
|
||||
expect(BrowserApi.tabSendMessageData).toHaveBeenCalledWith(
|
||||
buttonMessageConnectorPortSpy.sender.tab,
|
||||
"redirectOverlayFocusOut",
|
||||
"redirectInlineMenuFocusOut",
|
||||
{ direction: RedirectFocusDirection.Next },
|
||||
);
|
||||
});
|
||||
@@ -1256,7 +1259,7 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
|
||||
describe("forceCloseAutofillOverlay", () => {
|
||||
it("sends a `closeOverlay` message to the sender tab with a `forceCloseOverlay` flag of `true` set", () => {
|
||||
it("sends a `closeOverlay` message to the sender tab with a `forceCloseAutofillInlineMenu` flag of `true` set", () => {
|
||||
jest.spyOn(BrowserApi, "tabSendMessage");
|
||||
|
||||
sendPortMessage(listMessageConnectorPortSpy, {
|
||||
@@ -1518,16 +1521,16 @@ describe("OverlayBackground", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("redirectOverlayFocusOut", () => {
|
||||
describe("redirectInlineMenuFocusOut", () => {
|
||||
it("redirects focus out of the overlay list", async () => {
|
||||
const message = {
|
||||
command: "redirectOverlayFocusOut",
|
||||
command: "redirectInlineMenuFocusOut",
|
||||
direction: RedirectFocusDirection.Next,
|
||||
portKey,
|
||||
};
|
||||
const redirectOverlayFocusOutSpy = jest.spyOn(
|
||||
overlayBackground as any,
|
||||
"redirectOverlayFocusOut",
|
||||
"redirectInlineMenuFocusOut",
|
||||
);
|
||||
|
||||
sendPortMessage(listMessageConnectorPortSpy, message);
|
||||
|
||||
@@ -69,11 +69,11 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
autofillOverlayElementClosed: ({ message }) => this.overlayElementClosed(message),
|
||||
autofillOverlayAddNewVaultItem: ({ message, sender }) => this.addNewVaultItem(message, sender),
|
||||
getInlineMenuVisibilitySetting: () => this.getInlineMenuVisibility(),
|
||||
checkAutofillOverlayMenuFocused: () => this.checkOverlayMenuFocused(),
|
||||
focusAutofillOverlayMenuList: () => this.focusOverlayMenuList(),
|
||||
updateAutofillOverlayMenuPosition: ({ message, sender }) =>
|
||||
this.updateOverlayMenuPosition(message, sender),
|
||||
updateAutofillOverlayMenuHidden: ({ message, sender }) =>
|
||||
checkAutofillInlineMenuFocused: () => this.checkInlineMenuFocused(),
|
||||
focusAutofillInlineMenuList: () => this.focusInlineMenuList(),
|
||||
updateAutofillInlineMenuPosition: ({ message, sender }) =>
|
||||
this.updateInlineMenuPosition(message, sender),
|
||||
updateAutofillInlineMenuHidden: ({ message, sender }) =>
|
||||
this.updateOverlayMenuHidden(message, sender),
|
||||
updateFocusedFieldData: ({ message, sender }) => this.setFocusedFieldData(message, sender),
|
||||
updateIsFieldCurrentlyFocused: ({ message }) => this.updateIsFieldCurrentlyFocused(message),
|
||||
@@ -95,21 +95,23 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
overlayButtonClicked: ({ port }) => this.handleOverlayButtonClicked(port),
|
||||
closeAutofillInlineMenu: ({ port }) => this.closeInlineMenu(port.sender),
|
||||
forceCloseAutofillOverlay: ({ port }) =>
|
||||
this.closeInlineMenu(port.sender, { forceCloseOverlay: true }),
|
||||
this.closeInlineMenu(port.sender, { forceCloseAutofillInlineMenu: true }),
|
||||
overlayPageBlurred: () => this.checkOverlayListFocused(),
|
||||
redirectOverlayFocusOut: ({ message, port }) => this.redirectOverlayFocusOut(message, port),
|
||||
redirectInlineMenuFocusOut: ({ message, port }) =>
|
||||
this.redirectInlineMenuFocusOut(message, port),
|
||||
updateOverlayPageColorScheme: () => this.updateButtonPageColorScheme(),
|
||||
};
|
||||
private readonly overlayListPortMessageHandlers: OverlayListPortMessageHandlers = {
|
||||
checkAutofillOverlayButtonFocused: () => this.checkOverlayButtonFocused(),
|
||||
forceCloseAutofillOverlay: ({ port }) =>
|
||||
this.closeInlineMenu(port.sender, { forceCloseOverlay: true }),
|
||||
this.closeInlineMenu(port.sender, { forceCloseAutofillInlineMenu: true }),
|
||||
overlayPageBlurred: () => this.checkOverlayButtonFocused(),
|
||||
unlockVault: ({ port }) => this.unlockVault(port),
|
||||
fillSelectedListItem: ({ message, port }) => this.fillSelectedOverlayListItem(message, port),
|
||||
addNewVaultItem: ({ port }) => this.getNewVaultItemDetails(port),
|
||||
viewSelectedCipher: ({ message, port }) => this.viewSelectedCipher(message, port),
|
||||
redirectOverlayFocusOut: ({ message, port }) => this.redirectOverlayFocusOut(message, port),
|
||||
redirectInlineMenuFocusOut: ({ message, port }) =>
|
||||
this.redirectInlineMenuFocusOut(message, port),
|
||||
updateAutofillOverlayListHeight: ({ message }) => this.updateOverlayListHeight(message),
|
||||
};
|
||||
|
||||
@@ -333,11 +335,8 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
|
||||
this.updateOverlayMenuPositionTimeout = setTimeout(() => {
|
||||
if (this.isFieldCurrentlyFocused) {
|
||||
void this.updateOverlayMenuPosition(
|
||||
{ overlayElement: AutofillOverlayElement.List },
|
||||
sender,
|
||||
);
|
||||
void this.updateOverlayMenuPosition(
|
||||
void this.updateInlineMenuPosition({ overlayElement: AutofillOverlayElement.List }, sender);
|
||||
void this.updateInlineMenuPosition(
|
||||
{ overlayElement: AutofillOverlayElement.Button },
|
||||
sender,
|
||||
);
|
||||
@@ -385,7 +384,7 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
* Checks if the overlay is focused. Will check the overlay list
|
||||
* if it is open, otherwise it will check the overlay button.
|
||||
*/
|
||||
private checkOverlayMenuFocused() {
|
||||
private checkInlineMenuFocused() {
|
||||
if (this.overlayListPort) {
|
||||
this.checkOverlayListFocused();
|
||||
|
||||
@@ -413,17 +412,17 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
* Sends a message to the sender tab to close the autofill overlay.
|
||||
*
|
||||
* @param sender - The sender of the port message
|
||||
* @param forceCloseOverlay - Identifies whether the overlay should be forced closed
|
||||
* @param forceCloseAutofillInlineMenu - Identifies whether the overlay should be forced closed
|
||||
* @param overlayElement - The overlay element to close, either the list or button
|
||||
*/
|
||||
private closeInlineMenu(
|
||||
sender: chrome.runtime.MessageSender,
|
||||
{
|
||||
forceCloseOverlay,
|
||||
forceCloseAutofillInlineMenu,
|
||||
overlayElement,
|
||||
}: { forceCloseOverlay?: boolean; overlayElement?: string } = {},
|
||||
}: { forceCloseAutofillInlineMenu?: boolean; overlayElement?: string } = {},
|
||||
) {
|
||||
if (forceCloseOverlay) {
|
||||
if (forceCloseAutofillInlineMenu) {
|
||||
void BrowserApi.tabSendMessage(
|
||||
sender.tab,
|
||||
{ command: "closeInlineMenu", overlayElement },
|
||||
@@ -480,7 +479,7 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
* @param overlayElement - The overlay element to update, either the list or button
|
||||
* @param sender - The sender of the extension message
|
||||
*/
|
||||
private async updateOverlayMenuPosition(
|
||||
private async updateInlineMenuPosition(
|
||||
{ overlayElement }: { overlayElement?: string },
|
||||
sender: chrome.runtime.MessageSender,
|
||||
) {
|
||||
@@ -592,10 +591,10 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
* @param sender - The sender of the extension message
|
||||
*/
|
||||
private updateOverlayMenuHidden(
|
||||
{ isOverlayHidden, setTransparentOverlay }: OverlayBackgroundExtensionMessage,
|
||||
{ isAutofillInlineMenuHidden, setTransparentOverlay }: OverlayBackgroundExtensionMessage,
|
||||
sender: chrome.runtime.MessageSender,
|
||||
) {
|
||||
const display = isOverlayHidden ? "none" : "block";
|
||||
const display = isAutofillInlineMenuHidden ? "none" : "block";
|
||||
let styles: { display: string; opacity?: number } = { display };
|
||||
|
||||
if (typeof setTransparentOverlay !== "undefined") {
|
||||
@@ -607,7 +606,7 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
|
||||
void BrowserApi.tabSendMessage(
|
||||
sender.tab,
|
||||
{ command: "toggleInlineMenuHidden", isInlineMenuHidden: isOverlayHidden },
|
||||
{ command: "toggleInlineMenuHidden", isInlineMenuHidden: isAutofillInlineMenuHidden },
|
||||
{ frameId: 0 },
|
||||
);
|
||||
|
||||
@@ -619,9 +618,12 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
* Sends a message to the currently active tab to open the autofill overlay.
|
||||
*
|
||||
* @param isFocusingFieldElement - Identifies whether the field element should be focused when the overlay is opened
|
||||
* @param isOpeningFullOverlay - Identifies whether the full overlay should be forced open regardless of other states
|
||||
* @param isOpeningFullAutofillInlineMenu - Identifies whether the full overlay should be forced open regardless of other states
|
||||
*/
|
||||
private async openInlineMenu(isFocusingFieldElement = false, isOpeningFullOverlay = false) {
|
||||
private async openInlineMenu(
|
||||
isFocusingFieldElement = false,
|
||||
isOpeningFullAutofillInlineMenu = false,
|
||||
) {
|
||||
const currentTab = await BrowserApi.getTabFromCurrentWindowId();
|
||||
|
||||
await BrowserApi.tabSendMessage(
|
||||
@@ -629,7 +631,7 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
{
|
||||
command: "openAutofillInlineMenu",
|
||||
isFocusingFieldElement,
|
||||
isOpeningFullOverlay,
|
||||
isOpeningFullAutofillInlineMenu,
|
||||
authStatus: await this.getAuthStatus(),
|
||||
},
|
||||
{
|
||||
@@ -736,8 +738,8 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
/**
|
||||
* Facilitates redirecting focus to the overlay list.
|
||||
*/
|
||||
private focusOverlayMenuList() {
|
||||
this.overlayListPort?.postMessage({ command: "focusOverlayMenuList" });
|
||||
private focusInlineMenuList() {
|
||||
this.overlayListPort?.postMessage({ command: "focusInlineMenuList" });
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -786,7 +788,7 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
* @param direction - The direction to redirect focus to (either "next", "previous" or "current)
|
||||
* @param sender - The sender of the port message
|
||||
*/
|
||||
private redirectOverlayFocusOut(
|
||||
private redirectInlineMenuFocusOut(
|
||||
{ direction }: OverlayPortMessage,
|
||||
{ sender }: chrome.runtime.Port,
|
||||
) {
|
||||
@@ -794,7 +796,7 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
return;
|
||||
}
|
||||
|
||||
void BrowserApi.tabSendMessageData(sender.tab, "redirectOverlayFocusOut", { direction });
|
||||
void BrowserApi.tabSendMessageData(sender.tab, "redirectInlineMenuFocusOut", { direction });
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -983,7 +985,7 @@ class OverlayBackground implements OverlayBackgroundInterface {
|
||||
? AutofillOverlayPort.ListMessageConnector
|
||||
: AutofillOverlayPort.ButtonMessageConnector,
|
||||
});
|
||||
void this.updateOverlayMenuPosition(
|
||||
void this.updateInlineMenuPosition(
|
||||
{
|
||||
overlayElement: isOverlayListPort
|
||||
? AutofillOverlayElement.List
|
||||
|
||||
@@ -16,11 +16,11 @@ export type AutofillExtensionMessage = {
|
||||
overlayElement?: string;
|
||||
isFocusingFieldElement?: boolean;
|
||||
authStatus?: AuthenticationStatus;
|
||||
isOpeningFullOverlay?: boolean;
|
||||
isOpeningFullAutofillInlineMenu?: boolean;
|
||||
data?: {
|
||||
isOverlayCiphersPopulated?: boolean;
|
||||
direction?: "previous" | "next" | "current";
|
||||
forceCloseOverlay?: boolean;
|
||||
forceCloseAutofillInlineMenu?: boolean;
|
||||
inlineMenuVisibility?: number;
|
||||
};
|
||||
};
|
||||
|
||||
@@ -22,7 +22,7 @@ type OverlayListWindowMessageHandlers = {
|
||||
initAutofillOverlayList: ({ message }: { message: InitAutofillOverlayListMessage }) => void;
|
||||
checkAutofillOverlayListFocused: () => void;
|
||||
updateOverlayListCiphers: ({ message }: { message: UpdateOverlayListCiphersMessage }) => void;
|
||||
focusOverlayMenuList: () => void;
|
||||
focusInlineMenuList: () => void;
|
||||
};
|
||||
|
||||
export {
|
||||
|
||||
@@ -330,7 +330,7 @@ describe("AutofillOverlayList", () => {
|
||||
"setAttribute",
|
||||
);
|
||||
|
||||
postWindowMessage({ command: "focusOverlayMenuList" });
|
||||
postWindowMessage({ command: "focusInlineMenuList" });
|
||||
|
||||
expect(overlayContainerSetAttributeSpy).toHaveBeenCalledWith("role", "dialog");
|
||||
expect(overlayContainerSetAttributeSpy).toHaveBeenCalledWith("aria-modal", "true");
|
||||
@@ -348,7 +348,7 @@ describe("AutofillOverlayList", () => {
|
||||
autofillOverlayList["overlayListContainer"].querySelector("#unlock-button");
|
||||
jest.spyOn(unlockButton as HTMLElement, "focus");
|
||||
|
||||
postWindowMessage({ command: "focusOverlayMenuList" });
|
||||
postWindowMessage({ command: "focusInlineMenuList" });
|
||||
|
||||
expect((unlockButton as HTMLElement).focus).toBeCalled();
|
||||
});
|
||||
@@ -360,7 +360,7 @@ describe("AutofillOverlayList", () => {
|
||||
autofillOverlayList["overlayListContainer"].querySelector("#new-item-button");
|
||||
jest.spyOn(newItemButton as HTMLElement, "focus");
|
||||
|
||||
postWindowMessage({ command: "focusOverlayMenuList" });
|
||||
postWindowMessage({ command: "focusInlineMenuList" });
|
||||
|
||||
expect((newItemButton as HTMLElement).focus).toBeCalled();
|
||||
});
|
||||
@@ -371,7 +371,7 @@ describe("AutofillOverlayList", () => {
|
||||
autofillOverlayList["overlayListContainer"].querySelector(".fill-cipher-button");
|
||||
jest.spyOn(firstCipherItem as HTMLElement, "focus");
|
||||
|
||||
postWindowMessage({ command: "focusOverlayMenuList" });
|
||||
postWindowMessage({ command: "focusInlineMenuList" });
|
||||
|
||||
expect((firstCipherItem as HTMLElement).focus).toBeCalled();
|
||||
});
|
||||
@@ -407,7 +407,7 @@ describe("AutofillOverlayList", () => {
|
||||
);
|
||||
|
||||
expect(globalThis.parent.postMessage).toHaveBeenCalledWith(
|
||||
{ command: "redirectOverlayFocusOut", direction: "previous", portKey },
|
||||
{ command: "redirectInlineMenuFocusOut", direction: "previous", portKey },
|
||||
"*",
|
||||
);
|
||||
});
|
||||
@@ -416,7 +416,7 @@ describe("AutofillOverlayList", () => {
|
||||
globalThis.document.dispatchEvent(new KeyboardEvent("keydown", { code: "Tab" }));
|
||||
|
||||
expect(globalThis.parent.postMessage).toHaveBeenCalledWith(
|
||||
{ command: "redirectOverlayFocusOut", direction: "next", portKey },
|
||||
{ command: "redirectInlineMenuFocusOut", direction: "next", portKey },
|
||||
"*",
|
||||
);
|
||||
});
|
||||
@@ -425,7 +425,7 @@ describe("AutofillOverlayList", () => {
|
||||
globalThis.document.dispatchEvent(new KeyboardEvent("keydown", { code: "Escape" }));
|
||||
|
||||
expect(globalThis.parent.postMessage).toHaveBeenCalledWith(
|
||||
{ command: "redirectOverlayFocusOut", direction: "current", portKey },
|
||||
{ command: "redirectInlineMenuFocusOut", direction: "current", portKey },
|
||||
"*",
|
||||
);
|
||||
});
|
||||
|
||||
@@ -26,7 +26,7 @@ class AutofillOverlayList extends AutofillOverlayPageElement {
|
||||
initAutofillOverlayList: ({ message }) => this.initAutofillOverlayList(message),
|
||||
checkAutofillOverlayListFocused: () => this.checkOverlayListFocused(),
|
||||
updateOverlayListCiphers: ({ message }) => this.updateListItems(message.ciphers),
|
||||
focusOverlayMenuList: () => this.focusOverlayMenuList(),
|
||||
focusInlineMenuList: () => this.focusInlineMenuList(),
|
||||
};
|
||||
|
||||
constructor() {
|
||||
@@ -495,7 +495,7 @@ class AutofillOverlayList extends AutofillOverlayPageElement {
|
||||
* determined by the presence of the unlock button, new item button, or
|
||||
* the first cipher button.
|
||||
*/
|
||||
private focusOverlayMenuList() {
|
||||
private focusInlineMenuList() {
|
||||
this.overlayListContainer.setAttribute("role", "dialog");
|
||||
this.overlayListContainer.setAttribute("aria-modal", "true");
|
||||
|
||||
|
||||
@@ -150,7 +150,7 @@ class AutofillOverlayPageElement extends HTMLElement {
|
||||
* @param direction - The direction to redirect the focus out
|
||||
*/
|
||||
private redirectOverlayFocusOutMessage(direction: string) {
|
||||
this.postMessageToParent({ command: "redirectOverlayFocusOut", direction });
|
||||
this.postMessageToParent({ command: "redirectInlineMenuFocusOut", direction });
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -5,9 +5,9 @@ import { AutofillExtensionMessageParam } from "../../content/abstractions/autofi
|
||||
import AutofillField from "../../models/autofill-field";
|
||||
import { ElementWithOpId, FormFieldElement } from "../../types";
|
||||
|
||||
export type OpenAutofillOverlayOptions = {
|
||||
export type OpenAutofillInlineMenuOptions = {
|
||||
isFocusingFieldElement?: boolean;
|
||||
isOpeningFullOverlay?: boolean;
|
||||
isOpeningFullAutofillInlineMenu?: boolean;
|
||||
authStatus?: AuthenticationStatus;
|
||||
};
|
||||
|
||||
@@ -18,8 +18,8 @@ export type AutofillOverlayContentExtensionMessageHandlers = {
|
||||
blurMostRecentOverlayField: () => void;
|
||||
bgUnlockPopoutOpened: () => void;
|
||||
bgVaultItemRepromptPopoutOpened: () => void;
|
||||
redirectOverlayFocusOut: ({ message }: AutofillExtensionMessageParam) => void;
|
||||
updateInlineMenuVisibility: ({ message }: AutofillExtensionMessageParam) => void;
|
||||
redirectInlineMenuFocusOut: ({ message }: AutofillExtensionMessageParam) => void;
|
||||
updateAutofillInlineMenuVisibility: ({ message }: AutofillExtensionMessageParam) => void;
|
||||
getSubFrameOffsets: ({ message }: AutofillExtensionMessageParam) => Promise<SubFrameOffsetData>;
|
||||
getSubFrameOffsetsFromWindowMessage: ({ message }: AutofillExtensionMessageParam) => void;
|
||||
};
|
||||
@@ -28,7 +28,7 @@ export interface AutofillOverlayContentService {
|
||||
pageDetailsUpdateRequired: boolean;
|
||||
extensionMessageHandlers: AutofillOverlayContentExtensionMessageHandlers;
|
||||
init(): void;
|
||||
setupAutofillOverlayListenerOnField(
|
||||
setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement: ElementWithOpId<FormFieldElement>,
|
||||
autofillFieldData: AutofillField,
|
||||
): Promise<void>;
|
||||
|
||||
@@ -98,7 +98,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("setupAutofillOverlayListenerOnField", () => {
|
||||
describe("setupAutofillInlineMenuListenerOnField", () => {
|
||||
let autofillFieldElement: ElementWithOpId<FormFieldElement>;
|
||||
let autofillFieldData: AutofillField;
|
||||
|
||||
@@ -131,7 +131,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("ignores fields that are readonly", async () => {
|
||||
autofillFieldData.readonly = true;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -142,7 +142,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("ignores fields that contain a disabled attribute", async () => {
|
||||
autofillFieldData.disabled = true;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -153,7 +153,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("ignores fields that are not viewable", async () => {
|
||||
autofillFieldData.viewable = false;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -165,7 +165,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
AutoFillConstants.ExcludedOverlayTypes.forEach(async (excludedType) => {
|
||||
autofillFieldData.type = excludedType;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -177,7 +177,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("ignores fields that contain the keyword `search`", async () => {
|
||||
autofillFieldData.placeholder = "search";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -188,7 +188,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("ignores fields that contain the keyword `captcha` ", async () => {
|
||||
autofillFieldData.placeholder = "captcha";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -200,7 +200,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it.skip("ignores fields that do not appear as a login field", async () => {
|
||||
autofillFieldData.placeholder = "not-a-login-field";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -212,7 +212,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("skips setup on fields that have been previously set up", async () => {
|
||||
autofillOverlayContentService["formFieldElements"].add(autofillFieldElement);
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -225,7 +225,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
sendExtensionMessageSpy.mockResolvedValueOnce(undefined);
|
||||
autofillOverlayContentService["inlineMenuVisibility"] = undefined;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -240,7 +240,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
sendExtensionMessageSpy.mockResolvedValueOnce(AutofillOverlayVisibility.OnFieldFocus);
|
||||
autofillOverlayContentService["inlineMenuVisibility"] = undefined;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -264,7 +264,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
"op-1-username-field-focus-handler": focusHandler,
|
||||
};
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -288,7 +288,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
describe("form field blur event listener", () => {
|
||||
beforeEach(async () => {
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -305,13 +305,13 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("sends a message to the background to check if the overlay is focused", () => {
|
||||
autofillFieldElement.dispatchEvent(new Event("blur"));
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("checkAutofillOverlayMenuFocused");
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("checkAutofillInlineMenuFocused");
|
||||
});
|
||||
});
|
||||
|
||||
describe("form field keyup event listener", () => {
|
||||
beforeEach(async () => {
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -322,7 +322,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillFieldElement.dispatchEvent(new KeyboardEvent("keyup", { code: "Escape" }));
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -374,12 +374,14 @@ describe("AutofillOverlayContentService", () => {
|
||||
await flushPromises();
|
||||
|
||||
expect(updateMostRecentlyFocusedFieldSpy).toHaveBeenCalledWith(autofillFieldElement);
|
||||
expect(openAutofillOverlaySpy).toHaveBeenCalledWith({ isOpeningFullOverlay: true });
|
||||
expect(sendExtensionMessageSpy).not.toHaveBeenCalledWith("focusAutofillOverlayMenuList");
|
||||
expect(openAutofillOverlaySpy).toHaveBeenCalledWith({
|
||||
isOpeningFullAutofillInlineMenu: true,
|
||||
});
|
||||
expect(sendExtensionMessageSpy).not.toHaveBeenCalledWith("focusAutofillInlineMenuList");
|
||||
|
||||
jest.advanceTimersByTime(150);
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("focusAutofillOverlayMenuList");
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("focusAutofillInlineMenuList");
|
||||
});
|
||||
|
||||
it("focuses the overlay list when the `ArrowDown` key is pressed", async () => {
|
||||
@@ -390,7 +392,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillFieldElement.dispatchEvent(new KeyboardEvent("keyup", { code: "ArrowDown" }));
|
||||
await flushPromises();
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("focusAutofillOverlayMenuList");
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("focusAutofillInlineMenuList");
|
||||
});
|
||||
});
|
||||
|
||||
@@ -405,7 +407,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
) as ElementWithOpId<HTMLSpanElement>;
|
||||
jest.spyOn(autofillOverlayContentService as any, "storeModifiedFormElement");
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
spanAutofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -416,7 +418,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
});
|
||||
|
||||
it("stores the field as a user filled field if the form field data indicates that it is for a username", async () => {
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -432,7 +434,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
"password-field",
|
||||
) as ElementWithOpId<FormFieldElement>;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
passwordFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -447,7 +449,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
jest.spyOn(autofillOverlayContentService as any, "isUserAuthed").mockReturnValue(false);
|
||||
(autofillFieldElement as HTMLInputElement).value = "test";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -456,7 +458,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -468,7 +470,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
(autofillFieldElement as HTMLInputElement).value = "test";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -477,7 +479,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -485,7 +487,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
jest.spyOn(autofillOverlayContentService as any, "openAutofillInlineMenu");
|
||||
(autofillFieldElement as HTMLInputElement).value = "";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -500,7 +502,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
jest.spyOn(autofillOverlayContentService as any, "openAutofillInlineMenu");
|
||||
(autofillFieldElement as HTMLInputElement).value = "";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -518,7 +520,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
jest.spyOn(autofillOverlayContentService as any, "openAutofillInlineMenu");
|
||||
(autofillFieldElement as HTMLInputElement).value = "";
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -542,7 +544,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
jest
|
||||
.spyOn(autofillOverlayContentService as any, "isInlineMenuListVisible")
|
||||
.mockResolvedValue(false);
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -596,7 +598,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillOverlayContentService["mostRecentlyFocusedField"] = autofillFieldElement;
|
||||
autofillOverlayContentService["inlineMenuVisibility"] =
|
||||
AutofillOverlayVisibility.OnFieldFocus;
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -608,7 +610,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
});
|
||||
|
||||
it("updates the most recently focused field", async () => {
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -625,7 +627,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("removes the overlay list if the autofill visibility is set to onClick", async () => {
|
||||
autofillOverlayContentService["inlineMenuVisibility"] =
|
||||
AutofillOverlayVisibility.OnButtonClick;
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -635,7 +637,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -644,7 +646,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
"input",
|
||||
) as ElementWithOpId<HTMLInputElement>;
|
||||
(autofillFieldElement as HTMLInputElement).value = "test";
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -654,7 +656,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -662,7 +664,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
(autofillFieldElement as HTMLInputElement).value = "";
|
||||
autofillOverlayContentService["inlineMenuVisibility"] =
|
||||
AutofillOverlayVisibility.OnFieldFocus;
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -678,7 +680,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillOverlayContentService["inlineMenuVisibility"] =
|
||||
AutofillOverlayVisibility.OnFieldFocus;
|
||||
jest.spyOn(autofillOverlayContentService as any, "isUserAuthed").mockReturnValue(true);
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -696,7 +698,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
jest
|
||||
.spyOn(autofillOverlayContentService as any, "isInlineMenuCiphersPopulated")
|
||||
.mockReturnValue(true);
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -704,12 +706,9 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillFieldElement.dispatchEvent(new Event("focus"));
|
||||
await flushPromises();
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith(
|
||||
"updateAutofillOverlayMenuPosition",
|
||||
{
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
},
|
||||
);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -721,7 +720,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
writable: true,
|
||||
});
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -735,7 +734,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("sets the most recently focused field to the passed form field element if the value is not set", async () => {
|
||||
autofillOverlayContentService["mostRecentlyFocusedField"] = undefined;
|
||||
|
||||
await autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
await autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
@@ -819,10 +818,10 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
autofillOverlayContentService["openAutofillInlineMenu"]();
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuPosition", {
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
});
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuPosition", {
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
});
|
||||
});
|
||||
@@ -831,29 +830,30 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillOverlayContentService["inlineMenuVisibility"] =
|
||||
AutofillOverlayVisibility.OnButtonClick;
|
||||
|
||||
autofillOverlayContentService["openAutofillInlineMenu"]({ isOpeningFullOverlay: false });
|
||||
autofillOverlayContentService["openAutofillInlineMenu"]({
|
||||
isOpeningFullAutofillInlineMenu: false,
|
||||
});
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuPosition", {
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
});
|
||||
expect(sendExtensionMessageSpy).not.toHaveBeenCalledWith(
|
||||
"updateAutofillOverlayMenuPosition",
|
||||
{
|
||||
expect(sendExtensionMessageSpy).not.toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
},
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
it("overrides the onButtonClick visibility setting to open both overlay elements", () => {
|
||||
autofillOverlayContentService["inlineMenuVisibility"] =
|
||||
AutofillOverlayVisibility.OnButtonClick;
|
||||
|
||||
autofillOverlayContentService["openAutofillInlineMenu"]({ isOpeningFullOverlay: true });
|
||||
autofillOverlayContentService["openAutofillInlineMenu"]({
|
||||
isOpeningFullAutofillInlineMenu: true,
|
||||
});
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuPosition", {
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
});
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuPosition", {
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
});
|
||||
});
|
||||
@@ -962,7 +962,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("redirectOverlayFocusOut", () => {
|
||||
describe("redirectInlineMenuFocusOut", () => {
|
||||
let autofillFieldElement: ElementWithOpId<FormFieldElement>;
|
||||
let autofillFieldFocusSpy: jest.SpyInstance;
|
||||
let findTabsSpy: jest.SpyInstance;
|
||||
@@ -1003,7 +1003,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("skips focusing an element if the overlay is not visible", async () => {
|
||||
isInlineMenuListVisibleSpy.mockResolvedValue(false);
|
||||
|
||||
await autofillOverlayContentService.redirectOverlayFocusOut(RedirectFocusDirection.Next);
|
||||
await autofillOverlayContentService.redirectInlineMenuFocusOut(RedirectFocusDirection.Next);
|
||||
|
||||
expect(findTabsSpy).not.toHaveBeenCalled();
|
||||
});
|
||||
@@ -1011,13 +1011,15 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("skips focusing an element if no recently focused field exists", async () => {
|
||||
autofillOverlayContentService["mostRecentlyFocusedField"] = undefined;
|
||||
|
||||
await autofillOverlayContentService.redirectOverlayFocusOut(RedirectFocusDirection.Next);
|
||||
await autofillOverlayContentService.redirectInlineMenuFocusOut(RedirectFocusDirection.Next);
|
||||
|
||||
expect(findTabsSpy).not.toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it("focuses the most recently focused field if the focus direction is `Current`", async () => {
|
||||
await autofillOverlayContentService.redirectOverlayFocusOut(RedirectFocusDirection.Current);
|
||||
await autofillOverlayContentService.redirectInlineMenuFocusOut(
|
||||
RedirectFocusDirection.Current,
|
||||
);
|
||||
|
||||
expect(findTabsSpy).not.toHaveBeenCalled();
|
||||
expect(autofillFieldFocusSpy).toHaveBeenCalled();
|
||||
@@ -1025,7 +1027,9 @@ describe("AutofillOverlayContentService", () => {
|
||||
|
||||
it("removes the overlay if the focus direction is `Current`", async () => {
|
||||
jest.useFakeTimers();
|
||||
await autofillOverlayContentService.redirectOverlayFocusOut(RedirectFocusDirection.Current);
|
||||
await autofillOverlayContentService.redirectInlineMenuFocusOut(
|
||||
RedirectFocusDirection.Current,
|
||||
);
|
||||
jest.advanceTimersByTime(150);
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu");
|
||||
@@ -1039,7 +1043,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
nextFocusableElement,
|
||||
]);
|
||||
|
||||
await autofillOverlayContentService.redirectOverlayFocusOut(RedirectFocusDirection.Next);
|
||||
await autofillOverlayContentService.redirectInlineMenuFocusOut(RedirectFocusDirection.Next);
|
||||
|
||||
expect(findTabsSpy).toHaveBeenCalledWith(globalThis.document.body, { getShadowRoot: true });
|
||||
});
|
||||
@@ -1047,7 +1051,9 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("focuses the previous focusable element if the focus direction is `Previous`", async () => {
|
||||
jest.spyOn(previousFocusableElement, "focus");
|
||||
|
||||
await autofillOverlayContentService.redirectOverlayFocusOut(RedirectFocusDirection.Previous);
|
||||
await autofillOverlayContentService.redirectInlineMenuFocusOut(
|
||||
RedirectFocusDirection.Previous,
|
||||
);
|
||||
|
||||
expect(autofillFieldFocusSpy).not.toHaveBeenCalled();
|
||||
expect(previousFocusableElement.focus).toHaveBeenCalled();
|
||||
@@ -1056,7 +1062,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
it("focuses the next focusable element if the focus direction is `Next`", async () => {
|
||||
jest.spyOn(nextFocusableElement, "focus");
|
||||
|
||||
await autofillOverlayContentService.redirectOverlayFocusOut(RedirectFocusDirection.Next);
|
||||
await autofillOverlayContentService.redirectInlineMenuFocusOut(RedirectFocusDirection.Next);
|
||||
|
||||
expect(autofillFieldFocusSpy).not.toHaveBeenCalled();
|
||||
expect(nextFocusableElement.focus).toHaveBeenCalled();
|
||||
@@ -1104,8 +1110,8 @@ describe("AutofillOverlayContentService", () => {
|
||||
globalThis.dispatchEvent(new Event(EVENTS.SCROLL));
|
||||
await flushPromises();
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuHidden", {
|
||||
isOverlayHidden: true,
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuHidden", {
|
||||
isAutofillInlineMenuHidden: true,
|
||||
setTransparentOverlay: false,
|
||||
});
|
||||
});
|
||||
@@ -1132,12 +1138,12 @@ describe("AutofillOverlayContentService", () => {
|
||||
await flushPromises();
|
||||
jest.advanceTimersByTime(800);
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuHidden", {
|
||||
isOverlayHidden: false,
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuHidden", {
|
||||
isAutofillInlineMenuHidden: false,
|
||||
setTransparentOverlay: true,
|
||||
});
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -1163,10 +1169,10 @@ describe("AutofillOverlayContentService", () => {
|
||||
jest.advanceTimersByTime(800);
|
||||
await flushPromises();
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuPosition", {
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
});
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillOverlayMenuPosition", {
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
});
|
||||
expect(clearUserInteractionEventTimeoutSpy).toHaveBeenCalled();
|
||||
@@ -1191,7 +1197,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
await flushPromises();
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -1201,7 +1207,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillOverlayContentService["handleVisibilityChangeEvent"]();
|
||||
|
||||
expect(sendExtensionMessageSpy).not.toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
|
||||
@@ -1215,7 +1221,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
autofillOverlayContentService["handleVisibilityChangeEvent"]();
|
||||
|
||||
expect(sendExtensionMessageSpy).toHaveBeenCalledWith("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -1244,7 +1250,7 @@ describe("AutofillOverlayContentService", () => {
|
||||
});
|
||||
// FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
|
||||
// eslint-disable-next-line @typescript-eslint/no-floating-promises
|
||||
autofillOverlayContentService.setupAutofillOverlayListenerOnField(
|
||||
autofillOverlayContentService.setupAutofillInlineMenuListenerOnField(
|
||||
autofillFieldElement,
|
||||
autofillFieldData,
|
||||
);
|
||||
|
||||
@@ -18,7 +18,7 @@ import { elementIsFillableFormField, getAttributeBoolean, sendExtensionMessage }
|
||||
import {
|
||||
AutofillOverlayContentExtensionMessageHandlers,
|
||||
AutofillOverlayContentService as AutofillOverlayContentServiceInterface,
|
||||
OpenAutofillOverlayOptions,
|
||||
OpenAutofillInlineMenuOptions,
|
||||
} from "./abstractions/autofill-overlay-content.service";
|
||||
import { AutoFillConstants } from "./autofill-constants";
|
||||
|
||||
@@ -46,9 +46,10 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
blurMostRecentOverlayField: () => this.blurMostRecentOverlayField(),
|
||||
bgUnlockPopoutOpened: () => this.blurMostRecentOverlayField(true),
|
||||
bgVaultItemRepromptPopoutOpened: () => this.blurMostRecentOverlayField(true),
|
||||
redirectOverlayFocusOut: ({ message }) =>
|
||||
this.redirectOverlayFocusOut(message?.data?.direction),
|
||||
updateInlineMenuVisibility: ({ message }) => this.updateInlineMenuVisibility(message),
|
||||
redirectInlineMenuFocusOut: ({ message }) =>
|
||||
this.redirectInlineMenuFocusOut(message?.data?.direction),
|
||||
updateAutofillInlineMenuVisibility: ({ message }) =>
|
||||
this.updateAutofillInlineMenuVisibility(message),
|
||||
getSubFrameOffsets: ({ message }) => this.getSubFrameOffsets(message),
|
||||
getSubFrameOffsetsFromWindowMessage: ({ message }) =>
|
||||
this.getSubFrameOffsetsFromWindowMessage(message),
|
||||
@@ -68,13 +69,13 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets up the autofill overlay listener on the form field element. This method is called
|
||||
* Sets up the autofill inline menu listener on the form field element. This method is called
|
||||
* during the page details collection process.
|
||||
*
|
||||
* @param formFieldElement - Form field elements identified during the page details collection process.
|
||||
* @param autofillFieldData - Autofill field data captured from the form field element.
|
||||
*/
|
||||
async setupAutofillOverlayListenerOnField(
|
||||
async setupAutofillInlineMenuListenerOnField(
|
||||
formFieldElement: ElementWithOpId<FormFieldElement>,
|
||||
autofillFieldData: AutofillField,
|
||||
) {
|
||||
@@ -111,8 +112,8 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
*
|
||||
* @param options - Options for opening the autofill overlay.
|
||||
*/
|
||||
openAutofillInlineMenu(options: OpenAutofillOverlayOptions = {}) {
|
||||
const { isFocusingFieldElement, isOpeningFullOverlay, authStatus } = options;
|
||||
openAutofillInlineMenu(options: OpenAutofillInlineMenuOptions = {}) {
|
||||
const { isFocusingFieldElement, isOpeningFullAutofillInlineMenu, authStatus } = options;
|
||||
if (!this.mostRecentlyFocusedField) {
|
||||
return;
|
||||
}
|
||||
@@ -134,13 +135,13 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
|
||||
if (
|
||||
this.inlineMenuVisibility === AutofillOverlayVisibility.OnButtonClick &&
|
||||
!isOpeningFullOverlay
|
||||
!isOpeningFullAutofillInlineMenu
|
||||
) {
|
||||
this.updateOverlayButtonPosition();
|
||||
this.updateAutofillInlineMenuButtonPosition();
|
||||
return;
|
||||
}
|
||||
|
||||
this.updateOverlayElementsPosition();
|
||||
this.updateAutofillInlineMenuElementsPosition();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -187,7 +188,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
*
|
||||
* @param direction - The direction to redirect the focus out.
|
||||
*/
|
||||
async redirectOverlayFocusOut(direction?: string) {
|
||||
async redirectInlineMenuFocusOut(direction?: string) {
|
||||
if (!direction || !this.mostRecentlyFocusedField || !(await this.isInlineMenuListVisible())) {
|
||||
return;
|
||||
}
|
||||
@@ -290,7 +291,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
void this.sendExtensionMessage("updateIsFieldCurrentlyFocused", {
|
||||
isFieldCurrentlyFocused: false,
|
||||
});
|
||||
void this.sendExtensionMessage("checkAutofillOverlayMenuFocused");
|
||||
void this.sendExtensionMessage("checkAutofillInlineMenuFocused");
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -305,7 +306,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
const eventCode = event.code;
|
||||
if (eventCode === "Escape") {
|
||||
void this.sendExtensionMessage("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
return;
|
||||
}
|
||||
@@ -319,7 +320,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
|
||||
void this.focusOverlayMenuList();
|
||||
void this.focusInlineMenuList();
|
||||
}
|
||||
};
|
||||
|
||||
@@ -328,15 +329,15 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
* the overlay will be opened and the list will be focused after a short delay. Ensures
|
||||
* that the overlay list is focused when the user presses the down arrow key.
|
||||
*/
|
||||
private async focusOverlayMenuList() {
|
||||
private async focusInlineMenuList() {
|
||||
if (this.mostRecentlyFocusedField && !(await this.isInlineMenuListVisible())) {
|
||||
await this.updateMostRecentlyFocusedField(this.mostRecentlyFocusedField);
|
||||
this.openAutofillInlineMenu({ isOpeningFullOverlay: true });
|
||||
setTimeout(() => this.sendExtensionMessage("focusAutofillOverlayMenuList"), 125);
|
||||
this.openAutofillInlineMenu({ isOpeningFullAutofillInlineMenu: true });
|
||||
setTimeout(() => this.sendExtensionMessage("focusAutofillInlineMenuList"), 125);
|
||||
return;
|
||||
}
|
||||
|
||||
void this.sendExtensionMessage("focusAutofillOverlayMenuList");
|
||||
void this.sendExtensionMessage("focusAutofillInlineMenuList");
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -365,10 +366,10 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
|
||||
this.storeModifiedFormElement(formFieldElement);
|
||||
|
||||
if (await this.hideOverlayListOnFilledField(formFieldElement)) {
|
||||
if (await this.hideAutofillInlineMenuListOnFilledField(formFieldElement)) {
|
||||
void this.sendExtensionMessage("closeAutofillInlineMenu", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
return;
|
||||
}
|
||||
@@ -461,12 +462,16 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
) {
|
||||
await this.sendExtensionMessage("closeAutofillInlineMenu", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
}
|
||||
|
||||
if (await this.hideOverlayListOnFilledField(formFieldElement as FillableFormFieldElement)) {
|
||||
this.updateOverlayButtonPosition();
|
||||
if (
|
||||
await this.hideAutofillInlineMenuListOnFilledField(
|
||||
formFieldElement as FillableFormFieldElement,
|
||||
)
|
||||
) {
|
||||
this.updateAutofillInlineMenuButtonPosition();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -538,16 +543,16 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
/**
|
||||
* Updates the position of both the overlay button and overlay list.
|
||||
*/
|
||||
private updateOverlayElementsPosition() {
|
||||
this.updateOverlayButtonPosition();
|
||||
this.updateOverlayListPosition();
|
||||
private updateAutofillInlineMenuElementsPosition() {
|
||||
this.updateAutofillInlineMenuButtonPosition();
|
||||
this.updateAutofillInlineMenuListPosition();
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates the position of the overlay button.
|
||||
*/
|
||||
private updateOverlayButtonPosition() {
|
||||
void this.sendExtensionMessage("updateAutofillOverlayMenuPosition", {
|
||||
private updateAutofillInlineMenuButtonPosition() {
|
||||
void this.sendExtensionMessage("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.Button,
|
||||
});
|
||||
}
|
||||
@@ -555,8 +560,8 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
/**
|
||||
* Updates the position of the overlay list.
|
||||
*/
|
||||
private updateOverlayListPosition() {
|
||||
void this.sendExtensionMessage("updateAutofillOverlayMenuPosition", {
|
||||
private updateAutofillInlineMenuListPosition() {
|
||||
void this.sendExtensionMessage("updateAutofillInlineMenuPosition", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
});
|
||||
}
|
||||
@@ -567,9 +572,12 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
* @param isHidden - Indicates if the overlay elements should be hidden.
|
||||
* @param setTransparentOverlay - Indicates if the overlay is closing.
|
||||
*/
|
||||
private toggleOverlayHidden(isHidden: boolean, setTransparentOverlay: boolean = false) {
|
||||
void this.sendExtensionMessage("updateAutofillOverlayMenuHidden", {
|
||||
isOverlayHidden: isHidden,
|
||||
private toggleAutofillInlineMenuHidden(
|
||||
isHidden: boolean,
|
||||
setTransparentOverlay: boolean = false,
|
||||
) {
|
||||
void this.sendExtensionMessage("updateAutofillInlineMenuHidden", {
|
||||
isAutofillInlineMenuHidden: isHidden,
|
||||
setTransparentOverlay,
|
||||
});
|
||||
}
|
||||
@@ -711,7 +719,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
autofillFieldData.readonly = getAttributeBoolean(formFieldElement, "disabled");
|
||||
autofillFieldData.disabled = getAttributeBoolean(formFieldElement, "disabled");
|
||||
autofillFieldData.viewable = true;
|
||||
void this.setupAutofillOverlayListenerOnField(formFieldElement, autofillFieldData);
|
||||
void this.setupAutofillInlineMenuListenerOnField(formFieldElement, autofillFieldData);
|
||||
}
|
||||
|
||||
this.removeHiddenFieldFallbackListener(formFieldElement);
|
||||
@@ -760,7 +768,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
return;
|
||||
}
|
||||
|
||||
this.toggleOverlayHidden(true);
|
||||
this.toggleAutofillInlineMenuHidden(true);
|
||||
this.clearUserInteractionEventTimeout();
|
||||
this.userInteractionEventTimeout = setTimeout(this.triggerOverlayRepositionUpdates, 750);
|
||||
};
|
||||
@@ -779,25 +787,25 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
*/
|
||||
private triggerOverlayRepositionUpdates = async () => {
|
||||
if (!this.recentlyFocusedFieldIsCurrentlyFocused()) {
|
||||
this.toggleOverlayHidden(false, true);
|
||||
this.toggleAutofillInlineMenuHidden(false, true);
|
||||
void this.sendExtensionMessage("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
await this.updateMostRecentlyFocusedField(this.mostRecentlyFocusedField);
|
||||
this.updateOverlayElementsPosition();
|
||||
this.updateAutofillInlineMenuElementsPosition();
|
||||
setTimeout(async () => {
|
||||
this.toggleOverlayHidden(false);
|
||||
this.toggleAutofillInlineMenuHidden(false);
|
||||
if (
|
||||
await this.hideOverlayListOnFilledField(
|
||||
await this.hideAutofillInlineMenuListOnFilledField(
|
||||
this.mostRecentlyFocusedField as FillableFormFieldElement,
|
||||
)
|
||||
) {
|
||||
void this.sendExtensionMessage("closeAutofillInlineMenu", {
|
||||
overlayElement: AutofillOverlayElement.List,
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
}
|
||||
}, 50);
|
||||
@@ -808,7 +816,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
}
|
||||
|
||||
void this.sendExtensionMessage("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
};
|
||||
|
||||
@@ -837,7 +845,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
);
|
||||
}
|
||||
|
||||
private async hideOverlayListOnFilledField(
|
||||
private async hideAutofillInlineMenuListOnFilledField(
|
||||
formFieldElement?: FillableFormFieldElement,
|
||||
): Promise<boolean> {
|
||||
return (
|
||||
@@ -869,7 +877,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
|
||||
this.mostRecentlyFocusedField = null;
|
||||
void this.sendExtensionMessage("closeAutofillInlineMenu", {
|
||||
forceCloseOverlay: true,
|
||||
forceCloseAutofillInlineMenu: true,
|
||||
});
|
||||
};
|
||||
|
||||
@@ -981,7 +989,7 @@ class AutofillOverlayContentService implements AutofillOverlayContentServiceInte
|
||||
});
|
||||
};
|
||||
|
||||
private updateInlineMenuVisibility({ data }: AutofillExtensionMessage) {
|
||||
private updateAutofillInlineMenuVisibility({ data }: AutofillExtensionMessage) {
|
||||
if (isNaN(data?.inlineMenuVisibility)) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -2105,7 +2105,7 @@ export default class AutofillService implements AutofillServiceInterface {
|
||||
if (!inlineMenuPreviouslyDisabled && !inlineMenuCurrentlyDisabled) {
|
||||
const tabs = await BrowserApi.tabsQuery({});
|
||||
tabs.forEach((tab) =>
|
||||
BrowserApi.tabSendMessageData(tab, "updateInlineMenuVisibility", {
|
||||
BrowserApi.tabSendMessageData(tab, "updateAutofillInlineMenuVisibility", {
|
||||
inlineMenuVisibility: currentSetting,
|
||||
}),
|
||||
);
|
||||
|
||||
@@ -2578,7 +2578,7 @@ describe("CollectAutofillContentService", () => {
|
||||
);
|
||||
setupAutofillOverlayListenerOnFieldSpy = jest.spyOn(
|
||||
collectAutofillContentService["autofillOverlayContentService"],
|
||||
"setupAutofillOverlayListenerOnField",
|
||||
"setupAutofillInlineMenuListenerOnField",
|
||||
);
|
||||
});
|
||||
|
||||
|
||||
@@ -205,7 +205,7 @@ class CollectAutofillContentService implements CollectAutofillContentServiceInte
|
||||
autofillField.viewable = await this.domElementVisibilityService.isFormFieldViewable(element);
|
||||
|
||||
if (!currentViewableState && autofillField.viewable) {
|
||||
await this.autofillOverlayContentService?.setupAutofillOverlayListenerOnField(
|
||||
await this.autofillOverlayContentService?.setupAutofillInlineMenuListenerOnField(
|
||||
element,
|
||||
autofillField,
|
||||
);
|
||||
@@ -381,7 +381,7 @@ class CollectAutofillContentService implements CollectAutofillContentServiceInte
|
||||
|
||||
if (elementIsSpanElement(element)) {
|
||||
this.cacheAutofillFieldElement(index, element, autofillFieldBase);
|
||||
void this.autofillOverlayContentService?.setupAutofillOverlayListenerOnField(
|
||||
void this.autofillOverlayContentService?.setupAutofillInlineMenuListenerOnField(
|
||||
element,
|
||||
autofillFieldBase,
|
||||
);
|
||||
@@ -424,7 +424,7 @@ class CollectAutofillContentService implements CollectAutofillContentServiceInte
|
||||
};
|
||||
|
||||
this.cacheAutofillFieldElement(index, element, autofillField);
|
||||
void this.autofillOverlayContentService?.setupAutofillOverlayListenerOnField(
|
||||
void this.autofillOverlayContentService?.setupAutofillInlineMenuListenerOnField(
|
||||
element,
|
||||
autofillField,
|
||||
);
|
||||
@@ -1321,7 +1321,7 @@ class CollectAutofillContentService implements CollectAutofillContentServiceInte
|
||||
const cachedAutofillFieldElement = this.autofillFieldElements.get(formFieldElement);
|
||||
cachedAutofillFieldElement.viewable = true;
|
||||
|
||||
void this.autofillOverlayContentService?.setupAutofillOverlayListenerOnField(
|
||||
void this.autofillOverlayContentService?.setupAutofillInlineMenuListenerOnField(
|
||||
formFieldElement,
|
||||
cachedAutofillFieldElement,
|
||||
);
|
||||
|
||||
@@ -38,7 +38,7 @@ describe("generateRandomCustomElementName", () => {
|
||||
|
||||
describe("sendExtensionMessage", () => {
|
||||
it("sends a message to the extention", () => {
|
||||
const extensionMessageResponse = sendExtensionMessage("updateAutofillOverlayMenuHidden", {
|
||||
const extensionMessageResponse = sendExtensionMessage("updateAutofillInlineMenuHidden", {
|
||||
display: "none",
|
||||
});
|
||||
jest.spyOn(chrome.runtime, "sendMessage");
|
||||
|
||||
Reference in New Issue
Block a user