Skip to content
LogoLogo

transportMode

How the SDK reaches keys.jaw.id in CrossPlatform mode: an embedded iframe dialog with automatic popup fallback (default), or a popup window.

Type: 'popup' | 'iframe' | 'auto' Required: No Default: 'auto' (embedded iframe primary) Applies to: CrossPlatform mode only (ignored in AppSpecific mode)

Values

ValueBehavior
'auto'Default. Embeds keys.jaw.id as an in-page dialog, with automatic popup fallback where iframes can't work (see below).
'iframe'Same as 'auto' in this release.
'popup'Legacy behavior: always opens keys.jaw.id in a popup window. Set this explicitly to opt out of the embedded dialog.

The fallback matrix below means 'auto' never does worse than the popup: on browsers or pages where the iframe can't work, the SDK opens a popup exactly as before. If you need the popup unconditionally, set transportMode: 'popup'.

Usage

No configuration is needed for the default embedded dialog. To opt out and force the legacy popup:

import { jaw } from '@jaw.id/wagmi';
 
const connector = jaw({
  apiKey: 'your-api-key',
  appName: 'My App',
  preference: {
    transportMode: 'popup', // opt out of the embedded dialog
  },
});

With Provider Directly

import { JAW } from '@jaw.id/core';
 
const sdk = JAW.create({
  apiKey: 'your-api-key',
  appName: 'My App',
  preference: {
    transportMode: 'popup', // opt out of the embedded dialog
  },
});

Why an iframe?

The popup flow opens a separate window for sign-in and transaction confirmation, which interrupts the user and is easy to lose behind the main window. The iframe renders the same keys.jaw.id UI inline — a bottom drawer on mobile, a centered dialog on desktop — so the user never leaves the page.

The wallet, passkeys, and message protocol are identical across both transports; only the carrier changes.

Automatic popup fallback

Even with transportMode: 'iframe', the SDK falls back to a popup per request when an iframe cannot do the job:

ConditionWhy
Safari + passkey creation (eth_requestAccounts, wallet_connect)Safari does not support creating passkeys inside cross-origin iframes. Sign-in still happens in the iframe; only first-time credential creation uses a popup.
Non-HTTPS origin (incl. http://localhost dev servers)The iframe transport requires a real HTTPS origin. Any http:// page — including http://localhost and http://127.0.0.1, which browsers treat as secure contexts — falls back to the popup. HTTPS (and https://localhost) gets the iframe.
Occluded / untrusted embeddingIf the dialog's visibility can't be verified (no IntersectionObserver v2) and the embedder isn't a trusted host, the SDK uses a popup to prevent clickjacking. The user can also choose "Continue in new window" at any time.

In the worst case, 'iframe' degrades to exactly the popup behavior — it never does worse than today.

Embedding requirements

When you use the iframe transport, the SDK creates the iframe for you with the correct WebAuthn permissions (allow="publickey-credentials-get …; publickey-credentials-create …" scoped to the keys origin) and sandbox attributes. You don't need to configure anything in your app — no headers, no allow attribute, no CSP changes on your side.

Requirements that must already hold:

  • Your app is served over HTTPS. Plain-http:// origins — including http://localhost dev servers — fall back to the popup transport (see the fallback matrix above). To exercise the iframe locally, serve your dev app over HTTPS (e.g. https://localhost).
  • The user interacts with the dialog directly (WebAuthn in an iframe requires a user gesture).

Browser support

CapabilityChrome / EdgeFirefoxSafari
Passkey sign-in in iframe (get)84+118+15.5+
Passkey creation in iframe (create)123+123+Not supported → popup fallback

Anything older falls back to the popup transport automatically.

Notes for Safari users

On Safari, browser storage inside a third-party iframe is partitioned per embedding app. A returning user may need to re-authenticate with their passkey (a single tap) rather than being silently reconnected. Sign-in, signing, and transactions all work in the iframe; only first-time passkey creation uses a popup.

See also