Skip to main content

Error catalogue reference

Every error Notifizz returns has a stable string code so you can match on it programmatically. This page lists the public catalogue: backend HTTP errors, enricher SDK errors, and the HTTP status each maps to.

TL;DR

  • Backend errors return { code: <stable-string>, ... } in the body.
  • Enricher errors (Node SDK) are typed exception classes — EnricherInputValidationError, EnricherHmacVerificationError, etc.
  • HTTP status follows the family (401 for auth, 400 for input, 404 for not-found, 500 for handler failure).

Backend HTTP errors

Authorization (auth/*, authorization/*)

CodeStatusWhen
auth/tracking-secret-key401The sdkSecretKey header is missing, malformed, or doesn’t resolve to an environment. (NoTrackAuthorization)
auth/invalid-authorization403The sdkSecretKey did not match any environment. Most common on POST /v1/events/track. (InvalidAuthorization)
auth/invalid-token-signature401A widget JWT failed signature verification (Firebase, PubliclySignedJwt).
auth/invalid-api-key401The Front API Key in the widget request is unknown.
auth/no-public-key-registered401PubliclySignedJwt strategy was selected but the environment has no public key configured in the dashboard.
auth/invalid-inputs400A widget auth call (/v1/users/auth) is missing required JWT paths or fields.
auth/onboarding-not-completed403The organisation hasn’t finished its onboarding — the surface in question is gated until onboarding completes.
authorization/organisation-not-authorized-for-this-user403The dashboard user doesn’t have a role on the target organisation.
authorization/unauthorizedConfigIdForOrganisation404A request referenced a configId that belongs to a different organisation.

HTTP / functional (other/*, notification/*)

CodeStatusWhen
other/unknown500Catch-all for unexpected backend errors. The body’s message field has details.
notification/config-not-found404A request referenced a notificationConfigId that doesn’t exist.

Admin / event (event/*, region/*, organization-settings/*)

CodeStatusWhen
event/not-found404A dashboard request referenced an event id that doesn’t exist.
event/invalid-name400An event name failed the grammar (see Event Tracking). Body includes a reason field.
region/already-set409The organisation’s region was already chosen and cannot be changed.
organization-settings/already-exists409Tried to create org settings for an org that already has them.

Enricher SDK errors (Node)

The Node SDK (@notifizz/nodejs) ships typed exception classes for the enricher subsystem. client.dispatch(body) encodes them in the response body ({ ok: false, error: { code, message } }) and the Notifizz backend gateway translates error.code back to typed domain errors. The SDK does NOT throw across the dispatch boundary — Promise<DispatchResponse> is the contract. The classes below are the registration-time and internal exceptions you may still want to catch in unit tests.
ClassBody error.code (when it surfaces from dispatch)When
EnricherRegistrationErrorn/a (thrown synchronously at registration time)client.enricher() called with a duplicate name, empty name, invalid schema, or missing handler.
EnricherInputValidationErrorinput-invalid (with details)Incoming params failed the registered input schema.
EnricherHmacVerificationError401missing-header / bad-signature / stale-timestampHMAC verification failed. The reason discriminant tells you which check failed.
EnricherNotFoundError404enricher-not-foundPOST ?name=foo for a name that wasn’t registered on this client.
EnricherHandlerError500handler-errorThe user-supplied handler threw. The cause field carries the original error.
(any other thrown error)500internalCatch-all.
The error classes themselves are exported from @notifizz/nodejs so you can instanceof-check them in your own logging or error reporting.
import { EnricherInputValidationError, EnricherHmacVerificationError } from "@notifizz/nodejs";

try {
  // ...
} catch (e) {
  if (e instanceof EnricherInputValidationError) {
    logger.warn({ details: e.details }, "enricher input mismatch");
  } else if (e instanceof EnricherHmacVerificationError) {
    logger.warn({ reason: e.reason }, "enricher HMAC failed");
  }
  throw e;
}

Connector webhook errors

Connector webhooks return HTTP-level errors when signature verification fails — there’s no per-provider error code, just the status. See connector webhooks reference for the per-provider details.
StatusWhen
401Signature verification failed (header missing, secret mismatch, or — for Stripe — timestamp drift).
404The :sourceId in the URL doesn’t exist.
200 (paused)Source is paused in the dashboard — Notifizz acks the provider but drops the payload.

SDK retry behaviour

All three event-tracking SDKs retry transient failures twice (1s, then 2s) before bubbling. Errors that bubble:
  • Node — original axios error after 3 attempts.
  • JavaIOException (the last one) after 3 attempts.
  • PHP — original GuzzleHttp\Exception\GuzzleException after 3 attempts.
Permanent errors (e.g. 403 auth/invalid-authorization) still go through the retry loop today — improvements to short-circuit on permanent failures are tracked separately.

FAQ

auth/invalid-authorization on POST /v1/events/track means the sdkSecretKey (in the body and the Bearer header) didn’t resolve to an environment. Three common causes: (1) wrong environment (dev key in prod or vice versa); (2) typo / extra whitespace; (3) the key was rotated in the dashboard and your service hasn’t reloaded.
The 400 response carries { error: { code: "input-validation-failed", message, details } }. The details field is an array of validation issues — for Zod-derived schemas, it’s the Zod issues array; for raw JSON Schemas, it’s Ajv’s errors array. Read the first entry to see which property failed.
The registry is per-client-instance. If you have two NotifizzClient instances and only register the enricher on one, dispatch on the other returns { ok: false, error: { code: "enricher-not-found" } }. Make sure the same instance that called enricher() is the one whose dispatch() is wired in the controller.
There is no 422 path on the public endpoints. 400 covers both grammar violations (event name) and DTO validation (class-validator rejecting malformed bodies). Status follows the family — read the code field to disambiguate.
A backend exception that didn’t get caught by a more specific handler. Treat it as “infrastructure issue, retry, escalate if persistent”. The message field has the specific error message; the correlation id (in response headers) lets us trace it.
Read the reason field. missing-header means the HMAC headers weren’t sent (the backend usually sends them — if missing, the request didn’t come from Notifizz). bad-signature means the secret mismatches or the body was modified (often a JSON parse + re-serialise breaking the byte-for-byte match). stale-timestamp means clock drift outside ±5 minutes — NTP your enricher host.

See also

Event Tracking

Detailed error shapes for POST /v1/events/track.

Enrichers protocol

HMAC verification, input/output schemas.

Connector webhooks

Per-provider signature error semantics.

Troubleshooting

Cross-cutting failure modes — symptom → cause → fix.