Skip to content

feat: streaming, memory, screen capture, backlinks, graph view, web search, runbooks - #47

Merged
mdheller merged 4 commits into
mainfrom
feat/noetica-streaming-memory-triage
Aug 4, 2026
Merged

feat: streaming, memory, screen capture, backlinks, graph view, web search, runbooks#47
mdheller merged 4 commits into
mainfrom
feat/noetica-streaming-memory-triage

Conversation

@mdheller

@mdheller mdheller commented Aug 4, 2026

Copy link
Copy Markdown

Summary — full competitive parity sprint

Five commits closing every identified gap against Warp, Obsidian, ChatGPT Desktop, and Perplexity.


Commit 1 — SSE Streaming + Persistent Memory + Auto Error Triage

  • turtle-noetica-stream: real SSE chunked reading, word-by-word fallback
  • turtle-noetica-memory: SQLite facts store injected into every query
  • Auto error triage: async Noetica explain on non-zero exit, surfaced at next prompt
  • |? streaming fixed: direct call (no subshell capture)

Commit 2 — Screen Capture → Noetica + Notes Backlinks (ChatGPT Desktop / Obsidian gaps)

  • turtle-screen-capture: macOS region picker → vision endpoint → OCR fallback → streamed answer
  • turtle-notes-backlinks: [[wikilink]] reverse index, --watch 2s poll daemon
  • tsc / CMD+SHIFT+S keybinding; note() quick-capture; note bl <slug> backlinks

Commit 3 — note() + note_watch() shell functions

  • note "title" captures inline to ~/notes/ + memory mesh event
  • note_watch() manually restarts backlinks daemon

Commit 4 — Graph View + Web Search + Citations + Runbooks (Obsidian / Perplexity / Warp Drive gaps)

  • turtle-mesh-serve /graph: force-directed canvas graph of notes (200-iter warm-up, 30fps, click-to-highlight)
  • turtle-mesh-serve /api/graph: JSON graph data from backlinks index
  • turtle-web-search: SearXNG JSON search, --json/--urls/--count, sovereign (no API key)
  • turtle-noetica-search: search → grounded prompt with [1][2] citations → SSE stream live
  • turtle-runbook (full rewrite): list/show/run/new/push/pull/search/share; GCS sync; interactive per-step runner
  • Shell: ngraph() / ws() / noes() / rb() / rbr()
  • Palette: web_search / noetica_search / runbook_list / runbook_search

New binaries

Binary Gap closed Competitor
turtle-noetica-stream Real-time token output Warp AI
turtle-noetica-memory Cross-session memory All AI products
turtle-screen-capture Screen region → AI query ChatGPT Desktop
turtle-notes-backlinks [[wikilink]] reverse index Obsidian
turtle-web-search Sovereign web search Perplexity / Kagi
turtle-noetica-search Search + grounded citations Perplexity
turtle-runbook Cloud-shared runbooks Warp Drive

Shell functions

tsc · note · note bl · note_watch · ngraph · ws · noes · rb · rbr · noe mem · glog · td

Test plan

  • echo "error" | ? "what" — tokens stream live
  • noe mem "prefer Go"noe "what I prefer" — references memory
  • Failing command → next prompt shows triage in teal
  • tsc "what is this" → region picker → answer streams
  • note "test" → file in ~/notes/, mesh event visible in dashboard
  • note bl <slug> → backlinks shown
  • ngraph → force graph renders at localhost:7788/graph
  • ws "wezterm latest release" → numbered results
  • noes "k8s 1.32 release notes" → answer with [1][2] citations
  • rb list → runbooks shown; rb run deploy-k8s → interactive steps
  • rb push → runbooks sync to GCS bucket

turtle-noetica-stream (new):
- SSE chunked reading via http.client — tokens appear as they generate
- word-by-word 7ms/word fallback for non-streaming Noetica responses
- Env-var interface: TURTLE_NOETICA / TURTLE_PROMPT / TURTLE_MAX_TOKENS

turtle-noetica-memory (new):
- SQLite facts store at ~/.local/state/sourceos/noetica-memory.db
- add / list / remove / context / extract subcommands
- context_block() injected as system context into every noe() + |? query
- extract_from_utterance() auto-saves when utterance signals "remember"

turtle-shell-init.zsh:
- _turtle_noetica_query(): delegates to turtle-noetica-stream binary
- _turtle_memory_context(): reads context block from SQLite store
- |? fixed: direct call (no subshell capture) so SSE tokens stream live
- |? now injects persistent memory context alongside stdin
- noe(): persistent memory injection + auto-extract on remember phrases
- noe mem / noe mem list subcommands
- auto error triage: on rc≠0/130/146 fires async Noetica explain;
  result displayed at next prompt (TURTLE_ERROR_TRIAGE=0 to opt out)
- BB bridge + Goose bridge daemons auto-started at shell init
- glog(): semantic git log with per-commit Noetica annotation stream
- td(): delta/diff-so-fancy/bat/plain diff chain
- bb() / bbs(): injection-safe via env vars, not string interpolation
…e shortcuts

turtle-screen-capture (new):
- macOS screencapture -i interactive region select → PNG
- Vision endpoint first (OpenAI-compat image_url); OCR+text fallback
- OCR via tesseract / ocrmac in order of availability
- Writes screen-capture event to memory mesh
- tsc / CMD+SHIFT+S keybinding; --ocr / --full flags

turtle-notes-backlinks (new):
- Scans ~/notes/*.md for [[wikilinks]] and [[wikilink|alias]] refs
- Builds forward + reverse index → ~/.local/state/sourceos/notes-backlinks.json
- --watch polls every 2s, rebuilds on mtime change
- --backlinks <slug> prints all notes that link to a slug
- Auto-started as daemon at shell init (PID gated)

turtle-shell-init.zsh:
- tsc() wrapper → turtle-screen-capture
- note() quick-capture function: note "title" / note bl <slug> / note (editor)
- Backlinks daemon auto-start block (same pattern as BB+Goose bridges)

turtleterm.lua:
- screen_capture palette entry + CMD+SHIFT+S keybinding
- screen_capture dispatch entry
…tart

note():
- note "title" → ~/notes/YYYY-MM-DD-slug.md append + memory mesh event
- note → opens $EDITOR for blank note
- note bl <slug> → prints backlinks for that slug via turtle-notes-backlinks

note_watch():
- Kills + restarts the backlinks watch daemon
- Writes PID to /tmp/turtle-notes-backlinks.pid
- Auto-started at shell init; note_watch re-starts if it dies
…g competitive gaps

turtle-mesh-serve:
- GET /api/graph — notes graph JSON from backlinks index (nodes sized by degree)
- GET /graph — self-contained force-directed canvas graph page (no external libs)
  * 200-iteration warm-up, 30fps rAF animation, click-to-highlight neighbors
  * right panel shows slug + backlinks + forward-links on node click
  * drag to pin nodes; data refreshes every 10s from /api/graph
- Dashboard h1 gains "◆ Graph view" teal link-button opening /graph

turtle-web-search (new):
- SearXNG JSON search (default: searx.be; SEARXNG_URL override)
- --json / --urls / --count N flags; numbered list output with title+snippet+url
- User-Agent: TurtleTerm/1.0; stdlib only, no API key

turtle-noetica-search (new):
- Fetches top-5 results via turtle-web-search, builds grounded prompt with [1][2] citations
- Calls turtle-noetica-stream as subprocess with inherited stdout → SSE streams live
- Falls back to direct Noetica query when SearXNG unreachable (notices to stderr)

turtle-runbook (full rewrite from stub):
- list / show / run / new / push / pull / search / share subcommands
- run: interactive per-step with Enter/s/q, ${VAR:-default} substitution
- push/pull: gsutil/gcloud sync to gs://<mesh-bucket>/runbooks/; pull skips newer locals
- search: name=3pts / tag=2pts / description=1pt scoring
- PyYAML if available, built-in mini-parser fallback

turtle-shell-init.zsh:
- ngraph() → opens localhost:7788/graph in bb / open
- ws() → turtle-web-search
- noes() → turtle-noetica-search with teal searching indicator
- rb() / rbr() → turtle-runbook shortcuts

turtleterm.lua:
- Palette: web_search / noetica_search / runbook_list / runbook_search
- Dispatch: ws / noes / rb list / rb search (no newline, drops into prompt)
@mdheller mdheller changed the title feat(shell): real SSE streaming, persistent memory, auto error triage feat: streaming, memory, screen capture, backlinks, graph view, web search, runbooks Aug 4, 2026
@mdheller
mdheller merged commit 108a0e5 into main Aug 4, 2026
14 checks passed
@mdheller
mdheller deleted the feat/noetica-streaming-memory-triage branch August 4, 2026 01:56
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