Add cursor-based pagination to listSessions#295
Merged
Conversation
Introduce optional cursor + limit pagination for the root `listSessions` command so clients with a large session catalogue can load it incrementally instead of receiving every `SessionSummary` in one response. Modeled on MCP's opaque-cursor pagination, plus an optional `limit` the server SHOULD respect (but MAY cap). The pagination inputs/outputs are factored into reusable `PaginatedParams` (`limit` + `cursor`) and `PaginatedResult` (`nextCursor`) base interfaces in `types/common/commands.ts`, carrying the canonical pagination contract in one place for future paginated commands. `ListSessionsParams` now extends `PaginatedParams` and `ListSessionsResult` extends `PaginatedResult`. Fully additive: a client that omits `limit`/`cursor` and ignores `nextCursor` sees today's behaviour, and a server that does not paginate returns everything in one page. Regenerates the schema and all five client mirrors, updates the root channel spec doc, and adds CHANGELOG entries to the spec plus every client. Closes #275 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
roblourens
previously approved these changes
Jul 1, 2026
| export interface ListSessionsParams extends BaseParams, PaginatedParams { | ||
| channel: 'ahp-root://'; | ||
| /** Optional filter criteria */ | ||
| filter?: object; |
Member
There was a problem hiding this comment.
How is filter interpreted? Should we add a sort criteria?
Member
Author
There was a problem hiding this comment.
Yea, idk, I forgot this was a thing. I'll just remove it for now
The `filter` field was an untyped `object` placeholder with no defined semantics. Drop it rather than ship an unspecified field; it will be reintroduced with a concrete shape once session filtering/sorting is specified. Updates the two host-runtime call sites (Rust, TypeScript) that named the field, regenerates all clients + schema, and records the removal in every CHANGELOG. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
dmitrivMS
approved these changes
Jul 1, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds optional cursor + limit pagination to the root
listSessionscommand so a client with a large session catalogue can load it incrementally instead of receiving everySessionSummaryin a single response. Modeled on MCP's opaque-cursor pagination, plus an optionallimitthe server SHOULD respect (but MAY cap).Fully additive: a caller that omits the new fields, and a host that does not paginate, behave exactly as today.
Closes #275.
Shape
The pagination inputs/outputs are factored into reusable base interfaces in
types/common/commands.ts, so future paginated commands can just extend them and the pagination contract lives in one place:fetchTurnsexposesbefore/hasMorewithout dictating storage. Clients MUST NOT parse, modify, or persist it; an unrecognised cursor SHOULD be rejected withInvalidParams.root/session*notifications keep an already-fetched page live exactly as today; pagination governs only the initial and backfill fetches.Changes
types/— newPaginatedParams/PaginatedResult;ListSessionsParams/ListSessionsResultextend them; both exported fromtypes/index.ts.knownSpecialexhaustiveness lists in the rust/go/kotlin/swift generators (likeBaseParams, they're flattened viaextends, not emitted standalone).limit/cursor/nextCursorintoListSessions*.docs/specification/root-channel.md.types/**change ripples to all clients).Open questions from the issue (deliberately out of scope)
filterstays an untypedobjectas today. Pagination is additive so a typed filter/sort can land later without reworking this.approximateTotal: omitted for v1.Validation
npm run test→ 275 pass, 100% reducer branch coverage, changelog + release-metadata gates green;npm run lintclean.npm run generateproduces no generator warnings.cargo build,go build ./..., and the TypeScript clienttsc --noEmitall pass.