bzdos-hubdCAUTION
The project tracker for teams of humans and AI agents — in plain files. MCP server + CLI, zero dependencies.
Overview
From the repository's own README, as read at the audited commit. Badges and raw HTML are left out.
The project tracker for teams of humans and AI agents — in plain files.
You run two, three, five agent sessions — different tools, different vendors — across your projects. Each one is brilliant, and each one has no idea the others exist. You are the coordination layer: copy-pasting context, re-explaining state, discovering on Monday what an agent did on Friday.
hubd replaces you in that job with the most boring technology available: plain files. A shared headquarters for your whole team — agents and humans: a card that says where each project stands, a journal of what everyone did, tasks and queues every agent can wait on, heads that accept or reject their workers' work, rules the team learns from its own turns, and a read-only board to watch it all. All markdown and JSONL, in a folder you own; git carries it between machines.
`hub serve` on the demo hub. Each track's goal and work in hand; what its head accepted, rejected, and why; what is blocked and on what; an escalation that waits for your answer; a machine whose disk is nearly full.
Not a runner. Orchestrators launch your coding agents and stream their output — that's making coding faster. hubd manages the work: which projects, what's next, who does it and when, what already happened. An orchestrator can run your agents; hubd runs your projects. They compose.
Try it in a minute
npm i -g @bzdos/hubd hub demo # two tracks, six roles, three machines, a week of their work
hub demo writes an invented week of a small team into a folder of its own and prints the commands to look at it: the board on a port beside your own, hub board, hub agenda, the rules about to become laws, hub recall. Your own hub is not read or written. Run it again for a fr
6f661619d24dOBSERVED · 2026-10-10Connect
Built from this server's own package name, version and transport as found in its source — not copied from anyone's documentation, so it cannot drift against a page we do not control. Replace the environment placeholders with a token scoped to the least it needs.
claude mcp add hubd -- npx -y @bzdos/[email protected]
Exposed tools (33)
26 read · 7 write · 0 destructive.
| Tool | Risk | Description |
|---|---|---|
harvest | read | Harvest this dialog into the hub — projects, tasks, decisions, links, open questions (the Harvest Protocol). No need to fetch HARVEST.md. |
hub_agenda | read | The day split by WHO CAN ACT: agent work ready now, the owner\ |
hub_card_set | write | Create or update a project card from just a name and a digest — no folder needed (unlike hub_sync). Use it to capture a project that is not a local git checkout, e.g. when harvesting a dialog. Preserves any hand-written frontmatter and Facts. To fix ONE stale line without touching the owner\ |
hub_claim | read | Soft-lock a work area so other agents see it. Not enforced — informational. Write |
hub_claim_check | read | Before editing a file: is it inside somebody\ |
hub_context | read | Where am I — the first call of a session and the first call after a context compaction. Resolves which hub project YOUR working directory belongs to, most to least certain: a .hubd marker file (repo root, first line = project slug) · a project card\ |
hub_get | read | ONE project in depth: its card, its recent journal entries and any active soft-locks. Compact by default — the card |
hub_graph | read | The typed relationship graph across projects AND resources: who runs where, what depends on / deploys to / exposes what. Edges are frontmatter [[links]] keyed by relation (runs_on, depends_on, deploys_to, exposes, part_of, ...). Returns nodes, edges, and dangling links. Filter by project or type. |
hub_heartbeat | read | Record that an agent is alive — call it each work cycle (right after hub_report, before the next hub_queue_wait) so MCP/headless agents show up in hub_presence the same way screen-scraped ones do, no human bridge needed. Overwrites this agent\ |
hub_law | read | A head\ |
hub_next | read | The ONE task to do now, and why it won — not a list. Picking from a list is work, and a session that has to pick tends to pick the easy one. A task whose dependencies are still open is never eligible, however loud it is. Says explicitly when the chosen one is the owner\ |
hub_onboarding | read | Orientation for an agent that has never worked with this hub before: which channel to use for what (claim vs task vs report vs queue — the #1 mistake), the author rule, the session ritual, how to recover after a compaction. Call this FIRST the first time you connect. Default mode |
hub_presence | read | The fleet roster as far as it can honestly be seen from here: this node\ |
hub_queue_ack | read | Confirm that a delivered queue block was processed, not just read. Without this, a zombie session that reads a block and dies looks exactly like a processed one — the sender sees pending=0 but gets no reply. Ack moves the block from |
hub_queue_send | write | Append a message to a role\ |
hub_queue_wait | read | Block until new content lands in <role>\ |
hub_queue_wait_all | read | Subscribe to EVERY role\ |
hub_recall | read | What do we know about X — ranked across project cards, their sections, decisions, the journal and tasks, instead of hub_search\ |
hub_reflect | read | The reflection digest of one project, what a head reads instead of its workers\ |
hub_release | write | Release a soft-lock. Pass id, or project+area+agent, or task+agent (give a started task back to the work queue). |
hub_report | read | Append a session report to the shared journal: what was done / broken / blocked. Lines are routed by prefix: DECIDE: (what | why), FACT:, HYPO:, COMM:, NEXT:, DONE: <id>, TASK:, NOTE:, TO:, HANDOFF:. HANDOFF: lines replace your own |
hub_resource_get | read | One resource card plus its inbound and outbound typed relationships. |
hub_resource_list | read | List resource cards (hosts, vms, services, endpoints, providers). Optionally filter by type. |
hub_resource_set | write | Create or update a resource — an infrastructure/topology entity: host, vm, service, endpoint, or provider. Structured attributes (type, address, os, provider, status) and typed relationships go in fields, NOT prose. Use this instead of describing infra inside a card digest. |
hub_stats | read | What the sessions cost and what came of it, per task, model, role or day. Tokens are READ from the clients\ |
hub_sync | write | Sync a project folder into the hub. Collects git facts automatically; pass digest (your own summary of state/next steps) and the card is rewritten. |
hub_task_add | write | Add a task to the shared cross-project backlog. |
hub_task_get | read | ONE task by id, plus what it is blocked by and what it blocks, and, once the hub holds sessions (hub sessions ingest), |
hub_task_list | read | List backlog tasks. Filter by project and/or status; page with limit/offset. |
hub_task_update | write | Update a task: close it (status=done), reassign, reprioritise, edit text/deadline/cat. |
hub_trajectory | read | Deterministic dependency-graph plan over tasks\ |
hub_usage | read | What the work cost, over a window, per project and per agent — with a hard line between SUPPLIED (seconds/tokens/money, reported by clients through hub_usage_add: what the hub can neither measure nor read; a session\ |
hub_whatsnew | read | Personalized |
Trust audit
CAUTIONgrade B · trust 81/100 Install with care. The audit found things worth knowing before you trust its output.
| Layer | What it checks | Result |
|---|---|---|
| L0 | Provenance & inventory | PASS |
| L1 | Static analysis of the code | WARN |
| L2 | Instruction surface (what it tells the agent) | PASS |
| L3 | Class-specific surface | PASS |
| L4 | Behavioural (sandbox) | SKIPPED |
What the source does
- Filesystem
- declared (10 observation(s))
- Network
- declared (6 observation(s))
- Shell
- declared (5 observation(s))
- Dependencies
- pinned
- Secrets in source
- found
Findings (22)
console.log(removeSecret(name, { teamRoot }) ? `removed ${name}` : `no secret named ${name}`);ok(refused('-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaA\n-----END OPENSSH PRIVATE KEY-----', /carries a PEM block/), 'cargo: a PEM block is refused');.hubd
for (const [k, v] of Object.entries(secs)) out[k] = crypto.createHash('sha1').update(v).digest('hex').slice(0, 10);export const ruleId = (s) => createHash('sha1').update(ruleKey(s)).digest('hex').slice(0, 6);export const entryHash = (e) => crypto.createHash('sha1').update(String(e.text || '')).digest('hex').slice(0, 10);const hash = (s) => crypto.createHash('sha1').update(s).digest('hex').slice(0, 16);const hashOf = (family, line) => crypto.createHash('sha1').update(family + '\n' + line).digest('hex').slice(0, 12);try { return JSON.parse(fs.readFileSync(new URL('../../package.json', import.meta.url), 'utf8')).version; }try { return fs.readFileSync(new URL('../../prompts/protocol.md', import.meta.url), 'utf8'); }try { md = fs.readFileSync(new URL('../../HARVEST.md', import.meta.url), 'utf8'); }export const META_DIR = fileURLToPath(new URL('../../prompts/meta/', import.meta.url));const fragRows = names.map(n => [`[${n}](../../prompts/meta/${n}.md)`, docs.templates[n] || '',hubd kanban http://127.0.0.1:7790
hubd kanban http://127.0.0.1:7790
export MATRIX_HS=http://127.0.0.1:7808 MATRIX_ROOM='!team:example.org' MATRIX_TOKEN=stand-in
export SLACK_WEBHOOK=http://127.0.0.1:7808/services/T000/B000/stand-in
export NTFY_URL=http://127.0.0.1:7808/hubd-oak-k7q2m9
docs/media/kanban.gif
- **One token = full access** (single-tenant) or **one token = one workspace**
<div class="hint"><b>Share this exact line</b> to bring your team into the same hub — same token, same workspace. Anyone who has it gets full access, so treat it like a key. Need a separate space? <bu
cat >> ~/.ssh/config <<'EOF'
Gates applied: no_behavioural_pass.
6f661619d24dfull audit observations/trust-audit/mcp-server/bzdos__hubd.json · Report an issue / request a re-scanAudit history
Every audit this server has had. A grade with a past is a grade somebody is still checking.
| Date | Source | Verdict | Grade | Score | Change |
|---|---|---|---|---|---|
| 2026-10-10 | 6f661619d24d | CAUTION | B | 81 | first audit |
Questions
What is the bzdos-hubd MCP server?
The project tracker for teams of humans and AI agents — in plain files. MCP server + CLI, zero dependencies.
What tools does bzdos-hubd expose?
33 in total: 26 read-only, 7 that write, and 0 that can delete or overwrite. Every one is listed on this page with its risk.
Is bzdos-hubd safe to connect to an agent?
With care. The audit graded it B (81/100) and found 22 things worth knowing before you trust this server, listed below with the exact line each was found on.
What credentials does bzdos-hubd need?
It reads HUBD_SECRETS_DIR and HUBD_TOKEN from the environment. Give it a token scoped to the least it needs — an agent that can be talked into calling a tool can be talked into calling it with your credentials.
How does bzdos-hubd run?
It speaks stdio, so it runs as a local process your client starts. It is published on npm as @bzdos/hubd at 0.9.68.
How current is this page?
The grade is for one exact copy of the source (6f661619d24d), read on 2026-10-10. The repository is watched and re-audited when it changes.