Skip to content

feat(chat): persistence, streaming, and save UX#18

Merged
nokternol merged 1 commit into
mainfrom
feat/chat-persistence
Mar 9, 2026
Merged

feat(chat): persistence, streaming, and save UX#18
nokternol merged 1 commit into
mainfrom
feat/chat-persistence

Conversation

@nokternol

Copy link
Copy Markdown
Owner

Summary

  • Gap 1PATCH /api/content/:id now accepts an optional body field to update the markdown body (not just frontmatter), enabling future document-level writes from chat
  • Gap 2 — Save button added to chat header (summarise+patch without committing); park() auto-saves before navigating away so conversations survive every park action
  • Gap 3promote() passes session_summary into the new plan body as a seeded ## Context from idea session section, preserving evolved thinking
  • StreamingPOST /api/chat now streams via SSE (hono/streaming + Anthropic SDK messages.stream()); web side reads with fetch + ReadableStream, appending tokens progressively; empty assistant placeholder shows typing indicator until first token

Test Plan

  • Send a chat message — reply appears progressively token by token, not all at once
  • typing indicator shows while waiting for first token
  • Click Save mid-session — session_summary is written to the branch; Saved ✓ appears
  • Park an item after chatting — session is auto-saved before navigation
  • Return to a parked item — Continuing from last session: shows the saved summary
  • Promote an idea that has a session_summary — new plan body includes ## Context from idea session
  • CI checks pass

🤖 Generated with Claude Code

Gap 1 (body never written): extend PATCH /api/content/:id to accept
optional `body` field that updates the markdown body, not just frontmatter.

Gap 2 (conversation lost on park/navigate): add Save button to chat
header that summarises+patches without committing; auto-save runs inside
park() so the conversation is preserved on every explicit park action.

Gap 3 (promote loses evolved context): pass `session_summary` into the
promote payload as a seeded "## Context from idea session" section in
the new plan body.

Streaming: switch POST /api/chat from a blocking c.json() response to
SSE via Hono's streamSSE(); add LLMRouter.stream() using the Anthropic
SDK's messages.stream() async iterator. Web side reads the stream with
fetch + ReadableStream, appending tokens as they arrive. Empty assistant
placeholder shows "…" typing indicator until the first token lands.

Tests updated to cover SSE format, context event, and graceful closure
on stream error.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@nokternol nokternol merged commit 3f5a056 into main Mar 9, 2026
3 checks passed
@nokternol nokternol deleted the feat/chat-persistence branch March 9, 2026 20:49
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