Configuration
The widget is initialized by calling FanIDWidget.init() with a configuration object. baseUrl is required; every
other field is optional.
Minimal configuration
FanIDWidget.init({
baseUrl: 'https://your-org.fanid.co',
})
baseUrl points to your FanID tenant domain. Each customer has its own subdomain (e.g. team.fanid.co) or custom
domain (e.g. fans.your-site.com) — all widget API requests are sent to this URL directly.
Full configuration
FanIDWidget.init({
baseUrl: 'https://your-org.fanid.co', // Required: FanID tenant domain
containerId: 'my-widget-container', // DOM element ID for the floating widget panel
transport: 'bearer', // 'cookie' | 'bearer' — overrides detection; bearer for every embed off the tenant host
floatingWidget: { // Shorthand: true (defaults) / false (disable)
enabled: true, // Show the floating sign-in/profile panel
position: 'top-right', // 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right' | 'center'
autoShow: true, // Auto-mount on init. false = user must call showFloatingWidget()
persistClose: 'session', // 'session' | 'persistent' | 'never'
},
gatedContent: {
enabled: true, // Enable gated content features
customElementName: 'wmt-fanid-protected', // Custom element tag name
placeholder: {
title: 'Exclusive Content', // Overlay heading
message: 'Sign in with FanID to view this content', // Overlay description
buttonText: 'Sign In', // CTA button label
},
style: 'blur', // Visual style: 'blur' | 'gradient' | 'cover'
blurAmount: 8, // Blur intensity in pixels (blur mode only)
minHeight: 280, // Minimum height for the gated overlay container (px)
maxHeight: null, // Optional cap on the gated area height (px) — collapses content below
overlayAlign: 'top', // Vertical placement of the prompt: 'top' | 'center' | 'bottom'
teaserHeight: undefined, // Visible teaser height in pixels (gradient mode)
revealAnimation: 'fade', // Reveal animation: 'fade' | 'slide' | 'none'
},
})
Options reference
baseUrl
| Type | string |
| Required | yes |
| Example | 'https://your-org.fanid.co' |
Your FanID tenant domain. Every customer is provisioned on a unique subdomain ({tenant}.fanid.co) or a custom
domain (fans.your-site.com). All API calls (/api/subscriber/*), the login page, and profile page are served from
this URL. The widget logs an error and aborts init() if baseUrl is missing — there is no shared fanid.co
fallback.
If you operate across staging and production, pass the appropriate environment URL at init time — for example
'https://staging.your-org.fanid.co' vs 'https://your-org.fanid.co'.
The origin where you embed the widget (the page host) must also be registered as one of your tenant's approved
domains — the Domains list for your organization in the FanID admin dashboard. If the widget cannot resolve the
organization from baseUrl — typically because the embedding origin is not approved — it shows a red "Domain not
configured" error in the floating panel so the misconfiguration is visible immediately during integration.
containerId
| Type | string |
| Default | undefined |
DOM element ID where the floating widget panel will mount. If not provided, the widget creates its own container and
prepends it to document.body.
transport
| Type | 'cookie' | 'bearer' |
| Default | auto-detected |
How the widget authenticates API calls to your tenant. The widget detects this for you and you should rarely need to set it manually.
'cookie'— selected only when the embedding page's host is exactly equal to thebaseUrlhost, port included. The request is then first-party: the widget calls the tenant API withcredentials: 'include'and the portal's own session cookie is in scope. In practice this means the FanID portal itself, not a cross-domain embed.'bearer'— selected in every other case, including sibling subdomains of the tenant and hosts that merely share a parent domain with it. Every embed on a site you own takes this path. The widget receives a one-time exchange token after sign-in, redeems it for a bearer session, stores it locally, and sends it asAuthorization: Bearer <token>on every request. This is the path that works around browser third-party cookie restrictions.
There is no registrable-domain (eTLD+1) matching: sharing a parent domain with the tenant does not select the cookie transport. Assume bearer for any embed you do not serve from the tenant host.
Set transport: 'cookie' explicitly only to exercise the same-host path deliberately. Set transport: 'bearer' to
pin the cross-origin flow on a page that would otherwise match the tenant host exactly.
For bearer transport to work, the embedding origin must be added to your tenant's approved domains — the Domains list for your organization in the FanID admin dashboard. See Cross-Domain Setup for the full picture.
floatingWidget
| Type | boolean | FloatingWidgetConfig |
| Default | true |
Controls the floating sign-in / profile panel. Pass true to use defaults, false to disable auto-mount, or an
object for full control.
// Defaults: auto-mount in the top-right corner
FanIDWidget.init({ floatingWidget: true })
// Disable auto-mount. Panel still works via showFloatingWidget() / hideFloatingWidget().
FanIDWidget.init({ floatingWidget: false })
// Fine-grained control
FanIDWidget.init({
floatingWidget: {
enabled: true,
position: 'bottom-right',
autoShow: true,
persistClose: 'persistent',
},
})
The panel can always be shown or hidden programmatically regardless of these settings using
FanIDWidget.showFloatingWidget() and FanIDWidget.hideFloatingWidget(). showFloatingWidget() also clears any
persisted close flag.
floatingWidget.enabled
| Type | boolean |
| Default | true |
Master toggle. When false, the panel is not auto-mounted on init. Programmatic show/hide still works.
floatingWidget.position
| Type | 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right' | 'center' |
| Default | 'top-right' |
Position of the floating panel. Each preset has a tailored entrance animation (slide-down for top-, slide-up for
bottom-, fade-scale for center). Change at runtime with FanIDWidget.setFloatingWidgetPosition(position).
floatingWidget.autoShow
| Type | boolean |
| Default | true |
Whether to mount the panel automatically on init(). Set to false if you want the panel to only appear when
showFloatingWidget() is called explicitly (e.g. from a sign-in CTA click).
floatingWidget.persistClose
| Type | 'session' | 'persistent' | 'never' |
| Default | 'session' |
Where the "user closed the panel" flag is stored:
'session'—sessionStorage. Panel stays hidden for the rest of the browser tab's session.'persistent'—localStorage. Panel stays hidden across reloads and new sessions, untilshowFloatingWidget()is called.'never'— no persistence. Close just hides; the panel reappears on the next page load.
Use 'persistent' when you want a one-click dismiss that sticks until your app explicitly re-opens the panel.
gatedContent
Configuration for the gated content feature.
gatedContent.enabled
| Type | boolean |
| Default | true |
Enable or disable gated content. When false, <wmt-fanid-protected> elements and [data-fanid-gated] attributes are
ignored.
gatedContent.customElementName
| Type | string |
| Default | 'wmt-fanid-protected' |
The HTML tag name for the built-in gated content Custom Element. Change this if you need a site-specific tag name.
gatedContent.placeholder
Configuration for the overlay displayed on gated content.
| Property | Type | Default |
|---|---|---|
title | string | 'Exclusive Content' |
message | string | 'Sign in with FanID to view this content' |
buttonText | string | 'Sign In' |
gatedContent.style
| Type | 'blur' | 'gradient' | 'cover' |
| Default | 'blur' |
The visual style used to obscure gated content. See Visual Styles for examples.
gatedContent.blurAmount
| Type | number |
| Default | 8 |
Blur intensity in pixels. Only applies when style is 'blur'.
gatedContent.minHeight
| Type | number |
| Default | 280 |
Minimum height in pixels for the gated content overlay container. Ensures the sign-in prompt is always visible and clickable, even when the gated content is short.
gatedContent.maxHeight
| Type | number | null |
| Default | null |
Optional ceiling for the gated host element. When set, the SDK applies max-height: <value>px with overflow: hidden
on the gated container — anything below that mark is clipped and covered by the overlay. Use this when the gated
content would otherwise be long enough to push the sign-in prompt below the fold. Pair with overlayAlign: 'top' so
the prompt sits right at the top of the visible area.
gatedContent.overlayAlign
| Type | 'top' | 'center' | 'bottom' |
| Default | 'top' |
Vertical placement of the sign-in prompt inside the gated host. 'top' (default) keeps the panel close to the top
edge so the user sees it without scrolling — recommended for the common case. 'center' matches the legacy behavior
of vertically centering the prompt; 'bottom' pins it to the bottom edge. Internally this maps to the
--fanid-gate-overlay-align CSS variable (flex-start / center / flex-end).
gatedContent.teaserHeight
| Type | number |
| Default | undefined |
Height in pixels of the visible teaser area. When set, the first N pixels of content are fully visible before fading
into the gate. Most useful with the 'gradient' style.
gatedContent.revealAnimation
| Type | 'fade' | 'slide' | 'none' |
| Default | 'fade' |
Animation played when gated content is revealed after authentication.
Request telemetry
Not a configuration option — listed here because it shows up in your network tab.
Every request the widget sends to baseUrl carries two query parameters: widget_version (the
widget package version, fixed at build time) and widget_transport ('cookie' or 'bearer' — the
transport that request actually used).
GET https://your-org.fanid.co/api/subscriber/me?widget_version=0.2.2&widget_transport=bearer
They apply to every endpoint the widget calls and are appended to any query string already present. FanID reads them from its request logs to see which widget builds are live and which transport each embed selected. They cannot be turned off, carry no personal data, and nothing in the widget's behavior depends on them. See Cross-Domain Setup for details.