An open API service indexing awesome lists of open source software.

https://github.com/broomva/p9

bstack P9 — CI watcher + productive-wait primitive. Replaces sleep-based CI waits with an event-driven control loop, drains a context-scoped wait-queue while CI runs, classifies failures, and self-heals known categories. Merge authorization stays with the control metalayer.
https://github.com/broomva/p9

agent-skill broomva bstack ci-cd claude-code productive-wait self-heal

Last synced: 5 days ago
JSON representation

bstack P9 — CI watcher + productive-wait primitive. Replaces sleep-based CI waits with an event-driven control loop, drains a context-scoped wait-queue while CI runs, classifies failures, and self-heals known categories. Merge authorization stays with the control metalayer.

Awesome Lists containing this project

README

          

# p9 — bstack P9: productive-wait primitive (the wait optimizer)

> **Never `sleep` on a blocking wait.** P9 is a wait optimizer — turn any blocking external operation (PR CI, push-triggered deploys, builds, long indexing) into work on the next priority. PR CI is the canonical implementation today; the primitive is broader.

## Why P9 exists

When an agent kicks off a long external operation and waits for it, the dumb pattern is `sleep`. P9 replaces it with productive-wait discipline:

1. **Notification via `run_in_background`** — for PR CI, the observer is `gh pr checks --watch`. No polling.
2. **Productive wait** — the agent drains a context-scoped queue (session → memory → graph → docs → Linear) while the operation runs.
3. **Self-heal** — when CI fails for known categories (lint, format, codegen drift, flaky tests), P9 classifies and applies the heal command. Unknown failures escalate to a Linear ticket.
4. **Merge stays governed** — P9 emits `MERGE_READY`; the existing `.control/policy.yaml` + control-gate-hook authorizes the actual merge. P9 owns mechanism, not policy.

## Scope today vs. on roadmap

P9 currently tracks **PR-scoped waits** through the `p9 watch ` CLI. That covers ~95% of agent waits in a typical session.

The remaining 5% — **non-PR waits** — are not yet wired into `p9 watch`. These include:

- **Push-triggered deploys** — a push to `main` that fires a Vercel/Cloudflare deploy hook without opening a PR
- **Long-running test suites or builds** — outside the CI surface
- **External index / sync operations** — content pipelines, embeddings, search-index rebuilds

For these, the productive-wait *discipline* still applies: kick off next-priority work, then do **one direct check** on the operation's completion. Never `sleep`. Wiring these into `p9 watch ` is on the roadmap.

## Quick start

```bash
# 1. Install dependencies (stdlib-only at runtime; pytest for tests)
python3 -m venv .venv && source .venv/bin/activate
pip install -r tests/requirements-dev.txt

# 2. Wire policy blocks
# Add ci_watch: and ci_heal: to your .control/policy.yaml. See
# tests/fixtures/policy-good.yaml for a complete example.

# 3. Verify install
python3 scripts/p9.py doctor
# → p9 doctor: ok

# 4. Use it
gh pr create ... ; PR=42
python3 scripts/p9.py watch $PR --background
# In parallel: pull productive work while CI runs
python3 scripts/p9.py wait-queue pop
# When the bg-task notification fires, check terminal state:
python3 scripts/p9.py status --pr $PR --json
```

## Subcommands

| Command | Purpose |
|---|---|
| `p9 watch ` | Spawn `gh pr checks --watch` in background, transition to `WATCHING`. |
| `p9 status [--pr N]` | Show in-flight PRs and their state-machine position. |
| `p9 wait-queue {push,pop,list,clear}` | Manage the productive-wait queue (5 sources, priority-ordered). |
| `p9 heal --classify` | Read failure log, classify against the rubric (read-only — does not execute heals). |
| `p9 events tail` | Stream P9 events (P1 conversation-bridge consumes these). |
| `p9 merge-ready ` | Mark a green PR as ready for metalayer-authorized merge. |
| `p9 doctor` | Health-check: gh auth, state directory, policy blocks, rubric. |

## Architecture (one paragraph)

Pure Python, stdlib-only at runtime. State lives in `~/.config/broomva/p9/state.jsonl` (append-only, JSONL with `flock` serialization, partial-write recovery on read). Failure classification is regex-only — no LLM in the hot path — driven by `references/scoring-rubric.md` (markdown is human-canonical; `_builtin_rubric()` in `scripts/p9.py` is code-canonical; a unit test asserts they stay in sync). The evaluator scores progress with a four-term weighted sum (signature change + failures decreased + budget remaining + classifier confidence) and forces escalation after two consecutive sub-floor cycles. Multi-PR concurrency is bounded by `ci_watch.max_concurrent_prs` (default 1). Everything fails closed on missing or malformed policy blocks.

## Cardinal invariant

> **P9 never silently drops state.** Every failure produces (a) a `state.jsonl` event, (b) a Linear ticket via the escalation channel, or (c) both. If neither write succeeds, P9 crashes loudly (exit 99) — degraded silent operation is forbidden.

## Where it fits in the bstack

```
P3 (Linear ticket) → P4 (PR pipeline) → P9 (CI watcher + heal) → metalayer authorizes merge
↓ drains during wait
{context queue, P5 worktree, P6 bookkeeping}
```

Composes with — does not duplicate — existing primitives. See `AGENTS.md` in the workspace repo for the full bstack specification.

## Spec & design

The full design lives at [`broomva/workspace`](https://github.com/broomva/workspace) under `docs/superpowers/specs/2026-05-04-p9-ci-watcher-design.md`. Seven rounds of clarifying Q&A locked the architecture before a line of code was written.

## Tests

```bash
python3 -m pytest tests/
# 46 passed
```

## License

MIT — see [LICENSE](LICENSE).

## Related

- [broomva/bookkeeping](https://github.com/broomva/bookkeeping) — bstack P8 (knowledge graph engine)
- [broomva/workspace](https://github.com/broomva/workspace) — unified workspace + governance