[PM-4678] [Defect] Passkey browser fallback broken on iCloud (#6783)
* [PM-4678] fix: add cross-origin frame handling * [PM-4678] feat: force window and tab focus
This commit is contained in:
parent
200189c895
commit
ffd08a6d6d
|
@ -312,12 +312,36 @@ export default class RuntimeBackground {
|
|||
case "checkFido2FeatureEnabled":
|
||||
return await this.main.fido2ClientService.isFido2FeatureEnabled();
|
||||
case "fido2RegisterCredentialRequest":
|
||||
return await this.abortManager.runWithAbortController(msg.requestId, (abortController) =>
|
||||
this.main.fido2ClientService.createCredential(msg.data, sender.tab, abortController)
|
||||
return await this.abortManager.runWithAbortController(
|
||||
msg.requestId,
|
||||
async (abortController) => {
|
||||
try {
|
||||
return await this.main.fido2ClientService.createCredential(
|
||||
msg.data,
|
||||
sender.tab,
|
||||
abortController
|
||||
);
|
||||
} finally {
|
||||
await BrowserApi.focusTab(sender.tab.id);
|
||||
await BrowserApi.focusWindow(sender.tab.windowId);
|
||||
}
|
||||
}
|
||||
);
|
||||
case "fido2GetCredentialRequest":
|
||||
return await this.abortManager.runWithAbortController(msg.requestId, (abortController) =>
|
||||
this.main.fido2ClientService.assertCredential(msg.data, sender.tab, abortController)
|
||||
return await this.abortManager.runWithAbortController(
|
||||
msg.requestId,
|
||||
async (abortController) => {
|
||||
try {
|
||||
return await this.main.fido2ClientService.assertCredential(
|
||||
msg.data,
|
||||
sender.tab,
|
||||
abortController
|
||||
);
|
||||
} finally {
|
||||
await BrowserApi.focusTab(sender.tab.id);
|
||||
await BrowserApi.focusWindow(sender.tab.windowId);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -157,18 +157,24 @@ function isWebauthnCall(options?: CredentialCreationOptions | CredentialRequestO
|
|||
* Wait for window to be focused.
|
||||
* Safari doesn't allow scripts to trigger webauthn when window is not focused.
|
||||
*
|
||||
* @param fallbackWait How long to wait when the script is not able to add event listeners to `window.top`. Defaults to 500ms.
|
||||
* @param timeout Maximum time to wait for focus in milliseconds. Defaults to 5 minutes.
|
||||
* @returns Promise that resolves when window is focused, or rejects if timeout is reached.
|
||||
*/
|
||||
async function waitForFocus(timeout: number = 5 * 60 * 1000) {
|
||||
if (window.top.document.hasFocus()) {
|
||||
return;
|
||||
async function waitForFocus(fallbackWait = 500, timeout = 5 * 60 * 1000) {
|
||||
try {
|
||||
if (window.top.document.hasFocus()) {
|
||||
return;
|
||||
}
|
||||
} catch {
|
||||
// Cannot access window.top due to cross-origin frame, fallback to waiting
|
||||
return await new Promise((resolve) => window.setTimeout(resolve, fallbackWait));
|
||||
}
|
||||
|
||||
let focusListener;
|
||||
const focusPromise = new Promise<void>((resolve) => {
|
||||
focusListener = () => resolve();
|
||||
window.top.addEventListener("focus", focusListener, { once: true });
|
||||
window.top.addEventListener("focus", focusListener);
|
||||
});
|
||||
|
||||
let timeoutId;
|
||||
|
|
Loading…
Reference in New Issue