Skip to content

feat(session): add session list + export commands for AI SRE#30

Merged
ysyneu merged 2 commits into
mainfrom
feat/session-commands
Jun 2, 2026
Merged

feat(session): add session list + export commands for AI SRE#30
ysyneu merged 2 commits into
mainfrom
feat/session-commands

Conversation

@ysyneu
Copy link
Copy Markdown
Contributor

@ysyneu ysyneu commented Jun 2, 2026

What

Adds the CLI surface for the AI SRE session APIs — the commands the /insight skill shells out to:

  • flashduty session list — curated command over Sessions.List. Flags: --app (default ai-sre), --limit (default 200), --scope, --status, --team-id (sets team_ids), and a client-side --since window (the API has no time filter, so rows are filtered by updated_at after fetching). Output --format jsonl (default — one SessionItem per line for jq) / json (full envelope) / toon.
  • flashduty session export <session_id> — streams the session's full NDJSON transcript straight to stdout via the SDK's hand-written streaming method, line-by-line so a large transcript never buffers in memory. Redirect to a file: flashduty session export <id> > session.ndjson. --include-subagents inlines each child session's stream.

Streaming op handling (generator + coverage)

session/export's 200 response is application/x-ndjson, which the generated typed-response command template cannot model (the SDK exposes it as (io.ReadCloser, *Response, error), not the usual (out, *Response, error)). So:

  • cligen now skips streaming ops (200 body has no application/json), mirroring go-flashduty's own generator. Generated tree gets safari session-get / safari session-list; export is excluded.
  • A curated safari session-export leaf keeps the operation reachable at its path-is-king name, alongside the friendly session export.
  • The coverage tests (TestEveryOperationHasPathCommand, TestGeneratorTargetsFullSpec) account for streaming ops being curated-only: still reachable at their path-name, but not required in the generated manifest.

Dependency

Pins go-flashduty to the commit that adds the Sessions service (Sessions.List typed + Sessions.Export streaming).

Verification

  • go build ./... clean; go test ./... green (incl. the 6 new session tests + the two coverage invariants: path-is-king: all 251 operations reachable, generator targets 250/250 non-streaming spec operations (1 streaming, curated)).
  • golangci-lint run0 issues; gofmt/gci clean.
  • Live against the local pgy→safari gateway: session list --app ai-sre --format jsonl returned real ai-sre sessions (total 988) as one JSON object per line; session export <id> streamed valid NDJSON with line 1 = session_meta (jq-parseable), including tool_call/final_answer events (51-line / 53KB transcript, every line valid JSON).

ysyneu added 2 commits June 2, 2026 12:43
Add `flashduty session list` and `flashduty session export <id>`, the CLI
surface for the AI SRE session APIs (consumed by the /insight skill).

- session list: curated command over Sessions.List. --app (default ai-sre),
  --limit (default 200), --scope, --status, --team-id, and a client-side
  --since window (the API has no time filter, so rows are filtered by
  updated_at after fetching). Output --format jsonl (default, one SessionItem
  per line for jq) / json / toon.
- session export: streams the NDJSON transcript straight to stdout via the
  SDK's hand-written streaming method, line-by-line, so a large transcript
  never buffers in memory — redirect to a file.

session/export is a streaming op (200 is application/x-ndjson), which the
generated typed-response template cannot model. cligen now skips streaming
ops (mirroring go-flashduty's own generator) and the curated `safari
session-export` leaf keeps it reachable at its path-name alongside the
generated safari session-get / session-list. The coverage tests account for
streaming ops being curated-only.

Pins go-flashduty to the commit that adds the Sessions service.
The /safari/session/list handler binds limit with "lte=100": a single
request with limit>100 is a hard 400 bind failure, not a clamp. Honor
--limit above 100 by paginating server-side (fetchSessionsPaged) — each
page requests min(remaining, 100) and advances p until the limit is met
or the server is exhausted (short page / accumulated >= total). Adds two
regression guards: paginate-beyond-100 and stop-when-exhausted.

Also bumps the go-flashduty pin to the squash-merged main commit
(7583ebae, go-flashduty#8) so the dependency is reachable from main
rather than the soon-stale PR-branch pseudo-version.
@ysyneu ysyneu merged commit 8c0898c into main Jun 2, 2026
12 checks passed
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