Skip to content
Closed
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
2 changes: 1 addition & 1 deletion .github/AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,5 +22,5 @@ change requires explicit security review under `MAINTAINERS.md`.

- Inspect the complete workflow diff, including event triggers, permissions, conditions, interpolation, and shell behavior.
- Run the local commands represented by changed workflow steps where possible.
- Run `bun run prepush` for CI, release, dependency, packaging, or cross-platform workflow changes.
- Follow the root validation policy: run the suite by default; if a full run is too costly, run at least focused regression tests and document the reason and remaining coverage. Required CI checks still apply before merge.
- Do not claim the workflow itself passed until GitHub Actions reports success for the exact commit.
2 changes: 1 addition & 1 deletion .github/scripts/pr-quality-messages.test.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -208,7 +208,7 @@ describe("buildStaleNotice", () => {
// The notice must describe the exact state the reset produces: a fresh
// unticked section from pr-quality.cjs.
const section = buildReviewReadinessSection();
assert.match(section, /\[ \] All CI tests are green on my local testing\./);
assert.match(section, /\[ \] Required local validation passed; commands, results, and any full-suite exception are documented\./);
});
});

Expand Down
2 changes: 1 addition & 1 deletion .github/scripts/pr-quality.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ const REVIEW_READINESS_END = "<!-- pr-quality-readiness-checklist:end -->";
* so the "ready" claim reads as the closing confirmation, not a fourth task.
*/
const REVIEW_READINESS_ITEMS = [
"All CI tests are green on my local testing.",
"Required local validation passed; commands, results, and any full-suite exception are documented.",

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Update the gate prompt to match the new validation policy

When a contributor PR remains in draft with an incomplete checklist, .github/workflows/enforce-pr-target.yml lines 1220 and 1245 still instruct the author to wait until “local CI is green.” That is the old full-suite requirement and contradicts this newly generated checklist item, which permits a documented focused-test exception. Update both workflow prompts and their regression assertions so contributors receive the same validation policy from the checklist, documentation, and enforcement comment.

AGENTS.md reference: .github/AGENTS.md:L19-L19

Useful? React with 👍 / 👎.

"I pushed my PR to the latest dev commit.",
"I resolved all correct Codex and CodeRabbit findings.",
"My PR is ready for review.",
Expand Down
8 changes: 4 additions & 4 deletions .github/scripts/pr-quality.test.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -409,7 +409,7 @@ describe("review readiness checklist", () => {

it("treats a reworded but complete section as complete", () => {
const reworded = SECTION
.replace("All CI tests are green on my local testing.", "Local suite green.")
.replace("Required local validation passed; commands, results, and any full-suite exception are documented.", "Local suite green.")
.replaceAll("- [ ] ", "- [x] ");
const result = extractReviewReadiness(reworded);
assert.equal(result.present, true);
Expand Down Expand Up @@ -585,7 +585,7 @@ describe("uncheckReviewReadinessBoxes", () => {
"<!-- pr-quality-readiness-checklist:start -->",
"## Review readiness checklist",
"",
"- [x] All CI tests are green on my local testing.",
"- [x] Required local validation passed; commands, results, and any full-suite exception are documented.",
"- [x] I pushed my PR to the latest dev commit.",
"- [x] I resolved all correct Codex and CodeRabbit findings.",
"- [x] My PR is ready for review.",
Expand All @@ -596,7 +596,7 @@ describe("uncheckReviewReadinessBoxes", () => {
const body = uncheckReviewReadinessBoxes(checkedBody, [
REVIEW_READINESS_CLAIM_INDEX.latest_dev,
]);
assert.ok(body.includes("- [x] All CI tests are green on my local testing."));
assert.ok(body.includes("- [x] Required local validation passed; commands, results, and any full-suite exception are documented."));
assert.ok(body.includes("- [ ] I pushed my PR to the latest dev commit."));
assert.ok(body.includes("- [x] My PR is ready for review."));
});
Expand All @@ -606,7 +606,7 @@ describe("uncheckReviewReadinessBoxes", () => {
0,
REVIEW_READINESS_CLAIM_INDEX.latest_dev,
]);
assert.ok(body.includes("- [ ] All CI tests are green on my local testing."));
assert.ok(body.includes("- [ ] Required local validation passed; commands, results, and any full-suite exception are documented."));
assert.ok(body.includes("- [ ] I pushed my PR to the latest dev commit."));
assert.ok(body.includes("- [x] I resolved all correct Codex and CodeRabbit findings."));
assert.ok(body.includes("- [x] My PR is ready for review."));
Expand Down
54 changes: 31 additions & 23 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -196,7 +196,7 @@ it binds you regardless of which mechanism is within reach.
bun install
bun run typecheck # bun x tsc --noEmit (strict)
bun run test:changed # import-graph tests against the resolved `dev` merge base
bun run test # full tests/ suite (PR-ready / explicit ask only)
bun run test # full tests/ suite (default before review)
bun run lint:gui # GUI eslint
bun run privacy:scan # credential/privacy scan used by CI
bun run structure:check # structure/ doc-map, ownership, and invariant-binding gate
Expand All @@ -217,23 +217,29 @@ bun run skill:surface:check # what CI asserts
also if the hand-written pages name a command the registry does not have. That second check is not
hypothetical: it caught a documented `ocx request-history` that never existed.

During implementation, use the smallest focused checks that directly cover the
changed subsystem. Prefer `bun test tests/<domain>/<name>.test.ts` for a known
file, `bun test tests/<domain>` for one subsystem, or
`bun run test:changed` when the touch set is broader than one file. Do **not**
run repository-wide `bun run test` or a bare `bun test` with no file arguments
for a scoped change by default. `bun run test:changed` follows Bun's parsed module graph: it
selects test files that import changed modules, but it cannot see dependencies
expressed through subprocesses, source files read as data, or golden/derived
files. Run the relevant focused tests explicitly for those paths; if no reliable
focused set covers them, the full suite is required even for a scoped change.
That indirect-dependency case is the explicit exception to the scoped-change
default. The full suite is ~850 files, so otherwise reserve it for a failed or
ambiguous focused result, an explicit user request, or the PR-ready gate below.

Before creating or updating a non-trivial PR as review-ready, or before
approving such a PR, run `bun run typecheck` and `bun run test`. CI runs these
on Linux, Windows, and macOS.
Run the test suite for a change; `bun run test` is the default before a
non-trivial PR is marked review-ready or approved. During implementation, use
focused files or `bun run test:changed` for faster feedback.

If a full local run is disproportionately expensive for the task or available
resources, including contention across concurrent worktrees, run at least the
focused regression tests that exercise the changed behavior. This is a scope
exception, not permission to skip testing or ignore a failing test. Record why
the full run was impractical, the exact commands and results, and the coverage
left to CI in the PR's Verification section. Never describe an unrun suite as
passing. Run `bun run typecheck` before review readiness as well.

`bun run test:changed` follows Bun's parsed module graph, so it cannot discover
dependencies expressed through subprocesses, source files read as data, or
golden/derived files. Run those relevant regression files explicitly. If a
focused set cannot reliably cover the change, keep the PR in draft until the
broader validation is available.

After pushing, inspect the required CI for the current PR head. Missing,
awaiting-approval, skipped, cancelled, or older-head results are not passing
evidence. Required checks must actually complete successfully before merge.
The repository does not install an automatic pre-push validation hook;
`bun run prepush` remains available as an explicit comprehensive check.

Do not rerun passing checks on unchanged code merely for additional confidence.

Expand Down Expand Up @@ -377,8 +383,9 @@ empty, thin, or malformed descriptions; PRs whose title or description
mentions `gui` must include a screenshot of the UI change in the description.
Contributor PRs (authors without repository push permission) open in draft and
stay there until a four-box review-readiness checklist in the description is
complete: local CI green, branch on the latest `dev` commit, all correct Codex
and CodeRabbit findings fixed, and the ready-for-review confirmation. When all
complete: required local validation passed with its scope documented, branch
on the latest `dev` commit, all correct Codex and CodeRabbit findings fixed,
and the ready-for-review confirmation. When all
four boxes are ticked the gate marks the PR ready and notifies the maintainers
listed in `MAINTAINERS.md` (excluding the author). Completion is bound to the
exact commit the PR head pointed at: if new commits are pushed afterwards, the
Expand All @@ -387,7 +394,7 @@ and asks the author to test and tick the boxes again against the latest code.
Before a completion is accepted, the gate verifies the checklist claims it
can check itself: the branch must be on the latest `dev` commit or at most
10 commits behind it, and Codex/CodeRabbit findings must be resolved. The
local-CI box is an author attestation only — fork contributors cannot start
local-validation box is an author attestation only — fork contributors cannot start
repository CI; a maintainer has to — so the gate never disproves it; a new
push still resets every box. A disproved claim unticks the matching box and
keeps the PR a draft.
Expand All @@ -400,7 +407,7 @@ explicitly integrate through a PR without another maintainer approval, including
their own PR, under the policy in `MAINTAINERS.md`. Record the decision and exact-head
CI evidence; keep outstanding maintainer objections and security review separate.
The bypass is PR-only, so a direct push to `dev` remains rejected regardless of
`--no-verify`. Contributor review and `main`/`preview` rules remain unchanged.
local hook settings. Contributor review and `main`/`preview` rules remain unchanged.

[`MAINTAINERS.md`](./MAINTAINERS.md) is authoritative for review and merge
policy (approvals, CI requirements, security review, promotion). This file
Expand Down Expand Up @@ -430,7 +437,8 @@ reviewers (Codex, CodeRabbit).
- **Tests:** behavior changes in `src/` need a focused regression test near
the existing tests for that subsystem. During implementation, run the relevant
focused files and use `bun run test:changed` for import-connected coverage as
described above; the full suite is the PR-ready gate.
described above. Full-suite validation is the default before review readiness;
the documented resource exception still requires focused regression tests.
- **Docs sync:** user-facing behavior changes should update `docs-site/` (and
keep translated locales from contradicting the English source).
- **Privacy:** `bun run privacy:scan` must stay green; never introduce logging
Expand Down
25 changes: 13 additions & 12 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -56,21 +56,22 @@ A ready-for-review PR is the author's claim that the change is complete, underst
stated. A closed PR can be reopened once the stated reason is resolved, or
replaced with a clean one.

## Pre-push hook
## Local validation and hooks

After cloning, run once to install a local pre-push hook that runs the typecheck,
unit-test, privacy-scan, and (when `gui/` changed) GUI eslint and React Doctor
portions of the CI gate:
Run `bun run test` before review readiness. If the full local suite is too costly
for the task or available resources, run at least focused regression tests for
the changed behavior. Document the reason, commands, results, and remaining
coverage in the PR. Follow [AGENTS.md](./AGENTS.md#commands) for the complete
validation policy; required CI must pass on the current PR head before merge.
`bun run prepush` remains an optional comprehensive local check.

```sh
bun run setup:hooks
```

This installs a `pre-push` hook (into the hooks dir git reports, so worktrees and
`core.hooksPath` work) that runs `bun run prepush` — `typecheck`,
`lint:gui:if-changed`, `test`, `privacy:scan`, and `doctor:gui:if-changed` —
before every `git push`. Both `lint:gui:if-changed` and `doctor:gui:if-changed`
run their check only when the push touches `gui/`.
The same checks run on ubuntu-latest, macos-latest, and windows-latest in CI (CI
additionally builds the GUI and smoke-tests the CLI). Skip in an emergency with
`git push --no-verify`.
This installs the `post-merge` hook, which rebuilds the packaged dashboard when a
merge changes its source. It also removes the unmodified, retired repository
pre-push hook from Git's resolved hooks directory, including linked worktrees
and `core.hooksPath` setups. Custom pre-push hooks are preserved. Validation no
longer runs automatically on every push; existing contributors should rerun the
setup command once to migrate their hooks.
10 changes: 7 additions & 3 deletions MAINTAINERS.md
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,8 @@ when a maintainer steps down.
mentions `gui` must include a screenshot of the UI change in the description.
Contributor PRs (authors without repository push permission) open in draft
and stay there until a four-box review-readiness checklist in the
description is complete: local CI green, branch on the latest `dev` commit,
description is complete: required local validation passed with its scope documented,
branch on the latest `dev` commit,
all correct Codex and CodeRabbit findings fixed, and the ready-for-review
confirmation. When all four boxes are ticked the gate marks the PR ready and
notifies the maintainers listed in `MAINTAINERS.md` (excluding the author).
Expand All @@ -47,8 +48,11 @@ when a maintainer steps down.
Before a completion is accepted, the gate verifies the checklist claims
it can check itself: the branch must be on the latest `dev` commit or at
most 10 commits behind it, and Codex/CodeRabbit findings must be resolved.
The local-CI box is an author attestation only — fork contributors cannot
start repository CI; a maintainer has to — so the gate never disproves it;
The local-validation box follows the full-suite default and documented resource
exception in [AGENTS.md](./AGENTS.md#commands); focused regression tests remain
mandatory under that exception. It is an author attestation only — fork
contributors cannot start repository CI; a maintainer has to — so the gate
never disproves it;
a new push still resets every box. A disproved claim unticks the matching
box and keeps the PR a draft.
Authors with repository push permission skip the ancestry heuristic only. As
Expand Down
28 changes: 19 additions & 9 deletions docs-site/src/content/docs/contributing.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,14 +12,17 @@ Bun runtime for users, but this checkout's scripts run through your local Bun in
git clone https://github.com/lidge-jun/opencodex.git
cd opencodex
bun install
bun run setup:hooks # install post-merge; retire the managed pre-push hook
bun run dev:proxy # proxy API in dev mode
bun run dev:gui # dashboard dev server (another terminal)
bun run typecheck # bun x tsc --noEmit
bun run test:changed # routine import-graph test selection
bun test tests/routing/router.test.ts # routine focused test
bun run test # complete suite (PR-ready / explicit ask)
bun run test # full suite (default)
```

`bun run setup:hooks` installs only `post-merge` and removes an unmodified retired managed
`pre-push` hook, preserving custom hooks. A pre-push hook is no longer required.
`bun run prepush` remains an optional manual check.

`bun run dev` remains an alias for `bun run dev:proxy`. The dashboard dev server is `bun run dev:gui`;
the packaged dashboard at `GET /` is produced by `bun run build:gui` (`gui/dist`).

Expand All @@ -31,13 +34,21 @@ scripts so local commands match CI:
```bash
bun run typecheck # strict TypeScript check
bun run test:changed # import-graph tests against the resolved dev merge base
bun run test # complete tests/ suite (PR-ready / explicit ask)
bun run test # full suite (default)
bun test tests/routing/router.test.ts # focused test file
bun run build:gui # Vite GUI build + package preparation
bun run privacy:scan # credential/privacy scan used by CI
bun run prepare:package # refresh package launchers/assets
```

Run `bun run test` by default. If a full run is disproportionately expensive for the task size,
available machine resources, or concurrent worktrees, you must at least run focused regression tests
that exercise the changed behavior, such as `bun test tests/<domain>/<name>.test.ts`. Explain the
reason for narrowing the run and report the exact commands, results, and untested scope.
`bun run test:changed` can supplement this coverage, but it cannot detect every indirect dependency.
Neither relying only on CI nor skipping local testing is a blanket exemption. Before merge, all
required CI checks must pass for the exact current PR head.

`test:changed` selects the first comparison ref that exists, in order: `upstream/dev`,
`origin/dev`, then local `dev`. It reports that ref and the exact `git merge-base HEAD <ref>`
commit, then passes the merge-base SHA to Bun.
Expand All @@ -54,8 +65,7 @@ and `tests/test-layout.test.ts` enforces it, so a new test goes into its domain
an entry in the map (the tooling test tells you which one is missing). `tests/helpers/` holds
shared fixtures and `tests/helpers/repo-root.ts` is how a test reaches repository files;
`tests/e2e-style/` holds broader native-parity scenarios. Keep a focused regression near the
existing tests for the subsystem you change (`bun test tests/<domain>` runs one subsystem); run
the full suite for shared routing, adapters, config, or server behavior.
existing tests for the subsystem you change (`bun test tests/<domain>` runs one subsystem).

The docs site you're reading lives in `docs-site/` (Astro + Starlight):

Expand Down Expand Up @@ -250,6 +260,6 @@ startup path must not import the manifest catalog or activate Compatibility Lab.

## Verify before you claim done

Run the narrowest command that proves your change — `bun run typecheck` for types, a focused
`bun test tests/<domain>/<name>.test.ts` or runtime probe for behavior, then the broader gates appropriate to
the affected surface. opencodex favors small, verifiable commits over large batches.
Follow the testing policy above and run `bun run typecheck` for type changes, plus the checks
required for the affected surface. Report the commands, results, and remaining untested scope;
only claim the validation you actually completed.
9 changes: 5 additions & 4 deletions docs-site/src/content/docs/contributing/pr-quality.md
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,8 @@ tells you exactly what to change:
self-waive the screenshot requirement.
Contributor PRs (authors without repository push permission) open in draft
and stay there until a four-box review-readiness checklist in the
description is complete: local CI green, the branch on the latest `dev`
commit, all correct Codex and CodeRabbit findings fixed, and the
description is complete: required local validation passed with its scope
documented, the branch on the latest `dev` commit, all correct Codex and CodeRabbit findings fixed, and the
ready-for-review confirmation. Once every box is ticked the check marks the
PR ready for review and notifies the maintainers listed in `MAINTAINERS.md`
(excluding the author). The gate's status and "what to do" live in a single
Expand All @@ -67,8 +67,9 @@ tells you exactly what to change:
can check itself: the branch must be on the latest `dev` commit or at most
10 commits behind it, and every Codex and CodeRabbit review thread authored
by a review bot on the current head must be resolved (unresolved threads
from other authors do not block). The local-CI box is an author attestation
only — fork contributors cannot start repository CI; a maintainer has to —
from other authors do not block). The local-validation box follows the [test-scope policy](/contributing/#build-and-test-commands):
run the full suite by default; when it is too costly, run focused regressions
and document the exception. It is an author attestation only — fork contributors cannot start repository CI; a maintainer has to —
so the gate never disproves it; a new push still resets every box. CodeRabbit
findings that fall outside the diff range and are reported only in a review
body on the current head add to the unresolved count while a bot review
Expand Down
Loading
Loading