CSA sessions provide durable context across tool invocations and maintain parent-child genealogy for recursive agent trees.
A session represents one logical work context. Each session:
- Has a ULID identifier (26-character Crockford Base32)
- Stores tool-specific provider session IDs
- Tracks genealogy (
parent_session_id,depth) - Records access timestamps and context status
- Persists ACP transcripts as JSONL event logs
CSA uses ULID (Universally Unique
Lexicographically Sortable Identifier). Example: 01JH4QWERT1234567890ABCDEF.
Prefix matching: You can use a unique prefix instead of the full ID, similar to git commit hashes:
csa run --sa-mode false --session 01JH4Q "continue work"
csa session result -s 01JKIf a prefix is ambiguous, CSA reports all matching sessions.
Location: ~/.local/state/csa/{project_path}/sessions/{session_id}/
Sessions use flat physical storage with logical tree structure. This simplifies lookup, enables efficient prefix matching, and facilitates garbage collection.
~/.local/state/csa/home/user/my-project/
+-- sessions/
| +-- 01JH4QWERT1234.../
| | +-- state.toml # Session metadata
| | +-- locks/ # Tool-level flock files
| | +-- transcript.jsonl # ACP event transcript
| | +-- output/ # Execution artifacts
| +-- 01JH4QWERT9876.../
| | +-- state.toml
| | +-- ...
+-- usage_stats.toml # P95 memory estimates
Sessions are created automatically by csa run when --session is
not provided:
csa run --sa-mode false --tool codex --description "Auth refactor" "analyze auth module"Resume by ID, prefix, or the most recent session:
csa run --sa-mode false --session 01JH4Q "continue implementation"
csa run --sa-mode false --last "continue the most recent session"csa session list # All sessions
csa session list --tree # Tree view with genealogy
csa session list --tool codex # Filter by tool
csa session list --tool codex,claude-code # Multiple tools
csa session list --branch feat/auth # Filter by git branchcsa session result -s 01JH4Q # Last execution result
csa session result -s 01JH4Q --json # JSON output
csa session logs -s 01JH4Q # View session logs
csa session logs -s 01JH4Q --tail 200 # Last 200 lines
csa session artifacts -s 01JH4Q # List output artifacts
csa session log -s 01JH4Q # Git history for sessionSend the tool-specific compaction command:
| Tool | Compression Command |
|---|---|
| gemini-cli | /compress |
| codex | /compact |
| claude-code | /compact |
| opencode | (not supported) |
csa session compress --session 01JH4QCheck whether a session process is still running:
csa session is-alive --session 01JH4QUses filesystem liveness signals (lock files and heartbeat timestamps).
Write audit checkpoints via git-notes:
csa session checkpoint --session 01JH4Q # Create checkpoint
csa session checkpoints # List all checkpointsCheckpoints persist audit snapshots bound to each session commit, enabling post-hoc audit trail inspection.
csa session delete --session 01JH4QRemove sessions not accessed within N days:
csa session clean --days 30
csa session clean --days 30 --dry-run
csa session clean --days 30 --tool codexCSA records parent-child relationships in each session's state.toml:
[genealogy]
parent_session_id = "01JH4QWERT0000000000000000"
depth = 1When CSA spawns a sub-agent, it sets environment variables for the child:
| Variable | Description |
|---|---|
CSA_SESSION_ID |
Current session ULID |
CSA_DEPTH |
Recursion depth (0 = root) |
CSA_PROJECT_ROOT |
Absolute project path |
CSA_PARENT_SESSION |
Parent session ULID |
CSA_SESSION_DIR |
Absolute session directory path |
View the tree:
csa session list --treestate.toml contains the complete session metadata:
meta_session_id = "01JH4QWERT1234567890ABCDEF"
description = "Auth refactor"
project_path = "/home/user/project"
created_at = 2024-02-06T10:00:00Z
last_accessed = 2024-02-06T14:30:00Z
[genealogy]
parent_session_id = "01JH4QWERT0000000000000000"
depth = 1
[context_status]
is_compacted = false
last_compacted_at = "2024-02-06T12:00:00Z"
[tools.codex]
provider_session_id = "thread_abc123"
last_action_summary = "Reviewed auth flow"
last_exit_code = 0
updated_at = 2024-02-06T14:30:00ZACP sessions emit events that are persisted as JSONL transcripts:
- File:
{session_dir}/transcript.jsonl - Schema: Versioned (
v: 1), with sequentialseqnumbers - Redaction: Sensitive data (API keys, tokens) is automatically redacted
- Resume-safe: Transcript writer detects existing lines and continues from the correct sequence number
- Atomic writes: Buffered with periodic flush, truncates partial trailing lines on recovery
For one-off tasks that don't need persistence:
csa run --sa-mode false --ephemeral "quick question about syntax"Ephemeral sessions skip project file loading, context injection, and are automatically cleaned up after completion.
Active --> Available (after compression) --> Retired (after GC)
- Active: Session is in use or recently used
- Available: Session context has been compressed, still accessible
- Retired: Session marked for garbage collection
| Problem | Solution |
|---|---|
| "No sessions found" | Run csa run first to create a session |
| "Session prefix is ambiguous" | Use a longer prefix or full ULID |
| "Session locked by PID ..." | Another process is using the session; retry later |
- Architecture -- flat storage design
- Commands --
csa sessionreference - ACP Transport -- transcript event sources