Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
41 commits
Select commit Hold shift + click to select a range
57c33c9
docs: lean threads design, plus the orchestrator ideas
lszl84 Oct 19, 2026
2d525e8
docs: no line budgets; simplest clean solution instead
lszl84 Oct 19, 2026
b85f31e
feat(tools): resolve paths and run bash in the caller's folder
lszl84 Oct 19, 2026
87c4e49
feat: threads — several conversations per folder, running at once
lszl84 Oct 19, 2026
204b120
test: threads smoke script; grit.py thread commands
lszl84 Oct 19, 2026
5ab7dff
fix(threads): keep background failures until viewed; open a folder's …
lszl84 Oct 19, 2026
20a2e89
test(threads): smoke checks for background failures and opening a folder
lszl84 Oct 19, 2026
591b952
Merge threads step 1: several conversations per folder, running at once
lszl84 Oct 19, 2026
c47f5bf
docs(threads): list the remaining parallelism steps
lszl84 Oct 19, 2026
9220811
fix(tree): "Refresh" no longer saves the open file
lszl84 Oct 19, 2026
f5a67c8
fix(bash): a timed-out command loses its whole process group; timeout…
lszl84 Oct 19, 2026
b09303d
fix(run-config): serialize read-modify-write; write atomically
lszl84 Oct 19, 2026
3753b58
wip(threads): subagents — task tool child threads, Claude Code subage…
lszl84 Oct 19, 2026
f3fc281
fix(sse): parse CRLF streams, an unterminated last event and `data:` …
lszl84 Oct 19, 2026
3b9e9d3
wip(threads): subagent smoke test; keep background-cancel notice on c…
lszl84 Oct 19, 2026
65b187b
Merge threads step 3: bash group kill, run-config lock, SSE parsing, …
lszl84 Oct 19, 2026
4707f50
feat(threads): subagents — task tool and Claude Code subagent threads…
lszl84 Oct 19, 2026
a14dd74
Merge threads step 2: subagents (task tool, Claude Code subagent thre…
lszl84 Oct 19, 2026
c01e914
feat(threads): project brief in every thread's system prompt
lszl84 Oct 19, 2026
a595ef3
Merge threads step 4: project brief
lszl84 Oct 19, 2026
b0d62a0
test(smoke): fake free model for the threads and subagents smoke tests
lszl84 Oct 19, 2026
0fd835f
Merge deterministic smoke tests: local fake model server
lszl84 Oct 19, 2026
08e1865
feat(threads): project-scoped history search
lszl84 Oct 19, 2026
af2be56
test: the control client connects only to the port it is given
lszl84 Oct 19, 2026
69d5657
feat(threads): thread pane (step 5)
lszl84 Oct 19, 2026
61e893f
Merge threads step 7: thread-aware history search
lszl84 Oct 19, 2026
70cec69
Merge threads step 5: optional thread pane
lszl84 Oct 19, 2026
4e5a5cf
test(thread_pane): exact-port control client
lszl84 Oct 19, 2026
5e83235
wip(threads): worktree threads (step 6)
lszl84 Oct 19, 2026
663e166
feat(threads): worktree threads (step 6)
lszl84 Oct 19, 2026
30541db
Merge threads step 6: worktree threads (review, merge, discard)
lszl84 Oct 19, 2026
5c1077a
threads: switch threads in the left pane, keep the dropdown per folder
lszl84 Oct 25, 2026
c4bde5c
threads: left pane icon toolbar, automatic project brief, worktrees o…
lszl84 Oct 25, 2026
eabd6b3
threads: write the project brief with the selected model's provider
lszl84 Oct 25, 2026
ff29d39
docs: point the worktree note at the rewritten merge
lszl84 Oct 25, 2026
bb8114d
threads: run turns in one folder at the same time
lszl84 Oct 25, 2026
348ae38
threads: tell agents how to share a checkout, and when to use a worktree
lszl84 Oct 25, 2026
8e19a4d
threads: keep the shared-checkout note out of the chat, send it only …
lszl84 Oct 25, 2026
ea75259
threads: a draft per thread, a Play run per folder
lszl84 Oct 25, 2026
373b4a4
threads: the session dropdown's mark means something you haven't seen
lszl84 Oct 25, 2026
cd8d942
docs: README for threads, subagents and the project brief
lszl84 Oct 25, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -252,8 +252,10 @@ set(SRCS
src/shell_env.cpp
src/preferences.cpp
src/settings_dialog.cpp
src/project_brief.cpp
src/streaming_web_request.cpp
src/run_config_store.cpp
src/thread_list.cpp
)

# macOS-only native styling (Objective-C++); see src/mac_style.h.
Expand Down
9 changes: 6 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,11 @@ Get both from the [latest release](https://github.com/lszl84/gritcode/releases/l
- **An agent with real tools:** bash, read, write and edit files, list, grep, web search and URL fetch, with collapsible tool-call cards and thinking blocks
- **▶ Play:** the agent saves your project's run command, then one click builds and runs it with no AI round-trip. Output lands in the chat.
- **Built-in editor:** a file tree plus tree-sitter syntax highlighting, smart indentation and save
- **Sessions:** per-project history in SQLite. Export a session to a `.gritsession` file (images included) and replay its prompts in a new project.
- **Cross-project memory:** full-text search over past sessions, available to the agent through `grit_history_search` and `grit_history_fetch`
- **Threads:** several conversations per folder, all running at once, so an unrelated task starts with a clean context. Switch between them in the left pane; a mark tells you when one finished or failed while you were elsewhere.
- **Subagents:** DeepSeek and Kilo models can hand work to subagents running in the background, and Claude Code's own subagents show up too. Each one is a thread under its parent that you can open and follow live.
- **Project brief:** the first new thread in a folder writes a short brief of the project, and every new thread starts with it
- **Sessions:** history in SQLite. Export a thread to a `.gritsession` file (images included) and replay its prompts in a new project.
- **Cross-project memory:** full-text search over past conversations, available to the agent through `grit_history_search` and `grit_history_fetch`, across all projects or just the folder's other threads
- **Cheap long sessions:** compaction only near the context limit, a token-budgeted tail and chained summaries
- **Vision:** drag screenshots into the message box
- **Streaming markdown:** headings, tables and code blocks render live
Expand Down Expand Up @@ -68,7 +71,7 @@ Click the ⚙ gear button in the bottom toolbar to open Settings, then paste you

The Model dropdown also offers **Claude (Opus 5.5)** and **Claude (Sonnet 5)**. These run your installed [Claude Code](https://code.claude.com/docs/en/setup) (the `claude` command) headlessly, so you need Claude Code installed and signed in: run `claude` once in a terminal and log in. Gritcode never sees your Claude credentials; usage goes to your own Claude account or API key.

With Claude selected, Claude Code runs its own agent loop and tools (Bash, Read, Edit, …), and Gritcode shows them in the chat. As with Gritcode's own agent, tools run without confirmation prompts. The ▶ Play button works the same with Claude: Gritcode gives Claude its `run_project` tool so it can set up the run command. Each Gritcode session resumes the same Claude Code session, and when you switch models mid-session the other model gets a transcript of what happened. Claude's effort level is in Settings.
With Claude selected, Claude Code runs its own agent loop and tools (Bash, Read, Edit, …), and Gritcode shows them in the chat. As with Gritcode's own agent, tools run without confirmation prompts. The ▶ Play button works the same with Claude: Gritcode gives Claude its `run_project` tool so it can set up the run command. Each Gritcode thread resumes its own Claude Code session, and when you switch models mid-thread the other model gets a transcript of what happened. Claude Code's subagents appear as threads under the one that started them. The project brief is written with Sonnet through the same Claude Code install, so nothing goes to another provider. Claude's effort level is in Settings.

## Support Gritcode

Expand Down
4 changes: 4 additions & 0 deletions assets/icons/session.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
8 changes: 8 additions & 0 deletions assets/icons/threads.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
108 changes: 108 additions & 0 deletions docs/design/orchestrator-conversation.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
# Orchestrator conversation model (ideas, not decided)

Problem: while work is running, the user wants to keep talking to the
orchestrator. A common answer is a server-side message queue plus
"steer" (inject a queued message into the active turn) and "interrupt". That
makes the user classify every message's urgency. These are alternatives to
explore for Gritcode's thread runtime.

## 1. Orchestrator that's always free to talk
The orchestrator never does long work itself; it delegates everything to
worker threads. It is therefore never mid-turn, so messages to it never queue.
Queue/steer only exists at the worker level, and the orchestrator decides
which applies, not the user.

## 2. Route by intent instead of a mode button
The user just talks. The orchestrator works out what each message is:
- question → answered from the current state of the workers, no worker disturbed
- correction → passed to the affected worker immediately
- new work → a new thread or card
- change of plan → existing tasks updated, and the workers told
It shows one line saying what it did ("→ sent to *storage migration*"),
so a wrong guess is easy to spot.

## 3. Steer through shared state, not messages
Workers re-read a shared plan/board file (e.g. `.grit/board.md`) at every
step. The user or the orchestrator edits the plan; workers pick up the change
at their next step. Quieter than interrupting, leaves a record, and links up
with the planned kanban (cards hold their own instructions and limits).

## 4. Workers confirm corrections
A worker states its current step and confirms each correction ("got it,
switching after this edit"), so the user knows the correction landed.

## 5. Two separate streams
The conversation with the orchestrator stays clean; worker progress appears as
a status feed in a side pane, not mixed into the chat. Fits the default
chat-window-plus-optional-panes UI.

## 6. The orchestrator as a visible, personable guide
Luke's idea: the orchestrator is a named host for the project, not a hidden
mechanism. It greets you, e.g. "Hi! I'm the orchestrator for this project. I'll
start and watch your agents, report progress and guide you through the work.
Meanwhile, ask me anything about the project."
- It is the default view: the plain chat window *is* the orchestrator, and
worker threads appear as things it manages.
- Personality should come from usefulness (proactive status, raising
decisions, explaining what each agent is doing), not from chatter. Tone
could be user-configurable.
- Cheap model for orchestration (it mostly routes and summarises), strong
models for workers. This fits DeepSeek's prices: Flash as host, Pro or
Claude as workers.
- It decides when to interrupt you (decisions, failures, done) versus when to
stay quiet. Batching notifications is part of its job.
- The main risk is the orchestrator getting chatty or making decisions it
should hand to you. It needs a clear rule: it proposes, you decide anything
hard to undo.

## 7. Agent map: a zoomable radial view of agents
Luke's idea: instead of a lineage list, draw the agents
as a graph. The orchestrator is a circle at the centre, worker threads are
circles around it, and their subagents branch out as smaller circles. You can
zoom out for the big picture and zoom in on one branch.
- **Semantic zoom:** zoomed out, each circle shows only its state (colour,
pulse while running); in the middle range, name plus current step; zoomed
in, a live tail of the transcript and buttons (open, steer, cancel).
- **Visual encoding:** circle size = tokens or cost so far; an outer ring =
progress or remaining budget; colour = state (running, waiting for the write
lock, needs you, done, failed). Edges briefly light up when a result flows
back to the parent.
- **Linking:** clicking a circle selects that thread in the chat; it is the
same thread model as the thread list, drawn differently. Circles that need a
decision from you stand out, so the map doubles as an inbox.
- **Feasibility:** Gritcode already draws its chat on a custom canvas
(`chat_canvas.cpp`), so a native wxGraphicsContext view with a radial tree
layout and pan/zoom is realistic, with no web view needed. It belongs in a
side pane (IDE phase), built on WP5c's child-thread data.
- Possible prior art to look at: Gource (a radial, animated tree of a
repository's history), d3's zoomable circle packing and radial trees, and the
graph views in agent-workflow tools such as LangGraph Studio.

## 8. Decisions never get buried
Luke's observation: in a chat-only orchestrator, open questions and
decisions for the user scroll away and get lost in the conversation.
- Pending decisions are first-class objects, not chat text: a pinned
"Needs you" tray (or the most prominent nodes on the agent map, idea 7)
that stays visible until each one is resolved.
- Each decision card shows: the question, who is blocked by it (which
threads/packages, and from which wave), the recommended option with
one-line trade-offs, and one-click answers ("defaults OK" for a batch).
- Cards carry a deadline in workflow terms ("blocks wave E"), so the
orchestrator keeps working on everything that isn't blocked and only
escalates when a card actually blocks progress.
- Answers are recorded with the decision (an audit trail in the project, e.g.
`.grit/decisions.md`) and fed to the affected workers automatically.
- Layout: the agent map plus the "Needs you" tray in front, and the chat as
a side or bottom panel for asking questions, which turns the current
layout around once orchestration is in use.

## Gritcode advantage
A single native process holds all threads, so the orchestrator can read every
worker's state directly (no server or remote calls in between). Answering
questions from current state is fast and cheap.

## What the thread runtime needs to allow these
- Accept input at step boundaries (between model calls / tool calls) for both
the DeepSeek loop and the Claude stream-json driver.
- Plan/board state shared between threads and readable by tools.
- A per-thread "current step" status the orchestrator can query.
Loading
Loading