Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 16 additions & 9 deletions .agents/skills/project-management/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,43 +29,50 @@ Apply `AGENTS.md` section 7's authoritative secondmate routing rules; if an exis
Absence from the main `data/projects.md` registry is never evidence that no second mate owns the domain.
If the owning second mate cannot accept the route, report that concrete blocker or obtain an explicit captain redirection rather than silently duplicating the project in the main home.

Resolve the project name, destination, delivery mode, and autonomy posture before changing local or remote state.
Resolve the project name, destination, delivery posture, and autonomy posture before changing local or remote state.
Keep a newly added clone and its registry entry consistent, and roll back only artifacts created by the incomplete operation when a later initialization step fails and that rollback is safe.
Do not overwrite or repurpose an existing path.

## Delivery posture

Choose the delivery mode when adding or creating the project:
The registry records the project's standing posture, which is the captain's default for the work rather than any task's answer; `AGENTS.md` section 7 owns how each task's concrete mode and yolo are resolved at intake and passed explicitly to the brief, the spawn, and any promotion.
Choose that posture when adding or creating the project:

- `no-mistakes` runs the full validation pipeline before a PR and is the default when the captain does not specify a mode.
- `no-mistakes` runs the full validation pipeline before a PR.
- `direct-PR` pushes and opens a PR without the no-mistakes pipeline.
- `local-only` has no required remote or PR and lands only through the approved local fast-forward path.
- `no-mistakes-prod-only` is a conditional policy rather than one flat mode: genuinely internal-only tooling, automation, contributor or operator process, and release or submission work ships `direct-PR`, while product-facing, mixed, and uncertain work ships `no-mistakes`.

`no-mistakes-prod-only` is the default for a newly added or created remote-backed project when the captain specifies nothing, and a project with no remote defaults to `local-only`.
State that resolved default while confirming the source, local name, and posture instead of asking the captain to choose from scratch, and record a flat mode instead whenever they ask for one.
Existing registry entries keep the meaning they already have and are never migrated or reinterpreted, so a legacy entry with no bracket stays `no-mistakes`.
Registering a conditional policy is a one-time choice and never requires classifying any change; the per-task surface classification happens at each task's intake, and internal-only is never inferred from file location or project name.

The optional `+yolo` posture changes routine approval authority but does not change the delivery mode.
Default it off, and enable it only on the captain's explicit instruction.
Default it off for every project and every posture, and enable it only on the captain's explicit instruction.
`AGENTS.md` section 7 owns the complete authority boundary and exceptions when it is on.

## Add or clone an existing project

Confirm the source URL, local project name, delivery mode, and autonomy posture.
Confirm the source URL, local project name, delivery posture, and autonomy posture, stating the resolved default for each rather than asking the captain to invent one.
Clone into `projects/<name>` and add the registry entry only after the destination is known to be unused.
A `no-mistakes` project must have an `origin` remote and must complete the initialization procedure below.
A `no-mistakes` or `no-mistakes-prod-only` project must have an `origin` remote and must complete the initialization procedure below, because a conditional policy's product-facing work runs the pipeline while its internal-only work still takes the direct PR.
A `direct-PR` project needs an `origin` remote but skips no-mistakes initialization.
A `local-only` project may have no remote and skips no-mistakes initialization.

## Create a project

Creating a GitHub repository is outward-facing.
Before making that remote change, propose the repository name, owner or organization, visibility, and delivery mode, defaulting visibility to private and delivery mode to `no-mistakes`, then obtain the captain's explicit consent for those values.
Before making that remote change, propose the repository name, owner or organization, visibility, and delivery posture, defaulting visibility to private and the posture to `no-mistakes-prod-only`, then obtain the captain's explicit consent for those exact values; a stated default never replaces that consent.
Use `gh-axi` for the approved GitHub operation and consult its current help rather than relying on remembered flags.
After remote creation succeeds, clone it locally, add the registry entry, and initialize it according to its delivery mode.
After remote creation succeeds, clone it locally, add the registry entry, and initialize it according to its delivery posture.

For a purely `local-only` project, create a local Git repository under its unused `projects/<name>` path, add the registry entry, and make no GitHub call.
The captain's request to create that local project authorizes this local initialization, but it does not authorize an unmentioned remote repository.

## Initialize

Run no-mistakes initialization only for `no-mistakes` projects:
Run no-mistakes initialization only for `no-mistakes` and `no-mistakes-prod-only` projects:

```sh
cd projects/<name> && no-mistakes init && no-mistakes doctor
Expand Down
40 changes: 28 additions & 12 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,8 @@ jobs:
- run: bin/fm-lint.sh

# Deterministic proof that portable parallel shards + portable serial + Herdr
# equal the complete tests/*.test.sh inventory with no missing or duplicates.
# equal the complete tests/*.test.sh inventory with no missing or duplicates,
# and that the portable serial CI shards partition that serial lane exactly.
test-coverage:
name: Test coverage guard
runs-on: ubuntu-latest
Expand Down Expand Up @@ -104,13 +105,22 @@ jobs:

# Required portable serial remainder: watcher, lock, AFK, tmux, daemon,
# ambiguous, and other stateful tests. Real Herdr stays in tests-herdr.
# Split across separate runners so no two of these stateful scripts ever share
# a machine: each shard is still strictly serial in itself. Shard membership
# and the shard count both belong to bin/fm-test-run.sh, which refuses a lane
# whose "ofN" disagrees with it (docs/fm-test-portable-shards.md).
tests-portable-serial:
name: Behavior portable serial
name: Behavior portable serial ${{ matrix.shard }}
runs-on: ubuntu-latest
# Measured serial remainder is ~13 min wall without Herdr. Cap is a hang
# tripwire above observed p99 script cost and suite wall, not the expected
# healthy end (interim 25m full-suite slack reduced after sharding).
timeout-minutes: 20
# Measured whole remainder is ~19 min of serial work; the balanced shards
# are ~4.8 min each. Cap is a hang tripwire with roughly 3x margin, not the
# expected healthy end of the lane.
timeout-minutes: 15
strategy:
# Every shard reports so one failure never hides another shard's result.
fail-fast: false
matrix:
shard: [1, 2, 3, 4]
steps:
- uses: actions/checkout@v6
with:
Expand All @@ -133,18 +143,24 @@ jobs:
set -eu
npm install -g tasks-axi
tasks-axi --version
- name: Run portable serial remainder
- name: Run portable serial shard ${{ matrix.shard }}
env:
# job-total rather than a literal, so shrinking or growing the matrix
# without matching bin/fm-test-run.sh is refused instead of quietly
# leaving a shard of the required lane unrun.
FM_SERIAL_LANE: portable-serial-${{ matrix.shard }}of${{ strategy.job-total }}
FM_SERIAL_SHARD: ${{ matrix.shard }}
run: |
set -eu
mkdir -p "$RUNNER_TEMP/fm-test"
bin/fm-test-run.sh --lane portable-serial \
--json "$RUNNER_TEMP/fm-test/fm-test-timing-portable-serial.json"
- name: Upload portable serial timing artifact
bin/fm-test-run.sh --lane "$FM_SERIAL_LANE" \
--json "$RUNNER_TEMP/fm-test/fm-test-timing-portable-serial-${FM_SERIAL_SHARD}.json"
- name: Upload portable serial shard ${{ matrix.shard }} timing artifact
if: always()
uses: actions/upload-artifact@v4
with:
name: fm-test-timing-portable-serial
path: ${{ runner.temp }}/fm-test/fm-test-timing-portable-serial.json
name: fm-test-timing-portable-serial-${{ matrix.shard }}
path: ${{ runner.temp }}/fm-test/fm-test-timing-portable-serial-${{ matrix.shard }}.json
if-no-files-found: warn

# Required real-Herdr lane: pinned install, serial real-herdr-gated family,
Expand Down
10 changes: 8 additions & 2 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ data/ personal fleet records; LOCAL, gitignored as a whole
captain.md this home's domain-local captain preferences and working style; LOCAL, gitignored, canonical even if harness memory mirrors it, and updated with inspect-then-update
captain-shared.md main-authoritative shared captain preferences propagated read-only to secondmate homes; LOCAL, gitignored, owned by secondmate-provisioning
learnings.md fleet-local operational facts and gotchas; LOCAL, gitignored; dated, evidence-backed, curated, and updated with inspect-then-update - rewrite and prune rather than append forever, the same contract as captain.md; created lazily, absent until this home has a learning to store
projects.md thin fleet navigation registry; firstmate-private, parsed by fm-project-mode.sh (section 6)
projects.md thin fleet navigation registry recording each project's standing delivery posture; firstmate-private, parsed for mechanical sync and seeding by fm-project-mode.sh (section 6)
secondmates.md secondmate routing table; firstmate-private, maintained by fm-home-seed.sh (section 6)
<id>/brief.md per-task crewmate brief, or per-secondmate charter brief when kind=secondmate
<id>/report.md scout task deliverable, written by the crewmate; survives teardown
Expand Down Expand Up @@ -112,7 +112,7 @@ state/ volatile runtime signals; gitignored
.wake-queue durable queued wakes: epoch<TAB>seq<TAB>kind<TAB>key<TAB>payload
.afk durable away-mode flag; present = sub-supervisor may inject escalations (set by /afk, cleared on user return)
.watch.lock .wake-queue.lock watcher singleton and queue serialization locks
.claude-autoarm.lock .claude-autoarm-epoch .turnend-claude-blocks Claude Stop auto-arm single-flight, epoch, and guard-budget records; never touch
.claude-autoarm.lock .claude-autoarm-epoch .claude-autoarm-failure-notified .claude-autoarm-failure-alarmed .turnend-claude-blocks .turnend-claude-blocks.lock Claude Stop auto-arm single-flight, epoch, failure-episode, attended-alarm, guard-budget, and budget-lock records; never touch
.hash-* .count-* .stale-* .stale-since-* .paused-* .wedge-escalations-* .seen-* .hb-surfaced-* .last-* .heartbeat-streak watcher internals; never touch
.watch-triage.log watcher's absorbed-wake debug log (size-capped); never relied on, safe to delete
.last-watcher-beat watcher liveness beacon, touched every poll (including while absorbing benign wakes); guard scripts read it
Expand Down Expand Up @@ -258,6 +258,12 @@ Never both present a likely-enough solution and launch a parallel design exercis
A diagnostic request, report, recommendation, or implementation-ready finding is evidence, not authorization to change code.
Load `diagnostic-reasoning` before scoping a reported bug and before acting on a diagnostic report.

Resolve every ship task's concrete delivery mode and yolo posture at intake, and pass both explicitly to the brief, the spawn, and any scout promotion, which all refuse to guess.
A current explicit captain instruction wins; otherwise the project's registry entry is the captain's standing posture, and dropping below its rigor needs a reason you can state.
On a `no-mistakes-prod-only` project, classify the task's surface: internal-only tooling, automation, contributor or operator process, and release or submission work ships `direct-PR`, while product-facing, mixed, and uncertain work ships `no-mistakes`; never infer internal-only from file location or project name.
An unregistered project or absent registry resolves to `no-mistakes` with yolo off, and the registration gap goes to the captain.
Record the resulting mode, yolo, and the one-line reason for any deviation in the backlog item note.

At every intake, and whenever long validation, infrastructure or platform work, an external wait, or a blocker appears, firstmate must identify independently valuable user-facing proof or delivery paths, dispatch immediately every such path already authorized by the captain's original request or the accepted task criteria, and keep parallel-first decomposition to bounded independent outcomes rather than redundant planners, duplicate implementations, or competing product approaches or architectures.
The Selected delivery path and approval authority subsection exclusively owns standing `yolo` authority, and this parallel-first clause does not broaden it.
Identification may be silent and may find no material path, and identifying a path is never authorization to implement it, so raise an unauthorized path for a decision only when it is independently valuable to the requested outcome and could materially improve delivery or avoid meaningful delay or failure, never as speculative adjacent work.
Expand Down
7 changes: 4 additions & 3 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,8 @@ bin/fm-test-run.sh --family pure-contract-unit # ordinary family-scoped local
bin/fm-test-run.sh --changed # conservative changed-file-informed set (never silent full suite)
bin/fm-test-run.sh --proven-isolated --jobs 4 # explicit local parallel of the proven set only (default is serial)
bin/fm-test-run.sh --lane portable-serial # portable serial remainder (watcher/AFK/tmux/stateful)
bin/fm-test-run.sh --check-coverage # prove portable shards + serial + Herdr equal the full inventory
bin/fm-test-run.sh --list-lanes # discover exact lane names, including the current CI serial shards
bin/fm-test-run.sh --check-coverage # prove portable shards + serial + serial shards + Herdr equal the full inventory
bin/fm-test-run.sh --all # deliberate complete regression (optional local full walk; not no-mistakes Test)
bin/fm-test-isolation-proof.sh --list # proven parallel candidate set (Phase 2 owner)
bin/fm-test-isolation-proof.sh --jobs 4 --json /tmp/fm-isolation-proof.json # re-run concurrent isolation proof only
Expand All @@ -93,8 +94,8 @@ Its header and `--help` own the flags, family labels, lanes, and changed-file ma
Portable shard balance evidence lives in `docs/fm-test-portable-shards.md`.
Local no-mistakes Test stays intent-targeted and must not wire `commands.test` to `--all` or a `tests/*.test.sh` walk.
Family selection is the ordinary local path; `--all` is deliberate full regression only.
CI owns broad regression across required portable parallel shards, the portable serial lane, the Herdr lane, lint, invariants, the coverage guard, and stock macOS Bash compatibility in [`.github/workflows/ci.yml`](.github/workflows/ci.yml).
Use `bin/fm-test-run.sh --help` for lane names, `--jobs` rules, and required gate-skip flags when reproducing a lane locally.
CI owns broad regression across required portable parallel shards, the portable serial lane's separate-runner shards, the Herdr lane, lint, invariants, the coverage guard, and stock macOS Bash compatibility in [`.github/workflows/ci.yml`](.github/workflows/ci.yml).
Use `bin/fm-test-run.sh --list-lanes` for exact lane names and `--help` for `--jobs` rules and required gate-skip flags when reproducing a lane locally.
Discover tests by listing `tests/*.test.sh`: each is a self-contained bash script named `<subject>.test.sh`, and its header comment describes what it covers, so pass one to `bin/fm-test-run.sh` to focus on a subject with canonical timing output.
Tests that need a real optional backend or an explicit opt-in (real herdr/zellij/cmux smoke tests, the live Pi regression) skip themselves and print the tool or environment gate needed to enable them, so the portable suite remains safe on machines without those tools.
The [Herdr backend guide](docs/herdr-backend.md#destructive-lab-safety) owns the lane's isolation boundary, while [runtime backend verification](docs/verification/runtime-backends.md#herdr) owns active empirical evidence; live harness credential tests remain opt-in.
Expand Down
Loading
Loading