You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Commit c212ae9
Browse filesBrowse the repository at this point in the historyBrowse files
fix(bin): refuse a merge when a required check never reported
fm-pr-merge.sh built its GitHub refusals only from checks present in
statusCheckRollup, so a required check that never ran was simply absent and
the merge proceeded on the subset that reported, contradicting its own
"every required check green" claim.
The GitHub verify now reads the base branch's required contexts from the
forge itself - the classic branch protection summary on
GET repos/{o}/{r}/branches/{b} and the active ruleset rules on
GET repos/{o}/{r}/rules/branches/{b} - and refuses when a required context
has no entry in the same rollup, at the same head, that the merge is bound
to. Absence reads as unknown, never green. The required-set read joins the
existing refusal list, so a draft, a red check, and an unreported required
check are all reported together.
Could not read vs nothing required: both endpoints need only repository
read access. The admin-only GET .../branches/{b}/protection endpoint is
deliberately not used: it answers a non-admin token with the same 404 an
unprotected branch gets (observed live on kunchenguid/firstmate main with
this token), which would read a missing permission as "nothing required".
Any failed or malformed read of either source (auth, missing fine-grained
permission, rate limit, network, 404, unexpected shape) refuses the merge
with a line naming the unreadable source. The one exception is GitHub's
plan-gated 403 on the rules endpoint ("Upgrade to GitHub Pro or make this
repository public"), which already means "this repository has no branch
rules" for the merge-queue reader; that check moves into one shared helper
and the classic summary still decides for such a repository.
Attended waiver: --allow-missing <check-name> is the twin of --allow-red and
follows the same design and recording path: once, separate name argument,
waives only that exact unreported required check, still requires every
other required check reported and every check green, never waives an
unreadable required set, refused while the away-posture record exists, and
refused on GitLab. Merge-state BLOCKED policy is unchanged.
How this differs from the withdrawn kunchenguid#5353 (read from its diff):
- kunchenguid#5353 read the admin-only branches/{b}/protection endpoint and treated
its 404 as "no required checks", so for any non-admin token the required
set silently read as empty; this change reads the read-access branch
summary and treats every failure as unreadable.
- kunchenguid#5353 ignored rulesets; this change also reads required_status_checks
rules from the effective branch rules.
- kunchenguid#5353 made separate per-head REST reads of statuses and check-runs capped
at per_page=100 with no pagination; this change checks presence in the
same statusCheckRollup view the red-check gate already reads at the
verified head.
- kunchenguid#5353 stopped at the first unreadable read; this change reports it as one
refusal among all the others.
- kunchenguid#5353 also claimed kunchenguid#5345 (lock stealing) and changed 39 files, most
unrelated; this change is kunchenguid#5344 only.
Live proof, read-only (a gh wrapper refused every merge and mutating call):
- cli/cli#14474 (trunk requires 3 classic build contexts, none ran):
refused, naming build (macos-latest), build (ubuntu-latest),
build (windows-latest); with --allow-missing "build (macos-latest)" it
still refused, naming the other two.
- cli/cli#13665 (ran build (ubuntu-24.04-firewall) instead): refused,
naming build (ubuntu-latest).
- hashicorp/terraform#39262 (ruleset-required checks absent): refused,
naming Code Consistency Checks, End-to-end Tests, Race Tests, Unit Tests.
- cli/cli#14485 (all required reported and green): verified; the wrapper
blocked the merge call and the pull request read back open.
Fixeskunchenguid#5344
Copy file name to clipboardExpand all lines: .agents/skills/afk/SKILL.md
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -91,7 +91,7 @@ afk changes how the captain is informed and what happens at a captain-owned deci
91
91
A PR ready for merge keeps the merge authority from `AGENTS.md` section 7, and a needs-decision finding keeps the `ask-user-authority` policy; anything requiring the captain still waits for the captain's explicit word.
92
92
While the away-posture record exists, any pull request green at its live head may merge under away authority; which one the captain's words meant is the away session's reading, and a merge the words do not call for holds for the return.
93
93
Away authority never releases a captain hold, and it expires when the away record is archived.
94
-
`--allow-red`remains attended-only and is refused while the record exists.
94
+
`--allow-red`and `--allow-missing` remain attended-only and are refused while the record exists.
95
95
A merge under away authority must be synchronous; `fm-pr-merge.sh` refuses auto-merge and any GitHub queue state that cannot prove an immediate merge while the record exists.
96
96
The same gates bind whichever actor performs the action: on Pi the parked main's standing authority relocates to the supervision branch, which meets exactly these rules, and the spend cap recorded at entry is enforced by `fm-spawn.sh` for both actors while the record exists.
97
97
The captain's away words are their explicit instruction given before leaving, recorded verbatim and acted on by the away session's judgment at the moment an event makes them relevant; the words cover nothing they do not say, are never applied by analogy, and die at archive.
Copy file name to clipboardExpand all lines: AGENTS.md
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -363,7 +363,7 @@ The path's worker, automated gates, and captain approval remain authoritative:
363
363
364
364
Delivery mode and `yolo` are orthogonal.
365
365
`yolo` governs merge authority only: with it off, the captain approves every PR merge and every local-only landing; with it on, firstmate merges green, in-scope work itself.
366
-
Never merge a red PRunder either setting unless a current explicit captain instruction names the single GitHub check waived through `fm-pr-merge.sh --allow-red`; that attended-only waiver still requires every other check green.
366
+
Never merge a red PR, or one with a required check that has not reported, under either setting unless a current explicit captain instruction names the single GitHub check waived through `fm-pr-merge.sh --allow-red` or `--allow-missing`; each attended-only waiver still requires every other check green.
367
367
Destructive, irreversible, and security-sensitive merges still escalate.
368
368
Without a current explicit captain instruction that states the concrete merge, the green default stands, and standing `yolo` cannot authorize a red merge; section 1 owns when such an instruction overrides a Firstmate-written standing rule within its exact scope.
369
369
Load `ask-user-authority` before deciding any ask-user finding; the implementation worker never answers its own finding.
Copy file name to clipboardExpand all lines: bin/fm-branch-prompt.sh
+1-1Lines changed: 1 addition & 1 deletion
Original file line number
Diff line number
Diff line change
@@ -110,7 +110,7 @@ Away (the record exists): the wake message ends with a `POSTURE: AWAY` tail carr
110
110
The record is the captain's away words, recorded verbatim: the explicit instruction the captain gave before leaving, and the whole mandate.
111
111
No script parses them; you read them at the tail of every wake, decide by your own judgment whether the event in front of you is the moment they name, and act on them only through the guarded scripts under MAIN's standing authority - never more than MAIN could do attended - which enforce what a script can check without reading words:
112
112
- `bin/fm-pr-merge.sh`: a merge the words call for proceeds when the pull request is green at its live head, synchronously, under the record lock; which pull request the words meant is your reading, and any green merge is mechanically permitted while the record exists.
113
-
A red pull requestis never merged while away, whatever the words say, and `--allow-red` is refused under the record: a merge the words want past a red check holds for the return.
113
+
A red pull request, or one with a required check that has not reported, is never merged while away, whatever the words say, and `--allow-red` and `--allow-missing` are refused under the record: a merge the words want past a red or unreported check holds for the return.
114
114
- `bin/fm-spawn.sh`: work the words explicitly call for is dispatched within the record's spend cap, from a queued backlog item - one already queued, or one you file yourself for exactly that step under the `backlog` lease, writing its brief intent from the captain's words and a backlog note citing them; filing the item the captain asked for is not inventing work, and anything the words do not call for is.
115
115
- `bin/fm-send.sh` and `bin/fm-control.sh`: a run the words say to abort or a worker the words say to steer is steered, as in any posture.
116
116
- `bin/fm-send.sh --resolve-key`: a decision the words pre-answer is answered with the captain's own answer, and every other decision only as the ask-user-authority policy at the end of this prompt lets firstmate decide; a finding it says to escalate is reported with verdict captain and left for the return.
0 commit comments