跳到正文
DEV Community· ILIA KARPENKO·· 3 小時前AI 評分57

如何在 Git worktrees 中管理並行 AI 編碼智能體,避免資源衝突

Parallel AI Coding Agents in Git Worktrees: How to Stop the Collisions

AI 導讀

Git worktrees 可分隔並行 AI 編碼智能體的檔案,但不會隔離連接埠、資料庫、程序或磁碟空間;作者整理手動管理方法,並介紹 agentgc 作為工具方案。

正文

Run three AI coding agents on one machine, each in its own git worktree, and the code stays separate. Everything around the code does not.

Two dev servers try to bind port 3000, and one of them fails. Two tasks write to the same database, so one agent's test rows appear in the other agent's run. Three builds start at the same moment and the machine freezes. Finished task folders stay on disk, while package caches, browser downloads and temp files fill the drive.

Git keeps the files apart. It does not keep ports, databases, processes or disk space apart. You can fix most of this with no tool at all. Here is the manual version first.

Step 1: one worktree per task

git worktree add -b feature-login ../myapp-feature-login main
cd ../myapp-feature-login

-b creates a new branch from main. Each task gets its own folder and branch. Your main checkout stays as it is.

Step 2: one env file per task, with its own port

Create .env.local in each worktree:

PORT=3101
DATABASE_URL=postgres://localhost/myapp_feature_login

The next task gets PORT=3102. Check how your dev server reads its port. Some frameworks read .env.local. Others take a flag.

Step 3: one database per task, inside one Postgres server

createdb myapp_feature_login

Or, in psql: CREATE DATABASE myapp_feature_login;. Run the migrations against that database. One server holds all the tasks. You do not start a second Postgres instance for each agent.

Step 4: run heavy commands one at a time

On macOS, Linux or Git Bash, a directory lock works. mkdir either creates the folder or fails, so only one shell wins:

until mkdir /tmp/build.lock 2>/dev/null; do sleep 2; done
npm run build
rmdir /tmp/build.lock

If the build crashes or you close the terminal, rmdir never runs. Delete /tmp/build.lock by hand before the next build.

What gets hard by hand

Steps 1 to 4 hold up while the task count stays small. As it grows, four chores pile up:

  • Cleanup. git worktree remove refuses while a shell or an editor sits in the folder. On Windows, the folder stays locked until you find the program that holds it.
  • Port bookkeeping. You keep a list of which port belongs to which task. A forgotten dev server keeps its port after its task ends.
  • Killing the right process. On Windows, netstat -ano | findstr :3101 shows the PID. Then run taskkill /PID <pid> /F. Check the PID first. A wrong PID stops someone else's work.
  • Dependencies. Each worktree holds its own node_modules, .venv or target folder. The disk use adds up for every task.

The same steps in agentgc

agentgc is a garbage collector for the disk junk that CLI coding agents and dev tools leave behind: package caches, browser downloads, agent sessions and temp files. It also builds task environments: one worktree, free ports, one database name per task and an env file. The task commands create all of that in one step. The run command queues heavy work, and up starts the services of a task.

Build it from a clone of the repo with Rust: cargo install --path .

Put the task settings in agentgc.task.toml in the repo root. A short version:

[worktree]
dir = "worktrees"
base = "main"

[copy]
files = [".env.local"]

[ports]
names = ["web"]
range = [3100, 3999]

[db]
name = "{repo}_{name}"
create = "createdb {db}"
drop = "dropdb {db}"

[env.dynamic]
DATABASE_URL = "postgres://localhost/{db}"

[setup]
commands = ["npm install"]

dir = "worktrees" puts the worktrees in a folder inside the repo, so add that folder to .gitignore. agentgc prints a hint when the folder is not ignored. It never edits .gitignore itself.

The commands:

agentgc scan                                       # read every path before any clean
agentgc task new feature-login                     # dry run: prints the plan
agentgc task new feature-login --yes --run-setup   # worktree, ports, database, setup
agentgc task list                                  # ports, database and status per task
agentgc ps                                         # processes per task, with RAM
agentgc ps --stop                                  # dry run: idle dev servers, tests, builds
agentgc run -- npm test                            # queued: heavy commands take turns
agentgc clean --dry-run                            # junk from scan, item by item
agentgc task done feature-login                    # dry run: blockers and processes
agentgc task done feature-login --yes              # removes worktree, task files, merged branch

task new without --yes only prints the plan. The file .agentgc/task.env holds PORT_WEB and DATABASE_URL, so your dev server must read that file.

Safety model

Only two commands delete: task done --yes and clean.

  • Dry run first. task new, task done and ps --stop print a plan and change nothing until you add --yes.
  • Blockers stop task done. It refuses while the worktree holds uncommitted files or commits that are neither merged nor pushed. --force overrides both checks and prints what would be lost.
  • Item by item. clean asks about each item. A safe item needs a y. A risky item needs you to type its ID. Risky items go to the Recycle Bin, not to permanent delete.
  • Guards. clean refuses paths that hold a .git entry, and paths named Documents, Downloads or User Data, among others.
  • Idle only. ps --stop touches only idle dev servers, language servers, tests and builds. Agents, databases and other processes keep running.
  • Config runs commands. create, drop and setup.commands run as you, without a shell. Read agentgc.task.toml like a Makefile before you use --run-setup or task done --yes.

Honest limits

  • Built and covered by automated tests on Windows. The Linux and macOS code paths were never built or run.
  • agentgc up starts the services listed for a task. It is opt-in and installs no system service. Nothing starts at boot or login.
  • agentgc never starts containers, never runs Docker and never talks to a database server.
  • On Windows, ps --stop --yes stops nothing without --force, because agentgc has no graceful stop on Windows.
  • run is not fair. Whoever finds a free slot first gets it.

Proof

After one cleanup session on 2026-11-04, free space on my Windows machine went from about 6 GB to about 180 GB. This is my own statement. It is not a measurement by agentgc.

Credit

The queue idea behind run comes from heavy by mokevnin, a counting semaphore for macOS and Linux. agentgc's run is separate code. It adds Windows support and named resources, such as one phone or one browser profile.

Next step

If you run agents in parallel and want fewer collisions, star the repo: https://github.com/JohnWayneeee/agentgc

Telegram channel https://t.me/+pWGhdQdw5DZmYzYy

來源:DEV Community · dev.to