Skip to content

API tab: say what the credentials are and which one to use - #125

Closed
phwizard wants to merge 1 commit into
devfrom
ux/api-tab-clarity
Closed

phwizard wants to merge 1 commit into
devfrom
ux/api-tab-clarity

Conversation

@phwizard

Copy link
Copy Markdown
Member

The CEO flagged this tab as confusing. Current copy calls the app's id "Key", which reads as half of a key/secret pair when it is actually the App ID; says the pair can "generate JWT tokens etc" without saying which token or for what; and mentions a Rotate action that is not on this screen.

Changes

  • Correct labels: App ID and App Secret, with one line on what each is for and that the secret belongs on a server you control.
  • A "which credential do I need?" table mapping the three kinds to the situation each is for: user token (a person acting as themselves), app token (work scoped to one app: broadcasts, sources, bot config), server/B2B token (tenant provisioning: creating apps, batch users, app tokens).
  • A "Connect an AI assistant" section with the hosted MCP OAuth URL and a copy button, plus a pointer to Account → AI Assistants for clients that cannot run a sign-in flow. It says explicitly that the assistant acts as the signed-in person and never needs the App Secret, because the natural assumption is the opposite.
  • The rotate warning now sits next to the credentials it applies to.

Type-clean, Prettier-clean, no behaviour or API change.

What this PR deliberately does not do

The CEO's actual ask was a ready-made B2B token on this screen. That is not possible today: I checked the backend and no endpoint issues a type=server tokenTOKEN_PURPOSES.SERVER is only ever verified (middlewares/auth.mw.ts, controllers/internal.controller/verifyToken.js), never signed for a caller. Today the only way to get one is to sign it yourself from the App Secret, which is what an integrator has to do and what I had to do to test the MCP server.

Spec for the follow-up is in the BDSM report; short version: an authenticated owner-only endpoint that signs { data: { type: 'server', appId, tenantId } } with deriveScopedSecret(appSecret, 'server'), with a TTL and an audit row, then surface it here behind a reveal-once control like the Secret component.

https://claude.ai/code/session_011d6TeEAUvrRLiFcmxrRR1a

The tab labelled the app's id as "Key", which is the first thing that confuses
people: it is the App ID, not a secret half of a pair. It then said the pair can
"generate JWT tokens etc" without saying which token, for what, or how to
choose, and it mentioned a Rotate action that is not on this screen.

Now it names App ID and App Secret, says plainly that the secret is the signing
key and should stay on a server you control, and adds a short table mapping the
three credential kinds to the situation each is for: user token when a person is
acting as themselves, app token for work scoped to one app, server token for
tenant provisioning.

Adds a section for connecting an AI assistant, since that is now a first-class
way in and needs none of the above: the hosted MCP OAuth URL with a copy button,
and a pointer to Account > AI Assistants for clients that cannot run a sign-in
flow. Worth stating explicitly that the assistant acts as the signed-in person
and never needs the App Secret, because the natural assumption is the opposite.

The rotate warning moves next to the credentials it applies to.

Claude-Session: https://claude.ai/code/session_011d6TeEAUvrRLiFcmxrRR1a
@phwizard

Copy link
Copy Markdown
Member Author

Thanks, this landed as a port rather than a merge: the target branches carry the internationalised version of this page, and dev is a legacy branch. Same copy, via translation keys in en/fr/es: #126 (2610 dev line) and #127 (2609 release line). Closing this one in favour of those.

@phwizard phwizard closed this Sep 16, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant