跳转到内容

Authentication cheat sheet

此内容尚不支持你的语言。

Wetel has three credentials. Each operation accepts exactly one of them, and the reference pages say which. The full explanation is in Authentication; this page is the short version to keep open while you code.

CredentialHeaderWhere it comes fromLifetimeKeep itUsed for
API keyX-Api-Key: sk_...createNamedApiKey (shown once)Until revokedOn your server onlyServer-to-server runtime calls: sdkStart, sessionsByExternalCustomerId, runWorkflowTask and the like
Session token (avatarToken)Authorization: Bearer <avatarToken>Returned by sdkStartAbout one hour; renew with refreshAvatarToken up to 10 minutes after expiryWherever the conversation runs (server or browser)One session only: sdkSendMessage, sdkEndSession, the sessionEvents subscription
Dashboard JWTAuthorization: Bearer <jwt>The login mutation (a person, or a one-off setup script)Short-lived (expiresIn in the login response is the absolute expiry)Not in a long-running serviceBuilding and managing: agents, workflows, API keys, approvals, reading a session with session(id)

An API key is never accepted where a JWT is expected, and the other way round: a management call made with an API key answers Unauthorized. Keys and tokens belong to one environment; a sandbox key is refused in production.

sequenceDiagram
participant S as Your server
participant W as Wetel API
S->>W: sdkStart (X-Api-Key)
W-->>S: sessionId, avatarToken
S->>W: sdkSendMessage (Bearer avatarToken)
W-->>S: true
S->>W: sessionsByExternalCustomerId (X-Api-Key), repeat
W-->>S: messages, reply included
S->>W: sdkEndSession (Bearer avatarToken)
x-huat-platform: customer

Send it on every request, with every credential (on a WebSocket subscription it goes inside the connection_init payload instead, see Events and Subscriptions). The credential is checked first and the header second, so:

  • With a valid credential and no header, the answer is FORBIDDEN with Platform is not specified!. It looks like a permissions problem but is only the header.
  • With no credential and no header, you see the credential error (UNAUTHENTICATED) first. Fix both.

All of these arrive with HTTP status 200 in errors[0]; branch on extensions.code, not on the message text.

messageextensions.codeUsual cause
Missing X-Api-Key headerUNAUTHENTICATEDAn API-key operation (for example sdkStart) called without X-Api-Key, often with the key in Authorization instead
Invalid API keyUNAUTHENTICATEDA typo, a revoked key, or a key from the other environment
UnauthorizedUNAUTHENTICATEDA JWT operation called with an API key or a session token, or with an expired JWT
Missing or malformed Authorization headerUNAUTHENTICATEDA session-token operation without Authorization: Bearer <avatarToken> (the Bearer prefix is required)
Invalid or expired avatar tokenUNAUTHENTICATEDThe session token is older than about an hour (refresh it), or something else was sent as the session token
This credential is no longer valid. Please sign in again.UNAUTHENTICATEDThe JWT belongs to a user that no longer exists
This account has been suspended.UNAUTHENTICATEDThe JWT’s user is suspended
This avatar token is not valid for the requested sessionFORBIDDENThe token belongs to a different session than the sessionId you sent
Platform is not specified!FORBIDDENThe x-huat-platform header is missing
Platform is not allowedFORBIDDENThe header has an unknown value; send customer
Mismatched target platform between request headers and access token!FORBIDDENA JWT issued for another Wetel application (for example the admin portal) was sent to this API
Only the owner of this workspace can do thisFORBIDDENAn owner-only operation (the approvals inbox, granting key scopes) called by a member
No tenant assigned, No tenant resolved from API keyFORBIDDENThe account behind the credential is not attached to a workspace

More codes, including validation errors and rate limits, are on Errors.

  • Put the API key in your server’s secret store. Never in a browser, a mobile app or a repository.
  • One named key per consumer (each environment, each application), so revoking one breaks nothing else.
  • Treat the session token as a session cookie: hand it to the code that runs the conversation, renew it with refreshAvatarToken, and let it die with sdkEndSession.
  • A JWT cannot be revoked before it expires. Use it for setup and the dashboard, not as your service’s credential.