Sessions
A session is a short-lived token that lets one of your users into one document in the embedded editor, or into presence settings. Your server starts it with your secret key and hands the token to your page; the page passes it to Proof and never sees your key. Tokens last 15 minutes, and the embed asks your getToken function for a new one before the old one runs out, so an open editor keeps working for as long as the person is allowed in. See Embed the editor.
A session token only opens the editor or presence settings. It can’t call the REST API.
The session object
Section titled “The session object”| Attribute | Type | Description |
|---|---|---|
token |
string | The token to pass to the page, starting est_. |
user |
string | The user’s Proof id. |
document |
string or null | The document it opens, or null for a presence session. |
purpose |
string | editor or presence. |
role |
string or null | The role the user has in the document for this session: owner, editor, suggester or viewer. null for a presence session. |
via |
string or null | member when the role comes from membership, link when it comes from the document’s link access. null for a presence session. |
expires_at |
timestamp | When the token stops being accepted, 15 minutes after it was started. |
{ "token": "est_q7Lr2VkX9pN4sT8wY3mB6cZ1", "user": "usr_5Kq2Lm8R", "document": "doc_8Hq2Lm4R", "purpose": "editor", "role": "owner", "via": "member", "expires_at": "2026-10-30T18:35:00Z"}Create a session
Section titled “Create a session”POST /v1/sessions
Starts a session for the editor, or for presence settings when you pass purpose: "presence".
| Parameter | Type | Description |
|---|---|---|
user |
string, required | The user’s Proof id. The user must exist. |
document |
string | The document to open. Required unless purpose is presence. |
via |
string | link to let in someone who isn’t a member, with the document’s link access as their role. Leave it out for members. |
purpose |
string | editor (the default) or presence. |
group |
string | Up to 200 characters of yours that the session belongs to, such as the id of the person’s own sign-in session with you, so you can end them together. |
For the editor
Section titled “For the editor”Proof works out the user’s role when it starts the session: their member role, or with via: "link", the document’s link_access. A member who comes by link keeps whichever role is higher. The role is checked again on every edit, so lowering it or removing the member takes effect in an open editor at once, whatever the token says.
curl https://api.proof.exalto.ai/v1/sessions \ -H "Authorization: Bearer $PROOF_SECRET_KEY" \ -H "Content-Type: application/json" \ -d '{"user": "usr_5Kq2Lm8R", "document": "doc_8Hq2Lm4R"}'const session = await proof.sessions.create({ user: "usr_5Kq2Lm8R", document: "doc_8Hq2Lm4R",});{ "token": "est_q7Lr2VkX9pN4sT8wY3mB6cZ1", "user": "usr_5Kq2Lm8R", "document": "doc_8Hq2Lm4R", "purpose": "editor", "role": "owner", "via": "member", "expires_at": "2026-10-30T18:35:00Z"}For someone who followed a shared link:
curl https://api.proof.exalto.ai/v1/sessions \ -H "Authorization: Bearer $PROOF_SECRET_KEY" \ -H "Content-Type: application/json" \ -d '{"user": "usr_9Tb3Wc1X", "document": "doc_8Hq2Lm4R", "via": "link"}'const session = await proof.sessions.create({ user: "usr_9Tb3Wc1X", document: "doc_8Hq2Lm4R", via: "link",});{ "token": "est_d2Hs9QmW4kR7xV1nJ6pL8tF3", "user": "usr_9Tb3Wc1X", "document": "doc_8Hq2Lm4R", "purpose": "editor", "role": "suggester", "via": "link", "expires_at": "2026-10-30T18:35:00Z"}A document in the trash still opens, only to read: for its owners when it’s in the trash for everyone, and for a member who put it in their own. The session’s role is then viewer.
People who come by link aren’t added as members. Their writing is credited to them like anyone else’s, and they appear in the document’s mention list while they have it open.
For presence settings
Section titled “For presence settings”A presence session opens the window where a user adds security keys and chooses how often to check in. It isn’t tied to a document. Pass its token to mountPresenceSettings or openPresenceSettings in the embed API. See Set up check-ins.
curl https://api.proof.exalto.ai/v1/sessions \ -H "Authorization: Bearer $PROOF_SECRET_KEY" \ -H "Content-Type: application/json" \ -d '{"user": "usr_5Kq2Lm8R", "purpose": "presence"}'const session = await proof.sessions.create({ user: "usr_5Kq2Lm8R", purpose: "presence",});{ "token": "est_m5Tc8Wq1Zr6Kv3Np9Ys2Bx7H", "user": "usr_5Kq2Lm8R", "document": null, "purpose": "presence", "role": null, "via": null, "expires_at": "2026-10-30T18:35:00Z"}Errors
Section titled “Errors”| Error | When |
|---|---|
400 missing_parameter on document |
purpose is editor and there’s no document. |
400 invalid_parameter on group |
Empty, or longer than 200 characters. |
403 no_access |
The user isn’t a member, and either you didn’t pass via: "link" or the document’s link access is restricted. |
404 user_not_found |
The user doesn’t exist. |
404 document_not_found |
The document doesn’t exist. |
409 document_trashed |
The document is in its owners’ trash, and the user isn’t one of its owners. |
End a user’s sessions
Section titled “End a user’s sessions”DELETE /v1/users/{user_id}/sessions
Ends a user’s sessions at once: all of them, or with group, only those started in that group. Call it when someone signs out of your product, or is signed out everywhere. Their open editors lose their connection within moments and ask your page for a new token, which your server refuses once they’re signed out.
| Parameter | Type | Description |
|---|---|---|
user_id |
string, path, required | The user’s Proof id. |
group |
string, query | Only the sessions started with this group. |
curl "https://api.proof.exalto.ai/v1/users/usr_5Kq2Lm8R/sessions?group=sess_42" \ -X DELETE \ -H "Authorization: Bearer $PROOF_SECRET_KEY"await proof.users.endSessions("usr_5Kq2Lm8R", { group: "sess_42" });{ "deleted": 2 }