The Go and the Node build modules, ssh-client on the SDK's key keeper, and gitea's read-only builder accounts (design 47 R4c-3) #389

Merged
mesh-tools merged 25 commits from feat/r4c3-build-modules into main 2026-10-20 21:43:14 +00:00
Member

Design 47 R4c-3, its second delivery, one group with mesh-delivery's pull request on the same branch name. The build modules run dark: nothing calls them before the builder and checker releases, and the sandbox (issue 1309) comes last in R4c (ADR 0465 §5).

  • mesh-build-go (new): its own account and 0700 home, user-namespaces, packages go git openssh postgresql; recipe go1.27.1 and postgres 18, the toolchain written to toolchains and every step refused on another version, health unhealthy while refusing (issue 1483; ADR 0469 §1, ADR 0470 §4); forge key kind builder and ssh files from forge-account (1484; ADR 0466 §2 §4); tools fetch (1485), test unit level (1290) and integration level with a throwaway store and bus (1486; ADR 0470), digest (1291), build (1487); long steps answer an id and end on steps (ADR 0469 §2); event toolchain.reported on stream toolchains-go.
  • mesh-build-node (new): Node v26.10.0 with typescript, esbuild, @types/node, @novox/mesh-sdk and nats from its own lock, shipped as an archive (1488; ADR 0469 §4); fetch with a module without a lock refused by name (1489; ADR 0469 §5), test (1491), build at build-agent's depth (1490); stream toolchains-node.
  • ssh-client takes the key keeper from mesh-sdk go/forgekey (1480).
  • gitea: nox-builder in team builders, read-only, for the build modules' entries; reads mesh-build-go.keys and mesh-build-node.keys (1481, 1482; ADR 0466 §3).
  • checks/sshdir and checks/owned judge a runs-as module's own placed directory as its own.

Pins mesh-sdk 36d6f774 (#51, delivered). Try build-1792531166069740713 passed at this head; the real-toolchain integration tests skip where the check's image lacks postgres or node and are proven live on a build node after the delivery (1486/AC6, 1490/AC4). After the delivery the lead assigns both build modules to the four build nodes (ADR 0469 §6).

Reviewed-by: review-r4c3@shanks at bcee61edf7

Design 47 R4c-3, its second delivery, one group with mesh-delivery's pull request on the same branch name. The build modules run dark: nothing calls them before the builder and checker releases, and the sandbox (issue 1309) comes last in R4c (ADR 0465 §5). - mesh-build-go (new): its own account and 0700 home, user-namespaces, packages go git openssh postgresql; recipe go1.27.1 and postgres 18, the toolchain written to `toolchains` and every step refused on another version, health unhealthy while refusing (issue 1483; ADR 0469 §1, ADR 0470 §4); forge key kind builder and ssh files from forge-account (1484; ADR 0466 §2 §4); tools fetch (1485), test unit level (1290) and integration level with a throwaway store and bus (1486; ADR 0470), digest (1291), build (1487); long steps answer an id and end on `steps` (ADR 0469 §2); event toolchain.reported on stream toolchains-go. - mesh-build-node (new): Node v26.10.0 with typescript, esbuild, @types/node, @novox/mesh-sdk and nats from its own lock, shipped as an archive (1488; ADR 0469 §4); fetch with a module without a lock refused by name (1489; ADR 0469 §5), test (1491), build at build-agent's depth (1490); stream toolchains-node. - ssh-client takes the key keeper from mesh-sdk go/forgekey (1480). - gitea: nox-builder in team builders, read-only, for the build modules' entries; reads mesh-build-go.keys and mesh-build-node.keys (1481, 1482; ADR 0466 §3). - checks/sshdir and checks/owned judge a runs-as module's own placed directory as its own. Pins mesh-sdk 36d6f774 (#51, delivered). Try build-1792531166069740713 passed at this head; the real-toolchain integration tests skip where the check's image lacks postgres or node and are proven live on a build node after the delivery (1486/AC6, 1490/AC4). After the delivery the lead assigns both build modules to the four build nodes (ADR 0469 §6). Reviewed-by: review-r4c3@shanks at bcee61edf709caffaa4b709dd2b7c887f01446c6
mesh-tools added 25 commits 2026-10-20 21:21:49 +00:00
Skip, loudly, a build module's real-toolchain test where the check's image lacks the tool; it is proven live on a build node (issues 1486, 1490)
mesh/repo-check head bcee61edf709 merged into trunk 06d5dc98303a — pass: its merge-check.sh passed, each part in its toolchain: merge-check.sh (go), merge-…
mesh/merge-gate head bcee61edf709 merged into trunk 06d5dc98303a — pass: group feat/r4c3-build-modules composed: every machine composes with the change as …
mesh/delivery failed: its walk failed, carrying its own commit: a gate on a first machine (what it carried put back), a build, a machine
mesh/delivery-group group feat/r4c3-build-modules failed: a member failed
bcee61edf7
Author
Member

Delivery novox/mesh-catalog@bcee61edf709 — failed since 2026-10-20T21:47:09Z

Delivery plan — builds brother, gitea, messenger, ssh-client, new: modules/mesh-build-go, modules/mesh-build-go/cmd/mesh-build-go/testdata/repos/build, modules/mesh-build-node → ace, g14, novox, shanks; no bus step

  • tier 0: brother, gitea, messenger, ssh-client
  • ace: receives ssh-client
  • g14: receives ssh-client
  • novox: receives gitea, messenger, ssh-client
  • shanks: receives brother, ssh-client
  • gitea provides npm-package-registry, git, gitea-read, forge-account: its consumers are sent again after it
  • gitea keeps data (ADR 0233): what it holds is backed up before it moves
  • ssh-client keeps data (ADR 0233): what it holds is backed up before it moves
  • grants step: if this changes what the bus's user list says (a new tool, subject or user), novox is sent that list alone, every build there kept, before brother, ssh-client is judged on its first machine

Group feat/r4c3-build-modules: novox/mesh-catalog@bcee61edf7, novox/mesh-delivery@a5da6079de

  • composed together: pass — every machine composes with the change as it did without (4 of 4 compose)

Transitions

  • 2026-10-20 21:21 (new) → proposed (announced): novox/mesh-catalog#389's head announced
  • 2026-10-20 21:26 proposed → checked (checked): a verdict names this commit and the trunk's head as its trunk commit
  • 2026-10-20 21:26 checked → ready (accepted): the gate passed or warned, and the repository's own check did not fail
  • 2026-10-20 21:28 ready → proposed (trunk moved): out of date: judged against trunk e2e990a0eb, the trunk is now 06d5dc98303a; judged again on a recheck or when it is merged
  • 2026-10-20 21:30 proposed → checked (checked): a verdict names this commit and the trunk's head as its trunk commit
  • 2026-10-20 21:30 checked → ready (accepted): the gate passed or warned, and the repository's own check did not fail
  • 2026-10-20 21:45 ready → published (merged): on the trunk its modules follow: merged there, and its walk opened — or nothing for a walk to move
  • 2026-10-20 21:45 published → delivering (go): its walk started: let go by this owner in its group's order, by a person, or on the controller's own path — not a failed walk that carried a later commit for it, after which it waits for a walk of its own commit
  • 2026-10-20 21:47 delivering → failed (failed): its walk failed, carrying its own commit: a gate on a first machine (what it carried put back), a build, a machine

The commit's note under refs/notes/mesh-plan keeps every transition: git log --notes=mesh-plan.

<!-- mesh-delivery:view --> **Delivery** `novox/mesh-catalog@bcee61edf709` — **failed** since 2026-10-20T21:47:09Z **Delivery plan** — builds brother, gitea, messenger, ssh-client, new: modules/mesh-build-go, modules/mesh-build-go/cmd/mesh-build-go/testdata/repos/build, modules/mesh-build-node → ace, g14, novox, shanks; no bus step - tier 0: brother, gitea, messenger, ssh-client - ace: receives ssh-client - g14: receives ssh-client - novox: receives gitea, messenger, ssh-client - shanks: receives brother, ssh-client - gitea provides npm-package-registry, git, gitea-read, forge-account: its consumers are sent again after it - gitea keeps data (ADR 0233): what it holds is backed up before it moves - ssh-client keeps data (ADR 0233): what it holds is backed up before it moves - grants step: if this changes what the bus's user list says (a new tool, subject or user), novox is sent that list alone, every build there kept, before brother, ssh-client is judged on its first machine **Group** `feat/r4c3-build-modules`: novox/mesh-catalog@bcee61edf709, novox/mesh-delivery@a5da6079de01 - composed together: pass — every machine composes with the change as it did without (4 of 4 compose) **Transitions** - 2026-10-20 21:21 (new) → proposed (announced): novox/mesh-catalog#389's head announced - 2026-10-20 21:26 proposed → checked (checked): a verdict names this commit and the trunk's head as its trunk commit - 2026-10-20 21:26 checked → ready (accepted): the gate passed or warned, and the repository's own check did not fail - 2026-10-20 21:28 ready → proposed (trunk moved): out of date: judged against trunk e2e990a0ebdb, the trunk is now 06d5dc98303a; judged again on a recheck or when it is merged - 2026-10-20 21:30 proposed → checked (checked): a verdict names this commit and the trunk's head as its trunk commit - 2026-10-20 21:30 checked → ready (accepted): the gate passed or warned, and the repository's own check did not fail - 2026-10-20 21:45 ready → published (merged): on the trunk its modules follow: merged there, and its walk opened — or nothing for a walk to move - 2026-10-20 21:45 published → delivering (go): its walk started: let go by this owner in its group's order, by a person, or on the controller's own path — not a failed walk that carried a later commit for it, after which it waits for a walk of its own commit - 2026-10-20 21:47 delivering → failed (failed): its walk failed, carrying its own commit: a gate on a first machine (what it carried put back), a build, a machine The commit's note under `refs/notes/mesh-plan` keeps every transition: `git log --notes=mesh-plan`.
Author
Member

Merge check at bcee61ed
Judged: head bcee61edf709 merged into trunk e2e990a0ebdb; read beside it: mesh-controller f29d193ddbc1, mesh-controller-main f29d193ddbc1, mesh-host ce1b97ad973d, mesh-tools 18260ce9beca

  • mesh/merge-gate: PASS — every machine composes with the change as it did without (4 of 4 compose) (modules: brother, gitea, messenger, ssh-client, new:modules/mesh-build-go, new:modules/mesh-build-go/cmd/mesh-build-go/testdata/repos/build, new:modules/mesh-build-node)
  • mesh/repo-check: PASS — its merge-check.sh passed, each part in its toolchain: merge-check.sh (go), merge-check-typescript.sh (typescript)

Delivery plan — builds brother, gitea, messenger, ssh-client, new: modules/mesh-build-go, modules/mesh-build-go/cmd/mesh-build-go/testdata/repos/build, modules/mesh-build-node → ace, g14, novox, shanks; no bus step

  • tier 0: brother, gitea, messenger, ssh-client
  • ace: receives ssh-client
  • g14: receives ssh-client
  • novox: receives gitea, messenger, ssh-client
  • shanks: receives brother, ssh-client
  • gitea provides npm-package-registry, git, gitea-read, forge-account: its consumers are sent again after it
  • gitea keeps data (ADR 0233): what it holds is backed up before it moves
  • ssh-client keeps data (ADR 0233): what it holds is backed up before it moves
  • grants step: if this changes what the bus's user list says (a new tool, subject or user), novox is sent that list alone, every build there kept, before brother, ssh-client is judged on its first machine
  • read by no module's build: .gitignore, checks/owned/main.go, checks/owned/main_test.go, checks/sshdir/main.go, checks/sshdir/main_test.go, modules/brother/README.md, modules/brother/cmd/brother/pin_test.go, modules/brother/cmd/brother/testdata/pin/ecdsa.pem, modules/brother/cmd/brother/testdata/pin/rsa.pem, modules/messenger/cmd/messenger/offer_unsent_test.go, modules/ssh-client/cmd/ssh-client-tools/helpers_test.go, modules/ssh-client/cmd/ssh-client-tools/keeper_test.go, modules/ssh-client/cmd/ssh-client-tools/keykeeper_bus_test.go, modules/ssh-client/cmd/ssh-client-tools/keykeeper_test.go, modules/ssh-client/cmd/ssh-client-tools/ssh_test.go, modules/ssh-client/cmd/ssh-client-tools/sweep_test.go

Run by the build seat on ace as build-1792531316007664800 (builds --log build-1792531316007664800).

✔ the verdict heard while a 'building' write still waits its turn: the 'building' is never written (0.673876ms)
✔ a start heard after the verdict writes nothing (0.626195ms)
✔ a start from before the check now pending (a run before a recheck, the stream's history) writes nothing (0.80918ms)
✔ an old run's verdict redelivered after a recheck's pending is not written over it (1.124312ms)
[gitea] novox/hq@a6b08de8: the verdict of build-1791680941000000000 is an older run's than the check the forge holds pending; not written
[gitea] novox/hq@a6b08de8: the verdict of build-1791680941000000000 is an older run's than the check now pending; not written
✔ an old run's verdict in flight when the recheck comes lands before the recheck's pending (2.511507ms)
✔ a rechecked head says where its new run is: building on which machine (0.614023ms)
✔ the recheck's own verdict is written, even asked a little before the pending by another machine's clock (0.562206ms)
✔ after a restart, an old run's verdict is weighed against the check the forge's history holds open (0.636395ms)
✔ a recheck the forge does not take fails its caller, and the head is as it was (0.533953ms)
✔ the status tool writes the merge check's pending through the writer, and the mesh's other statuses as they were (6.947585ms)
✔ when a check was asked is read from its id; the opening of the check now pending from the gate's history (1.585437ms)
✔ a head this process did not announce (it restarted) is said only while the forge holds its gate pending (0.294253ms)
✔ a repository as the mesh clones it is told from another (0.243678ms)
✔ gitea_api refuses the forge's administration, a branch's protection and the merge check's status, and sends nothing (7.724937ms)
✔ gitea_api refuses a file written to the default branch or one a rule guards, and writes one on a branch of its own (56.549809ms)
✔ a protection rule covers a branch as the forge decides it: classes, alternatives, a plain name in any case (issue 539) (25.224196ms)
✔ gitea_api still writes what an author writes (8.681652ms)
✔ gitea_branch_protection_set only strengthens (15.331209ms)
✔ gitea_merge_pull_request merges only a head whose required statuses all succeeded, and only that head (42.109323ms)
✔ gitea_merge_pull_request refuses a verdict judged against an earlier trunk, and asks the check once (138.086757ms)
✔ gitea_merge_pull_request merges only the head it is named, and refuses one that is not the head (15.870321ms)
✔ gitea_merge_pull_request is loud when the forge merged a head other than the one it was handed (14.83013ms)
✔ gitea_merge_pull_request says the merge happened when reading back what landed fails (25.406408ms)
✔ gitea_merge_pull_request reads back a fast-forward, and says it cannot read back a squash or a rebase (54.230153ms)
✔ gitea_delete_repo deletes only the tools' own user's repository, unguarded, untouched for 30 days, named in full (20.210291ms)
✔ gitea_api sends the path it judged, and refuses moving a pull request's base (4.163799ms)
✔ gitea_merge_pull_request merges only into a branch whose protection requires the checks (6.956591ms)
✔ a rule named for a branch is not made weaker than the glob rule that guards it now (12.722542ms)
✔ a repository owner or name is never another path (0.230553ms)
✔ the judges, without a forge (0.345048ms)
✔ main's protection is never weakened in its push or its merge whitelist (issue 948, ADR 0398 §2) (0.242074ms)
✔ gitea_api never acts as another user: sudo, in any case, and any query key it does not send are refused (1.606136ms)
✔ gitea_api never approves a pull request nor requests changes: those are the operator's (2.179522ms)
✔ no tool's caller text becomes another path or another user: `..` and `?sudo=` are refused before the forge (4.526809ms)
✔ gitea_merge_pull_request merges a verdict that read siblings only with its group passed and each head approved (82.5001ms)
✔ gitea_merge_pull_request refuses a head the Approve did not name (20.031555ms)
✔ a group of two merges in one pass: the sibling's merge of the composed head does not stop the member's merge (issue 1049) (16.236359ms)
✔ gitea_create_repo has no owner argument and posts only to the tools' own user's repositories (1124/AC8) (36.200417ms)
✔ the tools' team cannot create in the organisation and its token holds no write:organization (1124/AC8) (0.368953ms)
✔ no ready mark, trusted ready-authors setting or approval-by-mark rule is left in the module (19.93341ms)
✔ every page of a pull request's files is read, though the forge caps a page at fifty (40.520349ms)
✔ a pass asks only the repositories that moved since the last look, every one before the first (0.760488ms)
✔ the directories above a merge's files that hold a module at the commit are said, the root never (16.166717ms)
✔ a lookup the forge refuses is thrown, not read as no module (5.854354ms)
✔ a renamed file is said under its old name too, as gone (novox/hq ADR 0267) (6.669723ms)
✔ a new head beyond the newest 20 open pull requests is announced, exactly once (91.663947ms)
✔ a pass pages until it reaches back past its floor, and no further (25.263639ms)
✔ gitea_branch_protection_get answers every rule, read with the administrator account the tools' token cannot read with (22.189136ms)
✔ gitea_branch_protection_get answers the rule for a branch, null when it has none (15.519432ms)
✔ gitea_branch_protection_set still gets the forge's refusal, as the tools' account (4.623983ms)
✔ the statuses asked for replace the rule's, and an empty list requires none (5.928371ms)
✔ a new rule refuses direct pushes unless asked; an administrator's override only when said (0.391555ms)
✔ main's body always refuses pushes and lets only the tools' account merge, whatever is asked (0.842012ms)
✔ another branch's body carries no merge whitelist (0.291518ms)
✔ the rule main is put right in the forge's own words: the body a setup sends carries no status checks of its own (0.347553ms)
✔ each open pull request's new head is announced once, and nothing closed or merged (15.400989ms)
✔ a verdict is the head commit's status; an error is the forge's error, never a success (1.288359ms)
✔ each layer is its own status: the gate with the modules it judged, the repository's own check beside it (0.877087ms)
✔ no verdict sets warning on a required check; only a person's decision fails (1.236552ms)
✔ a commit status is set on the commit, under the merge check's context (38.055751ms)
✔ a change plan is the gate's result: said on the status and, when it builds something, as a comment (0.456938ms)
✔ a head announced is pending in the build queue, since the local time it was announced (0.305143ms)
✔ a composed verdict sets every member's gate at its own head, naming its trunk and the group (0.4206ms)
✔ a member's own verdict with a composed gate layer leaves the gate to the composed verdict, in either order (0.477336ms)
✔ the vault's token is used, a setting of it is ignored and said once, without its value (2.073704ms)
[gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 at bbbbbbbbbbbb, it is now at dddddddddddd: out of date, nothing run (novox/hq ADR 0382)
[gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was closed unmerged: out of date, nothing run (novox/hq ADR 0382)
[gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 merged onto cccccccccccc, its main is now eeeeeeeeeeee: out of date, nothing run (novox/hq ADR 0382)
[gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head bbbbbbbbbbbb onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382)
[gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head bbbbbbbbbbbb onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382)
[gitea] novox/mesh-host's main moved from 444444444444 to 333333333333: 0 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323)
[gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head bbbbbbbbbbbb onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382)
[gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head dddddddddddd onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382)
✔ both statuses name the siblings the verdict read, keeping the verdict word and the start of its reason within 140 characters (1.70911ms)
✔ a verdict that could not learn its siblings says so on the status and in the comment, and names none (0.284845ms)
✔ a verdict without siblings is said exactly as before (an older controller) (0.577415ms)
✔ the siblings a verdict names are kept per member, replaced by its next verdict, and removed by one that read none (0.694935ms)
✔ a sibling's new head puts both statuses of the member back to pending, with the reason, and runs nothing (1.470762ms)
✔ a sibling closed unmerged puts the member's verdict out of date (0.333426ms)
✔ a move of the sibling's base puts it out of date, naming both commits (0.448382ms)
✔ the sibling's own merge of the head read onto the base read does not, in either order of the two merges (0.49001ms)
✔ a merge of another head, or onto another base, is a move (0.574228ms)
✔ only the members whose verdict names the sibling are touched, and a member that moved on is dropped (0.514476ms)
✔ a trunk that moved tells the siblings' weighing; one first seen does not (0.439265ms)
✔ the group rule names every missing thing: the group status at each head read, and each head the Approve does not cover (0.949403ms)
✔ a merged or closed member's entry is dropped, so a sibling's later push never re-pends its merged head (0.178946ms)
✔ without the composed verdict's siblings, a sibling's own merge of its new head is a move (the pin of issue 1049) (0.206528ms)
✔ a composed verdict names the siblings of each member at the heads and base commits it composed, so a sibling's own merge of its new head is no move (issue 1049) (0.561524ms)
✔ a composed verdict keeps nothing for a member it cannot name, and a group of one is none (issue 1049) (0.172504ms)
✔ a consumer that asks nothing, or write, publishes: the package team (1.587581ms)
✔ a consumer that asks to read joins the readers, who write no package (0.465544ms)
✔ a reader is made, put on the readers team, and taken off the package team (0.594426ms)
✔ a publisher is made and put on the package team, as before (0.253105ms)
✔ first start: mints with the admin account, keeps the token at 0600, asks for the tools' scopes only (40.927854ms)
✔ second start: reuses the kept token, mints nothing (21.491828ms)
✔ the forge rejects the kept token (its data was restored): minted afresh, once, and the call goes through (26.479224ms)
✔ a token kept with write:admin by an earlier build is minted again without it at the next start, and the forge drops the old one (26.554943ms)
✔ a kept token lacking a scope the tools need: the forge refuses the call for the scope, the token is re-minted with the whole list, and the call goes through (24.191567ms)
✔ the kept file is gone but the forge still holds a token by that name: replaced, not refused (22.614485ms)
✔ concurrent first calls share one mint (11.898474ms)
✔ two tokens hold the name (two mints raced): both are deleted by their id, and one fresh token is minted (15.558485ms)
✔ two processes on one kept file, both without a token, mint once: the second waits for the first and reuses it (102.545339ms)
✔ a lock left by a process that died mid-mint is taken over, not waited on for ever (7.280613ms)
✔ the admin account is refused: said plainly, nothing kept, and the next call fails the same way rather than crashing (15.317252ms)
✔ one process shares one source per kept file — the watcher and the tools never renew against each other (0.69218ms)
✔ a second process finds the token the first renewed, and reuses it instead of minting over it (20.73678ms)
✔ a configured token wins, and is reported rather than minted over when the forge rejects it (2.229076ms)
✔ nothing to mint with and no token: the client says what is missing (0.168486ms)
[gitea] no tools — no Gitea token, and nothing to mint one with — set MESH_GITEA_TOKEN, or MESH_GITEA_ADMIN_USER, MESH_GITEA_ADMIN_PASSWORD_FILE, MESH_GITEA_STATE_DIR
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-TmYUD6/state/token
✔ the tools register once there is a way to a token, and the first call mints it (24.522238ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-X9zyZA/state/token
✔ a pull request can be closed, read and cleaned up through the tools (35.463492ms)
[gitea] no token kept — minting one
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-9bjpKu/state/token
✔ the tools' token is minted for an account of their own, which is no administrator and writes through its team (68.89423ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-Nn9BcN/state/token
✔ with the tools' token, the forge writes a status and refuses a protection edit — the forge itself, not a guard (49.273565ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-xpgjqB/state/token
✔ what a base's protection asks is read from the branch, which the tools' account may read, not from the rules' list it may not (41.78221ms)
[gitea] the kept token was minted with other scopes than the tools take now — minting one with them
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-hZGZQx/state/token
[gitea] deleted 1 token(s) named "mesh-tools" the admin account "mesh-admin" held: the tools act as "mesh-tools" now
✔ the administrator's token from before goes: a kept admin token is minted again for the tools' account, and the forge drops the old one (39.365941ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-hq4TgR/state/token
✔ a tools' account someone made an administrator is made a plain account again at the next mint (33.825116ms)
✔ the tools never act as the administrator: MESH_GITEA_TOOLS_USER naming it is refused (0.661562ms)
✔ the manifest hands the tools their account, and the Go forge bundle holds no administrator password (0.784634ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-s6xPDn/state/token
✔ a repository check said as a warning on a head without merge-check.sh reads the base's protection from the branch (39.068132ms)
[gitea] no token kept — minting one
✔ a mint that fails leaves the administrator's old token in place: the tools are never left without one (27.46267ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-91qJ35/state/token
[gitea] FAILED to delete the token(s) named "mesh-tools" the admin account "mesh-admin" holds — tried again at the next start: Gitea DELETE /users/mesh-admin/tokens/902 (named mesh-tools): 500 {"message":"the forge is not well"}
✔ an old token that cannot be deleted after the mint is said, the new token kept, and deleted at the next start (41.855937ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-ILaYdx/state/token
✔ a team another process made between the look and the create is found, not a failure (37.23036ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-TzAjFI/state/token
✔ setting the tools' account up puts main's rule right in every repository: no push, only the tools' account merges (issue 948) (36.070723ms)
[gitea] no token kept — minting one
[gitea] the forge already holds a token named "mesh-tools" — replacing it
[gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-Vb5xpb/state/token
✔ a glob rule covering main keeps its statuses when main is given a rule of its own name (issue 948, review round 1) (35.262016ms)
✔ a start with the token kept still puts main's rules right: the module's start asks for it each time (issue 948, review round 1) (12.523075ms)
[gitea] novox/mesh-host's main moved from a2c2c35bbbbb to d28ca95ccccc: 25 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323)
[gitea] novox/mesh-host's main moved from d28ca95ccccc to ffffffffffff: 0 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323)
[gitea] novox/mesh-host: whether a trunk moved could not be weighed, so it is weighed again on the next pass — the forge is away
[gitea] novox/mesh-host's main moved from a2c2c35bbbbb to d28ca95ccccc: 0 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323)
[gitea] novox/mesh-controller's feat/57-config-and-provisioning moved from eeeeeeeeeeee to d28ca95ccccc: 1 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323)
✔ both statuses say the head and the trunk commit the verdict judged, first, whatever the summary's length (1.639098ms)
✔ a trunk's move puts an open head's merge check out of date, naming both commits, unless a check is on its way (1.811421ms)
✔ a push to a trunk puts every open pull request into it out of date — twenty-five of them — and none into another (3.116102ms)
✔ a trunk that cannot be read is weighed again on the next pass, never recorded half (0.375755ms)
✔ the trunk's move takes its turn after a verdict in flight, and weighs what the forge holds then (0.46841ms)
✔ a verdict judged against a trunk newer than the pass's first read is not put out of date (0.289444ms)
✔ a verdict that landed out of date keeps its account on the pull request (0.246223ms)
✔ a release branch's move puts every open pull request into it out of date, as a trunk's does (ADR 0358 §5) (0.434195ms)
✔ a signed event is published on the bus and acted on once (66.171427ms)
✔ an unsigned event, or one whose signature does not verify, is refused and published nowhere (34.611715ms)
✔ an event and the poll seeing the same head announce it once (0.352321ms)
✔ each forge event is named in the module's stream and trimmed (0.493707ms)
✔ the webhook is made a system webhook, which the forge sends every repository's events to (1.258102ms)
✔ default webhooks left at the receiver by an earlier start are replaced by one system webhook (1.025786ms)
✔ a repository's copy of a default webhook at the receiver is deleted, on every page, and said (3.423899ms)
✔ a forge that makes no system webhook is said, never taken as heard (0.61255ms)
✔ the receiver tells what it verified and what it refused (7.784008ms)
✔ a forge that never delivers is said loudly once, and unhealthy, when the poll finds what no event said (0.923645ms)
✔ a forge whose events stop after one delivery is said loudly once per silent spell, and refusals are unhealthy (0.4417ms)
✔ without a receiver by configuration the polls alone watch, healthy; a receiver that failed is unhealthy (0.310163ms)
✔ the polls look every 30 s until events are heard, every five minutes while they are, and 30 s again on a miss (0.194496ms)
✔ a pull request's edit event carries its description, and no other pull request event does (issue 1079) (0.220324ms)
ℹ tests 163
ℹ suites 0
ℹ pass 163
ℹ fail 0
ℹ cancelled 0
ℹ skipped 0
ℹ todo 0
ℹ duration_ms 768.572461
**Merge check** at `bcee61ed` Judged: head `bcee61edf709` merged into trunk `e2e990a0ebdb`; read beside it: mesh-controller `f29d193ddbc1`, mesh-controller-main `f29d193ddbc1`, mesh-host `ce1b97ad973d`, mesh-tools `18260ce9beca` - `mesh/merge-gate`: **PASS** — every machine composes with the change as it did without (4 of 4 compose) (modules: brother, gitea, messenger, ssh-client, new:modules/mesh-build-go, new:modules/mesh-build-go/cmd/mesh-build-go/testdata/repos/build, new:modules/mesh-build-node) - `mesh/repo-check`: **PASS** — its merge-check.sh passed, each part in its toolchain: merge-check.sh (go), merge-check-typescript.sh (typescript) **Delivery plan** — builds brother, gitea, messenger, ssh-client, new: modules/mesh-build-go, modules/mesh-build-go/cmd/mesh-build-go/testdata/repos/build, modules/mesh-build-node → ace, g14, novox, shanks; no bus step - tier 0: brother, gitea, messenger, ssh-client - ace: receives ssh-client - g14: receives ssh-client - novox: receives gitea, messenger, ssh-client - shanks: receives brother, ssh-client - gitea provides npm-package-registry, git, gitea-read, forge-account: its consumers are sent again after it - gitea keeps data (ADR 0233): what it holds is backed up before it moves - ssh-client keeps data (ADR 0233): what it holds is backed up before it moves - grants step: if this changes what the bus's user list says (a new tool, subject or user), novox is sent that list alone, every build there kept, before brother, ssh-client is judged on its first machine - read by no module's build: .gitignore, checks/owned/main.go, checks/owned/main_test.go, checks/sshdir/main.go, checks/sshdir/main_test.go, modules/brother/README.md, modules/brother/cmd/brother/pin_test.go, modules/brother/cmd/brother/testdata/pin/ecdsa.pem, modules/brother/cmd/brother/testdata/pin/rsa.pem, modules/messenger/cmd/messenger/offer_unsent_test.go, modules/ssh-client/cmd/ssh-client-tools/helpers_test.go, modules/ssh-client/cmd/ssh-client-tools/keeper_test.go, modules/ssh-client/cmd/ssh-client-tools/keykeeper_bus_test.go, modules/ssh-client/cmd/ssh-client-tools/keykeeper_test.go, modules/ssh-client/cmd/ssh-client-tools/ssh_test.go, modules/ssh-client/cmd/ssh-client-tools/sweep_test.go Run by the build seat on ace as `build-1792531316007664800` (`builds --log build-1792531316007664800`). ``` ✔ the verdict heard while a 'building' write still waits its turn: the 'building' is never written (0.673876ms) ✔ a start heard after the verdict writes nothing (0.626195ms) ✔ a start from before the check now pending (a run before a recheck, the stream's history) writes nothing (0.80918ms) ✔ an old run's verdict redelivered after a recheck's pending is not written over it (1.124312ms) [gitea] novox/hq@a6b08de8: the verdict of build-1791680941000000000 is an older run's than the check the forge holds pending; not written [gitea] novox/hq@a6b08de8: the verdict of build-1791680941000000000 is an older run's than the check now pending; not written ✔ an old run's verdict in flight when the recheck comes lands before the recheck's pending (2.511507ms) ✔ a rechecked head says where its new run is: building on which machine (0.614023ms) ✔ the recheck's own verdict is written, even asked a little before the pending by another machine's clock (0.562206ms) ✔ after a restart, an old run's verdict is weighed against the check the forge's history holds open (0.636395ms) ✔ a recheck the forge does not take fails its caller, and the head is as it was (0.533953ms) ✔ the status tool writes the merge check's pending through the writer, and the mesh's other statuses as they were (6.947585ms) ✔ when a check was asked is read from its id; the opening of the check now pending from the gate's history (1.585437ms) ✔ a head this process did not announce (it restarted) is said only while the forge holds its gate pending (0.294253ms) ✔ a repository as the mesh clones it is told from another (0.243678ms) ✔ gitea_api refuses the forge's administration, a branch's protection and the merge check's status, and sends nothing (7.724937ms) ✔ gitea_api refuses a file written to the default branch or one a rule guards, and writes one on a branch of its own (56.549809ms) ✔ a protection rule covers a branch as the forge decides it: classes, alternatives, a plain name in any case (issue 539) (25.224196ms) ✔ gitea_api still writes what an author writes (8.681652ms) ✔ gitea_branch_protection_set only strengthens (15.331209ms) ✔ gitea_merge_pull_request merges only a head whose required statuses all succeeded, and only that head (42.109323ms) ✔ gitea_merge_pull_request refuses a verdict judged against an earlier trunk, and asks the check once (138.086757ms) ✔ gitea_merge_pull_request merges only the head it is named, and refuses one that is not the head (15.870321ms) ✔ gitea_merge_pull_request is loud when the forge merged a head other than the one it was handed (14.83013ms) ✔ gitea_merge_pull_request says the merge happened when reading back what landed fails (25.406408ms) ✔ gitea_merge_pull_request reads back a fast-forward, and says it cannot read back a squash or a rebase (54.230153ms) ✔ gitea_delete_repo deletes only the tools' own user's repository, unguarded, untouched for 30 days, named in full (20.210291ms) ✔ gitea_api sends the path it judged, and refuses moving a pull request's base (4.163799ms) ✔ gitea_merge_pull_request merges only into a branch whose protection requires the checks (6.956591ms) ✔ a rule named for a branch is not made weaker than the glob rule that guards it now (12.722542ms) ✔ a repository owner or name is never another path (0.230553ms) ✔ the judges, without a forge (0.345048ms) ✔ main's protection is never weakened in its push or its merge whitelist (issue 948, ADR 0398 §2) (0.242074ms) ✔ gitea_api never acts as another user: sudo, in any case, and any query key it does not send are refused (1.606136ms) ✔ gitea_api never approves a pull request nor requests changes: those are the operator's (2.179522ms) ✔ no tool's caller text becomes another path or another user: `..` and `?sudo=` are refused before the forge (4.526809ms) ✔ gitea_merge_pull_request merges a verdict that read siblings only with its group passed and each head approved (82.5001ms) ✔ gitea_merge_pull_request refuses a head the Approve did not name (20.031555ms) ✔ a group of two merges in one pass: the sibling's merge of the composed head does not stop the member's merge (issue 1049) (16.236359ms) ✔ gitea_create_repo has no owner argument and posts only to the tools' own user's repositories (1124/AC8) (36.200417ms) ✔ the tools' team cannot create in the organisation and its token holds no write:organization (1124/AC8) (0.368953ms) ✔ no ready mark, trusted ready-authors setting or approval-by-mark rule is left in the module (19.93341ms) ✔ every page of a pull request's files is read, though the forge caps a page at fifty (40.520349ms) ✔ a pass asks only the repositories that moved since the last look, every one before the first (0.760488ms) ✔ the directories above a merge's files that hold a module at the commit are said, the root never (16.166717ms) ✔ a lookup the forge refuses is thrown, not read as no module (5.854354ms) ✔ a renamed file is said under its old name too, as gone (novox/hq ADR 0267) (6.669723ms) ✔ a new head beyond the newest 20 open pull requests is announced, exactly once (91.663947ms) ✔ a pass pages until it reaches back past its floor, and no further (25.263639ms) ✔ gitea_branch_protection_get answers every rule, read with the administrator account the tools' token cannot read with (22.189136ms) ✔ gitea_branch_protection_get answers the rule for a branch, null when it has none (15.519432ms) ✔ gitea_branch_protection_set still gets the forge's refusal, as the tools' account (4.623983ms) ✔ the statuses asked for replace the rule's, and an empty list requires none (5.928371ms) ✔ a new rule refuses direct pushes unless asked; an administrator's override only when said (0.391555ms) ✔ main's body always refuses pushes and lets only the tools' account merge, whatever is asked (0.842012ms) ✔ another branch's body carries no merge whitelist (0.291518ms) ✔ the rule main is put right in the forge's own words: the body a setup sends carries no status checks of its own (0.347553ms) ✔ each open pull request's new head is announced once, and nothing closed or merged (15.400989ms) ✔ a verdict is the head commit's status; an error is the forge's error, never a success (1.288359ms) ✔ each layer is its own status: the gate with the modules it judged, the repository's own check beside it (0.877087ms) ✔ no verdict sets warning on a required check; only a person's decision fails (1.236552ms) ✔ a commit status is set on the commit, under the merge check's context (38.055751ms) ✔ a change plan is the gate's result: said on the status and, when it builds something, as a comment (0.456938ms) ✔ a head announced is pending in the build queue, since the local time it was announced (0.305143ms) ✔ a composed verdict sets every member's gate at its own head, naming its trunk and the group (0.4206ms) ✔ a member's own verdict with a composed gate layer leaves the gate to the composed verdict, in either order (0.477336ms) ✔ the vault's token is used, a setting of it is ignored and said once, without its value (2.073704ms) [gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 at bbbbbbbbbbbb, it is now at dddddddddddd: out of date, nothing run (novox/hq ADR 0382) [gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was closed unmerged: out of date, nothing run (novox/hq ADR 0382) [gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 merged onto cccccccccccc, its main is now eeeeeeeeeeee: out of date, nothing run (novox/hq ADR 0382) [gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head bbbbbbbbbbbb onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382) [gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head bbbbbbbbbbbb onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382) [gitea] novox/mesh-host's main moved from 444444444444 to 333333333333: 0 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323) [gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head bbbbbbbbbbbb onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382) [gitea] novox/mesh-controller#346: its verdict was judged beside mesh-host#114 was merged otherwise than its head dddddddddddd onto cccccccccccc: out of date, nothing run (novox/hq ADR 0382) ✔ both statuses name the siblings the verdict read, keeping the verdict word and the start of its reason within 140 characters (1.70911ms) ✔ a verdict that could not learn its siblings says so on the status and in the comment, and names none (0.284845ms) ✔ a verdict without siblings is said exactly as before (an older controller) (0.577415ms) ✔ the siblings a verdict names are kept per member, replaced by its next verdict, and removed by one that read none (0.694935ms) ✔ a sibling's new head puts both statuses of the member back to pending, with the reason, and runs nothing (1.470762ms) ✔ a sibling closed unmerged puts the member's verdict out of date (0.333426ms) ✔ a move of the sibling's base puts it out of date, naming both commits (0.448382ms) ✔ the sibling's own merge of the head read onto the base read does not, in either order of the two merges (0.49001ms) ✔ a merge of another head, or onto another base, is a move (0.574228ms) ✔ only the members whose verdict names the sibling are touched, and a member that moved on is dropped (0.514476ms) ✔ a trunk that moved tells the siblings' weighing; one first seen does not (0.439265ms) ✔ the group rule names every missing thing: the group status at each head read, and each head the Approve does not cover (0.949403ms) ✔ a merged or closed member's entry is dropped, so a sibling's later push never re-pends its merged head (0.178946ms) ✔ without the composed verdict's siblings, a sibling's own merge of its new head is a move (the pin of issue 1049) (0.206528ms) ✔ a composed verdict names the siblings of each member at the heads and base commits it composed, so a sibling's own merge of its new head is no move (issue 1049) (0.561524ms) ✔ a composed verdict keeps nothing for a member it cannot name, and a group of one is none (issue 1049) (0.172504ms) ✔ a consumer that asks nothing, or write, publishes: the package team (1.587581ms) ✔ a consumer that asks to read joins the readers, who write no package (0.465544ms) ✔ a reader is made, put on the readers team, and taken off the package team (0.594426ms) ✔ a publisher is made and put on the package team, as before (0.253105ms) ✔ first start: mints with the admin account, keeps the token at 0600, asks for the tools' scopes only (40.927854ms) ✔ second start: reuses the kept token, mints nothing (21.491828ms) ✔ the forge rejects the kept token (its data was restored): minted afresh, once, and the call goes through (26.479224ms) ✔ a token kept with write:admin by an earlier build is minted again without it at the next start, and the forge drops the old one (26.554943ms) ✔ a kept token lacking a scope the tools need: the forge refuses the call for the scope, the token is re-minted with the whole list, and the call goes through (24.191567ms) ✔ the kept file is gone but the forge still holds a token by that name: replaced, not refused (22.614485ms) ✔ concurrent first calls share one mint (11.898474ms) ✔ two tokens hold the name (two mints raced): both are deleted by their id, and one fresh token is minted (15.558485ms) ✔ two processes on one kept file, both without a token, mint once: the second waits for the first and reuses it (102.545339ms) ✔ a lock left by a process that died mid-mint is taken over, not waited on for ever (7.280613ms) ✔ the admin account is refused: said plainly, nothing kept, and the next call fails the same way rather than crashing (15.317252ms) ✔ one process shares one source per kept file — the watcher and the tools never renew against each other (0.69218ms) ✔ a second process finds the token the first renewed, and reuses it instead of minting over it (20.73678ms) ✔ a configured token wins, and is reported rather than minted over when the forge rejects it (2.229076ms) ✔ nothing to mint with and no token: the client says what is missing (0.168486ms) [gitea] no tools — no Gitea token, and nothing to mint one with — set MESH_GITEA_TOKEN, or MESH_GITEA_ADMIN_USER, MESH_GITEA_ADMIN_PASSWORD_FILE, MESH_GITEA_STATE_DIR [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-TmYUD6/state/token ✔ the tools register once there is a way to a token, and the first call mints it (24.522238ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-X9zyZA/state/token ✔ a pull request can be closed, read and cleaned up through the tools (35.463492ms) [gitea] no token kept — minting one [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-9bjpKu/state/token ✔ the tools' token is minted for an account of their own, which is no administrator and writes through its team (68.89423ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-Nn9BcN/state/token ✔ with the tools' token, the forge writes a status and refuses a protection edit — the forge itself, not a guard (49.273565ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-xpgjqB/state/token ✔ what a base's protection asks is read from the branch, which the tools' account may read, not from the rules' list it may not (41.78221ms) [gitea] the kept token was minted with other scopes than the tools take now — minting one with them [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-hZGZQx/state/token [gitea] deleted 1 token(s) named "mesh-tools" the admin account "mesh-admin" held: the tools act as "mesh-tools" now ✔ the administrator's token from before goes: a kept admin token is minted again for the tools' account, and the forge drops the old one (39.365941ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-hq4TgR/state/token ✔ a tools' account someone made an administrator is made a plain account again at the next mint (33.825116ms) ✔ the tools never act as the administrator: MESH_GITEA_TOOLS_USER naming it is refused (0.661562ms) ✔ the manifest hands the tools their account, and the Go forge bundle holds no administrator password (0.784634ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-s6xPDn/state/token ✔ a repository check said as a warning on a head without merge-check.sh reads the base's protection from the branch (39.068132ms) [gitea] no token kept — minting one ✔ a mint that fails leaves the administrator's old token in place: the tools are never left without one (27.46267ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-91qJ35/state/token [gitea] FAILED to delete the token(s) named "mesh-tools" the admin account "mesh-admin" holds — tried again at the next start: Gitea DELETE /users/mesh-admin/tokens/902 (named mesh-tools): 500 {"message":"the forge is not well"} ✔ an old token that cannot be deleted after the mint is said, the new token kept, and deleted at the next start (41.855937ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-ILaYdx/state/token ✔ a team another process made between the look and the create is found, not a failure (37.23036ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-TzAjFI/state/token ✔ setting the tools' account up puts main's rule right in every repository: no push, only the tools' account merges (issue 948) (36.070723ms) [gitea] no token kept — minting one [gitea] the forge already holds a token named "mesh-tools" — replacing it [gitea] minted a token for "mesh-tools" (write:repository, write:issue, read:user), kept at /tmp/gitea-tools-account-Vb5xpb/state/token ✔ a glob rule covering main keeps its statuses when main is given a rule of its own name (issue 948, review round 1) (35.262016ms) ✔ a start with the token kept still puts main's rules right: the module's start asks for it each time (issue 948, review round 1) (12.523075ms) [gitea] novox/mesh-host's main moved from a2c2c35bbbbb to d28ca95ccccc: 25 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323) [gitea] novox/mesh-host's main moved from d28ca95ccccc to ffffffffffff: 0 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323) [gitea] novox/mesh-host: whether a trunk moved could not be weighed, so it is weighed again on the next pass — the forge is away [gitea] novox/mesh-host's main moved from a2c2c35bbbbb to d28ca95ccccc: 0 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323) [gitea] novox/mesh-controller's feat/57-config-and-provisioning moved from eeeeeeeeeeee to d28ca95ccccc: 1 open pull request(s) into it put out of date, nothing run (novox/hq ADR 0323) ✔ both statuses say the head and the trunk commit the verdict judged, first, whatever the summary's length (1.639098ms) ✔ a trunk's move puts an open head's merge check out of date, naming both commits, unless a check is on its way (1.811421ms) ✔ a push to a trunk puts every open pull request into it out of date — twenty-five of them — and none into another (3.116102ms) ✔ a trunk that cannot be read is weighed again on the next pass, never recorded half (0.375755ms) ✔ the trunk's move takes its turn after a verdict in flight, and weighs what the forge holds then (0.46841ms) ✔ a verdict judged against a trunk newer than the pass's first read is not put out of date (0.289444ms) ✔ a verdict that landed out of date keeps its account on the pull request (0.246223ms) ✔ a release branch's move puts every open pull request into it out of date, as a trunk's does (ADR 0358 §5) (0.434195ms) ✔ a signed event is published on the bus and acted on once (66.171427ms) ✔ an unsigned event, or one whose signature does not verify, is refused and published nowhere (34.611715ms) ✔ an event and the poll seeing the same head announce it once (0.352321ms) ✔ each forge event is named in the module's stream and trimmed (0.493707ms) ✔ the webhook is made a system webhook, which the forge sends every repository's events to (1.258102ms) ✔ default webhooks left at the receiver by an earlier start are replaced by one system webhook (1.025786ms) ✔ a repository's copy of a default webhook at the receiver is deleted, on every page, and said (3.423899ms) ✔ a forge that makes no system webhook is said, never taken as heard (0.61255ms) ✔ the receiver tells what it verified and what it refused (7.784008ms) ✔ a forge that never delivers is said loudly once, and unhealthy, when the poll finds what no event said (0.923645ms) ✔ a forge whose events stop after one delivery is said loudly once per silent spell, and refusals are unhealthy (0.4417ms) ✔ without a receiver by configuration the polls alone watch, healthy; a receiver that failed is unhealthy (0.310163ms) ✔ the polls look every 30 s until events are heard, every five minutes while they are, and 30 s again on a miss (0.194496ms) ✔ a pull request's edit event carries its description, and no other pull request event does (issue 1079) (0.220324ms) ℹ tests 163 ℹ suites 0 ℹ pass 163 ℹ fail 0 ℹ cancelled 0 ℹ skipped 0 ℹ todo 0 ℹ duration_ms 768.572461 ```
mesh-tools merged commit 199f72fed2 into main 2026-10-20 21:43:14 +00:00
mesh-tools deleted branch feat/r4c3-build-modules 2026-10-20 21:43:15 +00:00
Sign in to join this conversation.
No Reviewers
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: novox/mesh-catalog#389