> ## Documentation Index
> Fetch the complete documentation index at: https://notifizz.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Notification Widget Authentication

> Pick the right widget auth mode — Firebase, backend token, publicly-signed JWT, or none. The conceptual overview; per-mode reference lives under each SDK page.

# Notification widget authentication

Authentication controls how the Notification Center widget identifies the current user to Notifizz. The right choice depends on your existing auth stack and your security requirements.

## TL;DR

* **Four modes total**: `firebase`, `backendToken`, `none`, and `PubliclySignedJwt`.
* **Three are SDK-exposed** via `authType`: `firebase`, `backendToken`, `none`.
* **`PubliclySignedJwt` is dashboard-configured** — no SDK shorthand. The widget picks it up from the server-side auth strategy attached to your environment.
* Production must use `firebase`, `backendToken`, or `PubliclySignedJwt`. `none` is dev-only.

## The four modes

### Firebase Authentication

**Best for:** Apps already using Firebase Auth.

The widget passes a Firebase ID token; Notifizz verifies it server-side against Firebase.

```javascript theme={null}
{
  apiKey: "YOUR_FRONT_API_KEY",
  authType: "firebase",
  token: firebaseUser.idToken,
}
```

* **Where the token comes from** — your Firebase client SDK after `signInWith…`.
* **What Notifizz does** — verifies the token's signature against the project's JWKS, extracts the user identity, scopes the widget session.
* **Backend work** — none beyond what you already do for Firebase.

See the [Firebase auth reference](/docs/sdks/authentication/firebase).

### Backend Token

**Best for:** Apps with their own auth, no Firebase, security-sensitive notifications.

Your backend uses the Notifizz Node SDK to generate a hashed token and ships it to the frontend along with the user identity:

```javascript theme={null}
// Backend
const token = client.generateHashedToken("u_42");

// Frontend
{
  apiKey: "YOUR_FRONT_API_KEY",
  authType: "backendToken",
  token,
  userId: "u_42",
  userEmail: "alice@example.com",
}
```

* **What the token is** — `SHA-256(userId + authSecretKey)`, hex-encoded.
* **What Notifizz does** — recomputes the hash with its server-side `authSecretKey` and compares.
* **Backend work** — generate one token per user per session and ship it (typically alongside login response or via a dedicated endpoint).

```mermaid theme={null}
sequenceDiagram
    participant Frontend
    participant Backend as Your backend
    participant Notifizz

    Frontend->>Backend: User logs in
    Backend->>Backend: client.generateHashedToken(userId)
    Backend->>Frontend: Return token + user info
    Frontend->>Notifizz: Mount widget with token + userId + userEmail
    Notifizz-->>Notifizz: Recompute hash, compare
    Notifizz->>Frontend: Connected — notifications flow
```

See the [backend tokens reference](/docs/sdks/authentication/backend-tokens).

### Publicly-Signed JWT

**Best for:** Apps using Auth0, Clerk, Cognito, Supabase Auth, or any provider that publishes a JWKS endpoint.

The widget passes a JWT issued by your identity provider; Notifizz verifies it against a JWKS URL configured in the dashboard. Unlike the other three, this mode has **no SDK shorthand** — there's no `authType: "publiclySignedJwt"` in the call site. Instead, the dashboard's `notificationCenterSetup` dev-task wires the JWKS URL + expected issuer/audience claims, and the widget picks the strategy up server-side from your Front API Key.

<Note>
  In the backend codebase the strategy is called `CustomRsaJwt` — same mode, different name. Customer-facing prose always uses **`PubliclySignedJwt`**; the backend alias only surfaces in dashboard logs and a few internal tools. Don't be surprised if you see it once.
</Note>

When `PubliclySignedJwt` is the configured strategy, the widget reads the JWT from your existing identity provider session and passes it to Notifizz transparently — your call site looks like the other modes minus the `authType` field, since the strategy is server-side.

See the [publicly-signed JWT reference](/docs/sdks/authentication/publicly-signed-jwt) for the dashboard setup, required claims, and per-provider walkthroughs (Auth0 / Clerk / Cognito / Supabase Auth).

### No authentication

**Best for:** Local development, demos, internal tools with no security needs.

```javascript theme={null}
{
  apiKey: "YOUR_FRONT_API_KEY",
  authType: "none",
  userId: "u_42",
  userEmail: "alice@example.com",
}
```

<Warning>
  `authType: "none"` does not verify the user. Anyone with the API key and a `userId` can read that user's inbox. Never ship this to production.
</Warning>

See the [no-auth reference](/docs/sdks/authentication/no-auth).

## Comparison

|                           | Firebase      | Backend Token                  | Publicly-Signed JWT                | None                  |
| ------------------------- | ------------- | ------------------------------ | ---------------------------------- | --------------------- |
| **Identity verification** | Firebase JWKS | HMAC + auth secret             | Provider JWKS                      | None                  |
| **Backend work**          | none          | generate hashed token          | configure JWKS URL in dashboard    | none                  |
| **SDK `authType` value**  | `'firebase'`  | `'backendToken'`               | n/a (server-side)                  | `'none'`              |
| **Required SDK fields**   | `token`       | `token`, `userId`, `userEmail` | (provider session)                 | `userId`, `userEmail` |
| **Best for**              | Firebase apps | Custom auth                    | Auth0 / Clerk / Cognito / Supabase | dev only              |

## SDK type union

Across all three frontend SDKs (`@notifizz/react`, `@notifizz/angular`, `@notifizz/vanilla`), the call-site type is:

```ts theme={null}
type AuthType = 'firebase' | 'backendToken' | 'none';
```

`PubliclySignedJwt` deliberately does not appear in this union — it's reachable only through dashboard configuration so the SDK surface stays minimal and the strategy can be swapped without a frontend deploy.

## FAQ

<AccordionGroup>
  <Accordion title="Why isn't `PubliclySignedJwt` an SDK option?">
    Because the strategy is decided per-environment and changing it shouldn't require a frontend deploy. The dashboard owns the JWKS URL, expected issuer, expected audience — your code just initialises the widget and the strategy applies server-side. This also keeps the SDK surface to three options and pushes config decisions to the people who need them (operators, not developers).
  </Accordion>

  <Accordion title="I see `CustomRsaJwt` in the dashboard logs.">
    Same thing as `PubliclySignedJwt` — the backend originally named the strategy `CustomRsaJwt` and the rename hasn't propagated everywhere. Treat them as identical. Customer-facing prose uses `PubliclySignedJwt`.
  </Accordion>

  <Accordion title="Can I switch auth modes without changing my code?">
    Between `firebase` / `backendToken` / `none` — no, those are explicit `authType` values in your call site. Between any SDK mode and `PubliclySignedJwt` — yes, since `PubliclySignedJwt` is configured server-side. Many teams ship `backendToken` initially and switch to `PubliclySignedJwt` later.
  </Accordion>

  <Accordion title="How do I migrate from `none` to `backendToken` for production?">
    On the backend, expose an authenticated endpoint that returns `{ token: client.generateHashedToken(userId), userId, userEmail }`. On the frontend, mount the widget after that endpoint resolves and switch `authType` to `backendToken`. The transition is per-environment — keep `none` on dev if your team uses it for fast iteration.
  </Accordion>

  <Accordion title="The token expired mid-session — what happens?">
    The widget surfaces `state.hasError = true` with an error code. Refresh the token from your backend (or re-fetch the Firebase ID token) and re-mount the widget — there is no in-place re-auth today.
  </Accordion>

  <Accordion title="Multiple users on the same browser — how do I switch?">
    Destroy the current widget, mount a new one with the new identity. Across all three SDKs the pattern is the same: clear cached real-time state by destroying the instance, then create a fresh one with the new `token` + `userId`.
  </Accordion>
</AccordionGroup>

## See also

<CardGroup cols={2}>
  <Card title="Authentication overview (SDK)" icon="key" href="/docs/sdks/authentication/overview">
    The four-mode model with per-mode references.
  </Card>

  <Card title="Backend tokens" icon="lock" href="/docs/sdks/authentication/backend-tokens">
    `client.generateHashedToken()` end-to-end.
  </Card>

  <Card title="Firebase auth" icon="fire" href="/docs/sdks/authentication/firebase">
    Pass a Firebase ID token to the widget.
  </Card>

  <Card title="Publicly-signed JWT" icon="shield" href="/docs/sdks/authentication/publicly-signed-jwt">
    Auth0 / Clerk / Cognito / Supabase setup.
  </Card>
</CardGroup>
