Skip to content

matheusvanzan/multiagent

Repository files navigation

🧠 multiagent

A terminal group chat where you talk to multiple AI CLIs at once.

Claude → Codex → Opencode reply one after another (or all at once in parallel mode), inside a clean full-screen developer TUI. The roster is configurable, so bring your own agents.

Python TUI Platform i18n Status

English · Português


What is this?

multiagent turns your terminal into a group chat between AI agents. You type one message; Claude, Codex and Opencode answer one after another, and every agent reads the full transcript before replying, so they build on (and argue with) each other instead of answering in a vacuum.

It looks and feels like a real developer tool: a two-pane TUI with the conversation on the left and a live technical panel (execution status, logs, consensus, meta) on the right.

multiagent TUI showing a sequential multi-agent conversation


Instructions for AI agents working on this repo

Read this README first, then inspect magent/cli.py, magent/tui.py, magent/agents.py, and agents.json before changing behavior.

Keep the Windows-first CLI assumptions intact unless the task is explicitly about POSIX support. The agent CLIs receive prompts through STDIN, sessions are stored under sessions/, and the configurable roster lives in agents.json.

Do not push to a remote unless the human explicitly asks for it.


✨ Features

  • 🔀 Sequential and parallel modes : by default agents reply in turn, each reading what the others said. In parallel mode they all receive the same snapshot and reply simultaneously, like using multiple AI web UIs at once. Toggle at any time with Ctrl+T or start with --parallel.
  • 🗣️ Mode tag per message : every agent reply is labeled (sequential) or (parallel) so the transcript is always self-explanatory.
  • 📋 System prompt visible on open : the exact instructions sent to every agent appear as the first dimmed message in the chat so you always know what context they are working from.
  • 🧵 Full shared context : every agent receives the entire transcript each turn.
  • 🖥️ Full-screen TUI : two-pane layout, color-coded participants, live status, logs, consensus and meta panels. The active mode is always visible in the top bar.
  • 💾 Resumable sessions : --session <name> saves to sessions/<name>.json every round; reuse the name to pick up exactly where you left off (history, messages, consensus, tokens, runtime, mode).
  • 🌍 Bilingual : English by default, full Portuguese with --pt (UI and the prompts sent to the agents). Set a default with MULTIAGENT_LANG.
  • 🖱️ Mouse + keyboard : wheel-scroll the chat, Shift+drag to select/copy, plus keyboard shortcuts for everything.
  • 🧰 Graceful degradation : no prompt_toolkit or no real terminal? It drops to a clean linear mode automatically (parallel is supported there too, via ThreadPoolExecutor).
  • 📝 Plain-text logs : every run writes a human-readable session_*.txt transcript (and, with --debug, the exact prompt sent to each agent).

⚙️ How it works (the interesting part)

Each agent is a real CLI invoked per turn, and the accumulated transcript is delivered through STDIN, never as a command-line argument.

Why STDIN? On Windows the codex/opencode CLIs are npm shims (.cmd / .ps1). Passing a long, multiline transcript as an argument gets mangled when it crosses the batch shim, so the later agents would silently lose the conversation. Feeding the prompt on STDIN keeps the multiline context intact. The launcher resolves .exe directly and routes .cmd/.ps1 through powershell -File, which forwards STDIN to the real executable.

The TUI runs each agent in a background executor, so the interface stays responsive and the status panel updates live: waiting to analyzing… to done.


📦 Requirements

  • Python 3.8+
  • prompt_toolkit (the TUI engine)
  • The agent CLIs in your roster installed and authenticated, on your PATH. The default roster is:
    • claude (Claude Code), invoked as claude -p
    • codex, invoked as codex exec --skip-git-repo-check
    • opencode, invoked as opencode run

🪟 Platform: built and tested on Windows (the CLI resolution is PowerShell/npm-shim aware). POSIX support is on the roadmap.

Missing one of the CLIs? The app still runs; that agent's turn just reports it's unavailable and the loop keeps going.


🚀 Install

git clone <your-repo-url> multiagent
cd multiagent
pip install prompt_toolkit

Run it:

python multiagent.py

🧑‍💻 Usage

python multiagent.py                                  # start empty, type your first message
python multiagent.py "should we ship this on Friday?" # start with an initial prompt
python multiagent.py --parallel "..."                 # start in parallel mode
python multiagent.py --pt "vamos enviar na sexta?"    # Portuguese UI + prompts
python multiagent.py --session design-review "..."    # named, resumable session
python multiagent.py --debug "..."                    # log the exact prompt per agent

Flags

Flag Description
--session <name> Named session. Reusing the same name resumes it (mode is restored too); a new name starts fresh.
--parallel Start in parallel mode (all agents reply simultaneously, no cross-contamination within the round). Toggle at runtime with Ctrl+T.
--lang {en,pt} Interface and agent-prompt language. Overrides $MULTIAGENT_LANG.
--pt Shortcut for --lang pt.
--debug Write the full prompt sent to each agent into the session log.

Keyboard shortcuts

Key Action
Enter Send message
Ctrl+J New line (multiline input)
PgUp / PgDn Scroll the chat
Ctrl+T Toggle parallel / sequential mode
Ctrl+L Toggle the side panel
Ctrl+K Clear the chat / context
Alt+N New topic (reset context, keep the screen)
Ctrl+C Quit

🖱️ Mouse wheel scrolls the chat. To select and copy text, hold Shift while dragging (the terminal's native selection).


🧩 Configuring agents

The roster lives in agents.json at the project root. Edit it to add, remove or reorder agents, no code changes needed. The array order is the execution order, and the last agent gives the round's consensus.

[
  { "label": "Claude", "cmd": "claude", "flags": ["-p"], "color": "#b07cff" },
  { "label": "Codex",  "cmd": "codex",  "flags": ["exec", "--skip-git-repo-check"] },
  { "label": "Opencode", "cmd": "opencode", "flags": ["run"] },
  { "label": "Gemini", "cmd": "gemini", "flags": ["-p"], "color": "#f7768e" }
]

Only label and cmd are required. Optional per agent: flags (CLI arguments), color (hex; a palette color is assigned if omitted), key, name and cmd_label. Every agent must read its prompt from STDIN (that is how the transcript is delivered).

Point at a different file with the MULTIAGENT_AGENTS environment variable. If the file is missing or invalid, the app falls back to a built-in default roster.


🌍 Language

English is the default. Three ways to switch, in precedence order:

python multiagent.py --pt          # 1. flag (highest priority)
export MULTIAGENT_LANG=pt          # 2. environment variable (bash/zsh)
$env:MULTIAGENT_LANG = "pt"        #    ...or PowerShell
setx MULTIAGENT_LANG pt            #    ...or persistent on Windows
                                   # 3. default is en

Switching the language changes the whole UI and the instructions sent to the agents, so they reply in your language too.


🔀 Sequential vs parallel mode

Sequential (default): agents reply one at a time. Each one receives the full transcript including the previous agents' replies from the same round, so they build on each other.

Parallel: all agents get the same snapshot (the conversation up to, but not including, the current round's replies). They run concurrently and responses appear as they arrive. After every agent has finished, their replies are appended to the history in roster order, so the next round's sequential or parallel context is deterministic.

sequential:  Claude sees [history]
             Codex   sees [history + Claude's reply]
             Opencode sees [history + Claude's reply + Codex's reply]

parallel:    Claude, Codex, Opencode all see [history] -- no cross-contamination
             (responses arrive as they finish; history updated in roster order)

Every agent message is tagged (sequential) or (parallel) so the transcript is self-explanatory when you mix modes mid-session. The active mode is always visible in the top bar and is saved with the session.


💾 Sessions

Every run logs to a human-readable session_YYYYMMDD_HHMMSS.txt. With --session, the full state is also persisted as JSON:

python multiagent.py --session design-review "let's review the API"
# ...chat, then quit...
python multiagent.py --session design-review        # resumes right where you left off

Restored on resume: conversation history, on-screen messages, consensus, token estimate and accumulated runtime. Saved atomically every round, on clear, on new topic and on exit.


🏗️ Architecture

A thin launcher over the magent package, one responsibility per module:

multiagent.py        # launcher: fixes UTF-8 streams, calls magent.cli.main()
agents.json          # the agent roster (editable, see "Configuring agents")
magent/
├── i18n.py          # translation table (EN/PT) + L() + set_lang()
├── config.py        # UI colors, tunables, agent-roster loader
├── agents.py        # prompt building + CLI execution (never raises)
├── sessions.py      # save/resume sessions as JSON
├── utils.py         # input sanitizing, log writing, formatting, git
├── tui.py           # full-screen prompt_toolkit app (chat + side panel)
└── cli.py           # argparse, language resolution, TUI/fallback routing

Modules are layered with no import cycles: i18n and sessions are leaves; config and utils depend on i18n; agents on those; tui on everything below it; and cli ties it together.


🧯 Fallback mode

No prompt_toolkit, or piping input (no TTY)? multiagent automatically switches to a linear mode that runs the same agents in order and prints their replies, handy for scripting and CI:

echo "summarize this in one line" | python multiagent.py

🗺️ Roadmap

  • Configurable agent roster and order (agents.json)
  • Parallel mode (all agents reply simultaneously, toggle with Ctrl+T / --parallel)
  • POSIX (macOS/Linux) CLI invocation
  • Real token accounting per CLI (current count is an estimate)
  • Per-session export (Markdown)

📄 License

MIT. See LICENSE.

About

A terminal group chat where you talk to multiple AI CLIs at once.

Resources

License

Stars

0 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors