Why a signature is required
Anyone can put anything in a POST body. If an unsigned user id were enough to bind somebody to stored history, a stranger could read another customer’s conversations by guessing their user id. So the claim is signed with a secret only your server and we hold, and we recompute it before acting on it. A claim that does not verify is dropped — never downgraded to “probably them”.The recipe
Your identity secret is on the agent’s Channels page. Keep it on your server; it must never reach the browser.ThinnestAgents.identify({…}) after
sign-in instead.
Which fields do what
Only the id is signed as an identity. Name and email are written to the
record but never used to find one, so changing a display name does not mean
re-signing anything.
Per channel, not per workspace
The secret belongs to a channel. If you run a brochure site and a logged-in app, install two widgets with two secrets — a key lifted from the brochure site must not be able to assert identities against the app.Common mistakes
Signing something other than the id
Signing something other than the id
The digest must be of the user id alone. A digest of the secret itself is
a constant and verifies nothing.
Computing the HMAC in the browser
Computing the HMAC in the browser
That publishes the secret to every visitor, and the secret is the only thing
stopping anyone forging any customer’s identity.
Sending an id with no signature
Sending an id with no signature
It is treated as unverified and bound to nothing. The widget works; the
customer stays anonymous, and it looks exactly like a working feature.