Files
TJWaterAgent/.github/copilot-instructions.md
2026-05-28 18:22:39 +08:00

125 lines
4.1 KiB
Markdown

# Copilot Instructions for TJWaterAgent
## Overview
- TJWaterAgent is a Bun + TypeScript backend service.
- Main entrypoint: `src/server.ts`
- Chat API base path: `/api/v1/agent/chat`
- Persistent storage is **PostgreSQL-first**. Historical file storage only remains for one-time migration and external result payload files.
## Core identity model
- `sessionId` = durable chat thread identifier exposed to clients and used for persistence.
- `runtimeSessionId` = temporary opencode runtime execution identifier for a single active request.
- Do **not** reintroduce `conversationId` / `clientSessionId` naming for the durable thread id. Use `sessionId`.
## Persistence design
Canonical PostgreSQL tables:
- `conversations`
- `conversation_states`
- `conversation_turns`
- `runtime_sessions`
- `learning_states`
- `result_refs`
- `memories`
### conversations
Stores durable thread metadata:
- `session_id`
- actor / owner / project fields
- `parent_session_id`
- `title`
- `status`
- streaming lifecycle fields:
- `is_streaming`
- `active_runtime_session_id`
- `streaming_started_at`
`is_streaming` is persisted so the frontend can recover streaming state after refresh. Stream cleanup must be guarded by `active_runtime_session_id` so an old stream cannot clear a newer one.
### conversation_states
Stores frontend-facing session UI state:
- `messages`
- `branch_groups`
- `is_title_manually_edited`
### conversation_turns
Stores transcript turns as one row per turn:
- keyed by `turn_id`
- linked by `session_id`
- ordered by deterministic `turn_index`
Do not fall back to legacy transcript files in runtime code.
### runtime_sessions
Stores runtime binding context for internal tools and learning review/gate flows:
- `runtime_session_id`
- `session_id`
- actor / project / trace fields
- `allow_learning_write`
- `learning_mode`
- `released_at`
This replaces the old alias-based `tool_session_contexts` model.
### result_refs
`result_refs` is **metadata-only in PostgreSQL**:
- metadata lives in PG
- payload body lives outside PG via `payload_path` or future `object_key`
Most payloads are large, so do not inline them into PostgreSQL.
### memories
Durable memory is stored in PG, not markdown files.
## Runtime flow
1. Client sends/loads a `session_id`.
2. `ChatSessionBridge` binds that durable `sessionId` to a fresh `runtimeSessionId`.
3. Internal tools call back into the server using `runtimeSessionId`.
4. Transcript, memory, learning state, and result refs persist against `sessionId`.
5. Stream start sets `conversations.is_streaming = true`; stream completion clears it only if the runtime id still matches.
## Important files
- `src/server.ts` - bootstrap, internal tool endpoints, app wiring
- `src/chat/sessionBridge.ts` - `sessionId` vs `runtimeSessionId` binding
- `src/db/index.ts` - PostgreSQL bootstrap and schema migration/cleanup
- `src/conversations/store.ts` - durable session metadata + streaming state
- `src/conversations/stateStore.ts` - UI state persistence
- `src/history/store.ts` - transcript persistence
- `src/session/runtimeSessionStore.ts` - runtime session persistence
- `src/results/store.ts` - metadata-only result refs + external payload files
- `src/results/resolver.ts` - result ref normalization and retrieval
- `src/learning/orchestrator.ts` / `src/learning/stateStore.ts` - learning review pipeline
- `src/memory/store.ts` - persistent memory store
- `scripts/migrate-file-storage-to-postgres.ts` - one-time migration from legacy file storage
## Compatibility rules
- Runtime code should target the canonical schema only.
- Legacy column/table handling belongs only in `src/db/index.ts` bootstrap migration or `scripts/migrate-file-storage-to-postgres.ts`.
- Do not add back file-based runtime persistence or compatibility reads unless a migration explicitly requires it.
## Validation
Useful commands:
```bash
bun run check
PGHOST=... PGPORT=... PGUSER=... PGPASSWORD=... PGDATABASE=agent PGSSLMODE=disable bun test tests/conversations/store.test.ts tests/history/store.test.ts tests/session/runtimeSessionStore.test.ts tests/results/store.test.ts tests/routes/chatSession.test.ts
```