project-manager-tui
A terminal task board for people running coding agents in git worktrees.
Tasks live in plain Markdown that you and the agents both edit. pm-tui renders
them as one list ordered by what needs you: agent requests waiting on an answer
first, then your open tasks, with everything an agent is busy with hidden until
you ask to see it. One keypress opens a task's worktree, starts its agent, or
releases its branch — the TUI shells out to a script you supply for all of it,
so it knows nothing about tmux, ssh or your remote host.
Install
pip install project-manager-tui
pm-tui
Requires Python 3.9+.
Configure
~/.project-manager-tui.toml:
# Required.
agent_worktree_script = "/path/to/agent-worktree.sh"
projects_dir = "/efs/me/projects"
# Optional, with their defaults.
projects_filename = "Projects.md"
git_repo_dir = "." # the cwd `go` is run in
sync_interval = 300 # seconds between `sync-master` runs
editor = "$EDITOR" # falls back to vim
approvals_dir = "" # default: {projects_dir}/../approvals
# Optional. Which agent a NEW worktree starts on, cycled in the UI with `m`.
# Short name -> "<cli>-<model>", split at the FIRST dash: everything before it
# is the CLI to run, everything after is the model handed to that CLI. The
# first entry is the default, and the table's order is the cycle order.
#
# Keep this table LAST in the file: a TOML table swallows every bare key that
# follows it, so a `models` section in the middle silently steals the settings
# under it.
[models]
fable = "claude-fable" # claude --model fable
astra = "codex-gpt-6-astra" # codex -m gpt-6-astra
Without [models] the picker is empty, m does nothing, and every worktree
starts the way it did before: claude, on whatever the container defaults to.
agent_worktree_script is the only real dependency, and writing one is the bulk
of the setup — see the contract below.
Layout
projects_dir/
Projects.md ## Active / ## Future / ## Archived, one slug per line
my-project/
Project.md the task list
tasks/3/Task.md one task's brief, created on demand
A task is a numbered line in Project.md:
1. [ ] rewrite the fill parser
2. [ ] backfill september >1 blocked until task 1 closes
3. [ ] chase the vendor >2026-09-20 pinned to a date
4. [x] delete the old path
The state character drives everything:
| state | meaning |
|---|---|
[ ] |
todo |
[i] |
an agent is running /ready on it |
[t] |
tested |
[r] |
released — branch pushed to master |
[d] |
delivered — deployed |
[v] |
verified — you have seen it work |
[x] |
complete |
[s] [z] |
snoozed / snoozed forever |
[x] and [v] are what unblock a dependent task. [i] [t] [r] [d] mean
underway, so the task is not offered as new work.
Keys
Task view:
j/k navigate z snooze: 1H/2H/4H/8H/1D/2D…
t vim Task.md u unset: clear state + time snooze
p vim Project.md c complete
v view worktree r release (mark [r])
g go: start its agent d delete task
s switch to worktree V/Z/B/W show verified/snoozed/blocked/working
m cycle the model P project view, ? help, q quit
Approval rows (!) — requests an agent has filed and cannot execute itself:
Enter review + run it i inspect the request JSON
x reject, with a reason t/p vim the filing task's Task.md/Project.md
v view the agent z snooze, u clear a hold nothing is paying
Status light
pm-tui --web # TUI plus the status page
pm-tui --web-only # just the page, no TUI
Serves a full-window light on port 8899: green when the default view is
empty, amber with a count when something wants you, grey when the count
is too old to trust. --web-port, --web-bind and --web-interval move it;
/status.json is the same thing as JSON. Park it on a second screen and stop
checking.
The agent-worktree.sh contract
The TUI never touches git, tmux or ssh itself. It invokes your script with
list, add, rm, switch, view, go, release, approve and
sync-master, and the shipped contract document specifies each one — the exact
list output format, which status tokens the working filter and the status
light read, what may prompt and what may not, and the approval queue's on-disk
format, statuses and leases.
It ships inside the package:
python -c "import importlib.resources as r, sys; \
sys.stdout.write((r.files('project_manager_tui') / 'agent-worktree-contract.md').read_text())"
Read it before writing a script. Several of the TUI's behaviours — hiding busy
worktrees, the green light, a go that does not steal your terminal — are
conventions your script has to hold up its end of, and a script that ignores
them still runs, just quieter than it should.
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file project_manager_tui-0.1.15.tar.gz.
File metadata
- Download URL: project_manager_tui-0.1.15.tar.gz
- Upload date:
- Size: 48.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via:
twine/7.0.0 CPython/3.10.8
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a8850475a21a3134354b250f833fc3824f79e2677e02e4bd3e216a96f9d66ccd
|
|
| MD5 |
e097e1957446eabfe2b18b8c3816bd9d
|
|
| BLAKE2b-256 |
17289551bbba748303e7e83ec1182e9c032856abbbd0bb889e4db05ce509635f
|
File details
Details for the file project_manager_tui-0.1.15-py3-none-any.whl.
File metadata
- Download URL: project_manager_tui-0.1.15-py3-none-any.whl
- Upload date:
- Size: 50.7 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via:
twine/7.0.0 CPython/3.10.8
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
11cd78af42ae9ab01962c8d4747b1deb510e1e29d66dc217330f2ea9bb2d9342
|
|
| MD5 |
1b6c4d59b02a801038f15142d9a05f87
|
|
| BLAKE2b-256 |
fea98ae5b29459efa2282a5066eecdaec5c4bd7d7610be707c31f385386bb312
|