Repository navigation
docs: document session sharing for 1.x (#562) - #657
Conversation
Signed-off-by: Moritz Schmitz von Hülst <mschmitzvonhuelst@gmail.com>
|
The deploy check failed in the Preview workflow: |
Rachael-Graham
left a comment
There was a problem hiding this comment.
Thank you for this. The capability framing and the insecure-mode warning are exactly the register the issue asked for, and linking the cap rather than restating it is right. Since you opened this, kagent-dev/kagent#3453 landed for rc1 and changed the share model, so several claims below no longer match the code; please re-verify the page against v1.0.0-rc1.
| Each share carries one of two permissions: | ||
|
|
||
| | Permission | Allows | | ||
| | ---------- | ------ | | ||
| | `READ_ONLY` | A2A `get`, `list`, and `subscribe`. | | ||
| | `READ_WRITE` | The `READ_ONLY` operations, plus `send` and `cancel`. | |
There was a problem hiding this comment.
Blocking. At rc1 READ_WRITE and the permission field are gone, and every share is read-only (SessionShare in proto/kagent/api/v1/sessions.proto, CreateShare in go/core/internal/service/session/service.go). Drop the table and state that a share grants A2A get, list, and subscribe only.
|
|
||
| ## A share is a capability, not a grant to a user | ||
|
|
||
| The token resolves to the conversation's owner, and the backend answers as though the owner had asked, keeping the caller's own identity only for the record. Anyone holding the token acts with the owner's access to that one Session. The share does not name a person, and it does not create a second principal. |
There was a problem hiding this comment.
Blocking. At rc1 the recipient's own identity is checked against policy, and the owner supplies only the storage lookup (authorize in go/core/internal/service/session/service.go: "Checking the owner would lend their grants to visitors"). "Acts with the owner's access" is no longer true, so please rewrite this section to say the holder needs their own read permission on the Session.
|
|
||
| A caller spends the share by presenting the token in the `X-Share-Token` header. The controller resolves the token to the owner and scopes the call to that Session. | ||
|
|
||
| The owner revokes a share with `RevokeSessionShare`, keyed by the `SessionShare.id`. Revoking withdraws the holder's access immediately; the share record remains so the owner can confirm it is gone from `ListSessionShares`. Deleting the Session removes its shares with it. |
There was a problem hiding this comment.
Blocking. RevokeSessionShare runs DELETE FROM session_share (go/core/internal/database/shares.go), so the record does not remain and does not appear in ListSessionShares afterward. Please say that revoking deletes the share.
|
|
||
| When you create a share you can set `CreateSessionShareRequest.ttl` to a positive lifetime, counted from creation. The returned `SessionShare.expiresAt` records when the token stops granting access; once that time passes, the token lookup returns not found, and the owner still sees the expired share in `ListSessionShares` and can revoke it. | ||
|
|
||
| Omit `ttl` and `expiresAt` stays unset. The share then grants access until it is revoked or the Session is deleted. |
There was a problem hiding this comment.
Should fix. This line says an omitted ttl leaves expiresAt unset, while line 38 says a positive cap supplies the lifetime for an omitted ttl. Line 38 matches the code, so this line needs "when no cap is set".
| | `READ_WRITE` | The `READ_ONLY` operations, plus `send` and `cancel`. | | ||
|
|
||
| > [!WARNING] | ||
| > **`READ_ONLY` is not a security boundary in a default install.** `config.server.auth.mode` defaults to `insecure`, where a caller supplies its own identity in `X-User-Id`. A caller can claim the owner's identity and reach the Session without any share token at all. Treat `READ_ONLY` as a scope on what the share link can do, not as access control: the boundary holds only under `trusted-proxy`, with a credential-validating proxy in front of the controller. For the modes themselves, see [Controller authentication modes]({{< link path="about/substrate-runtime/identity#controller-authentication-modes" >}}). |
There was a problem hiding this comment.
Should fix. This warning repeats the owner's-access claim from line 12. Re-check this sentence once that is settled, because the insecure-mode impersonation point may still hold on its own.
| @@ -0,0 +1,51 @@ | |||
| --- | |||
There was a problem hiding this comment.
Should fix. The issue scoped this as a UI procedure, and the page has no steps. Either add the UI steps or retitle the page as a concept page ("Session sharing"), because "Share a session" promises a task.
| author: kagent.dev | ||
| --- | ||
|
|
||
| A share lets the owner of a {{< gloss "Session" >}}Session{{< /gloss >}} give another account access to that one conversation. Creating a share produces a token; a caller presenting that token reaches the shared Session without becoming its creator. kagent exposes three RPCs for this: `CreateSessionShare`, `ListSessionShares`, and `RevokeSessionShare`. There is no `kagent` CLI verb for sharing — it is a gRPC and UI procedure, not something you script from the command line. |
There was a problem hiding this comment.
Nit. The em dash joins two clauses. Split them into two sentences.
Signed-off-by: Moritz Schmitz von Hülst <mschmitzvonhuelst@gmail.com>
|
Re-verified the page against v1.0.0-rc1 (kagent-dev/kagent) and rewrote it per the review:
|
Rachael-Graham
left a comment
There was a problem hiding this comment.
TY very much! Merging.
Closes #562
Session sharing had no page in the 1.x docs, while the
ttlfield is referenced from "Controller identity" and "Operational considerations" on the assumption that one exists. This adds1.x/agents/share-a-session.md(weight 60, after Human in the loop) covering the surface from the issue:READ_ONLYpresented as a scope, with theinsecure-mode caveat that it is not a security boundary in a default installttl,expiresAt, and theconfig.sessions.shareMaxTtlcap, including rejection of attlabove the capX-Share-Token, and revoking viaRevokeSessionShareThe cap is linked to the existing pages rather than restated.
How to Test