mirror of
https://github.com/garrytan/gstack.git
synced 2026-06-26 11:39:58 +02:00
v1.57.10.0 feat: Codex review default-on across review/ship/plan/docs (#1966)
* feat(config): make codex_reviews the master switch for all Codex review Broaden the codex_reviews doc to describe it governing /review, /ship, /document-release, plan reviews, and /autoplan. Reject invalid values on set (preserving the existing value) so a typo can never silently flip paid Codex calls on or off. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * feat(review): Codex review default-on across review/ship/plan/docs Add a shared codexPreflight() helper (constants.ts) that, in one bash block, reads codex_reviews, sources gstack-codex-probe, checks install + auth, and echoes a single canonical mode (ready/not_installed/not_authed/ disabled). All Codex resolvers route through it. - generateCodexPlanReview: opt-in question removed; the outside voice now runs automatically (default-on), falling back to a Claude subagent when Codex is missing/unauthed. Cross-model tension still gates on user approval (sovereignty preserved). - generateAdversarialStep: probe-based availability (install AND auth), distinct not-installed vs not-authed guidance; 200-line structured-review threshold unchanged. - generateCodexDocReview (new, wired via CODEX_DOC_REVIEW): reviews the release's docs against the shipped diff range, informational + an explicit apply-fixes decision point, never auto-edits. - autoplan Phase 0.5 now honors codex_reviews=disabled so the switch is truly global. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * chore(docs): regenerate SKILL docs + refresh ship golden Output of gen:skill-docs for the Codex-default-on resolver/template changes. Refreshes the factory-ship golden fixture (codex-host output unchanged — resolvers strip for the codex host). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * test(infra): widen size-budget guards for default-on Codex outside-voice The codexPreflight() block + CODEX_MODE branch prose (replacing the smaller opt-in question) grows plan-ceo/eng/devex-review and review by 5-7% over baseline. Each bump carries a comment justifying it as intentional capability, not slop. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * test: guard Codex default-on + config reject-on-set skill-validation: assert plan reviews no longer carry the opt-in question and render the default-on outside-voice, document-release carries the doc review, and the codex host strips all of it. gstack-config: codex_reviews defaults to enabled, accepts enabled/disabled, and rejects an invalid value while preserving the existing one. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix(test): align gstack-config tests with defaults-fallback behavior Three tests (last touched v0.13.7.0) asserted get/list print empty for unset keys, but gstack-config falls back to the documented defaults table (get returns the default, list shows the active-values block). Update the assertions to the real behavior and split out an unknown-key case that does still return empty. Pre-existing red, unrelated to codex review. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * v1.57.10.0 feat: Codex review default-on across review/ship/plan/docs Codex cross-model review now runs by default on /review, /ship, all four plan reviews, /document-release, and /autoplan, governed by one master switch (codex_reviews, default enabled). Plan-review outside voice is default-on; /document-release gets a new Codex doc-vs-diff audit; every call site detects install AND auth and falls back to a Claude subagent with a clear reason. Disable everything with: gstack-config set codex_reviews disabled Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -1386,15 +1386,16 @@ describe('Codex skill', () => {
|
||||
expect(content).toContain('Adversarial review (always-on)');
|
||||
// Always-on: both Claude and Codex adversarial
|
||||
expect(content).toContain('Claude adversarial subagent (always runs)');
|
||||
expect(content).toContain('Codex adversarial challenge (always runs when available)');
|
||||
expect(content).toContain('Codex adversarial challenge (runs whenever');
|
||||
// Claude adversarial subagent dispatch
|
||||
expect(content).toContain('Agent tool');
|
||||
expect(content).toContain('FIXABLE');
|
||||
expect(content).toContain('INVESTIGATE');
|
||||
// Codex availability check
|
||||
expect(content).toContain('CODEX_NOT_AVAILABLE');
|
||||
// OLD_CFG only gates Codex, not Claude
|
||||
expect(content).toContain('skip Codex passes only');
|
||||
// Probe-based availability via the shared codexPreflight() (install + auth)
|
||||
expect(content).toContain('CODEX_MODE');
|
||||
expect(content).toContain('command -v codex'); // install check kept literal
|
||||
// codex_reviews=disabled gates Codex passes only; Claude adversarial still runs
|
||||
expect(content).toContain('skip the Codex passes ONLY');
|
||||
// Review log
|
||||
expect(content).toContain('adversarial-review');
|
||||
expect(content).toContain('reasoning_effort="high"');
|
||||
@@ -1449,6 +1450,43 @@ describe('Codex skill', () => {
|
||||
expect(content).toContain('codex exec');
|
||||
});
|
||||
|
||||
// D5 regression guard: the Codex outside voice is default-on, not opt-in. A future
|
||||
// gen-skill-docs change must not silently reintroduce the "Want an outside voice?"
|
||||
// AskUserQuestion. The CODEX_PLAN_REVIEW content renders into each skill's
|
||||
// sections/review-sections.md (the skeleton points at it). plan-design-review uses
|
||||
// DESIGN_OUTSIDE_VOICES, not CODEX_PLAN_REVIEW, so it is excluded here.
|
||||
test('plan reviews run the Codex outside voice default-on (no opt-in question)', () => {
|
||||
for (const skill of ['plan-eng-review', 'plan-ceo-review', 'plan-devex-review']) {
|
||||
const content = fs.readFileSync(
|
||||
path.join(ROOT, skill, 'sections', 'review-sections.md'), 'utf-8');
|
||||
expect(content).not.toContain('Want an outside voice');
|
||||
expect(content).toContain('Outside Voice — Independent Plan Challenge (default-on)');
|
||||
expect(content).toContain('CODEX_MODE');
|
||||
expect(content).toContain('command -v codex'); // preflight install check (e2e relies on it)
|
||||
}
|
||||
});
|
||||
|
||||
test('/document-release includes the default-on Codex documentation review', () => {
|
||||
// The doc-review renders into the carved release-body section (kept out of the
|
||||
// always-loaded skeleton to respect the skeleton-byte budget).
|
||||
const content = fs.readFileSync(
|
||||
path.join(ROOT, 'document-release', 'sections', 'release-body.md'), 'utf-8');
|
||||
expect(content).toContain('Codex Documentation Review (default-on)');
|
||||
expect(content).toContain('CODEX_MODE');
|
||||
expect(content).toContain('codex-doc-review');
|
||||
});
|
||||
|
||||
test('codex-host document-release does NOT contain the Codex doc review', () => {
|
||||
// .agents/ is gitignored — generate on demand (codex never invokes itself)
|
||||
Bun.spawnSync(['bun', 'run', 'scripts/gen-skill-docs.ts', '--host', 'codex'], {
|
||||
cwd: ROOT, stdout: 'pipe', stderr: 'pipe',
|
||||
});
|
||||
const content = fs.readFileSync(
|
||||
path.join(ROOT, '.agents', 'skills', 'gstack-document-release', 'SKILL.md'), 'utf-8');
|
||||
expect(content).not.toContain('Codex Documentation Review');
|
||||
expect(content).not.toContain('codex-doc-review');
|
||||
});
|
||||
|
||||
test('codex review invocations avoid the prompt plus --base argument shape', () => {
|
||||
for (const rel of ['codex/SKILL.md', 'review/SKILL.md', 'ship/SKILL.md']) {
|
||||
// ship's codex command moved into sections/adversarial.md (T9 carve).
|
||||
|
||||
Reference in New Issue
Block a user