diff --git a/.claude-plugin/marketplace.json b/.claude-plugin/marketplace.json
index a6aea30c..17d4d38e 100644
--- a/.claude-plugin/marketplace.json
+++ b/.claude-plugin/marketplace.json
@@ -12,7 +12,7 @@
{
"name": "compound-engineering",
"description": "AI-powered development tools that get smarter with every use. Make each unit of engineering work easier than the last. Includes 29 specialized agents, 22 commands, and 20 skills.",
- "version": "2.38.1",
+ "version": "2.38.2",
"author": {
"name": "Kieran Klaassen",
"url": "https://github.com/kieranklaassen",
diff --git a/plugins/compound-engineering/.claude-plugin/plugin.json b/plugins/compound-engineering/.claude-plugin/plugin.json
index e659557f..d833afc9 100644
--- a/plugins/compound-engineering/.claude-plugin/plugin.json
+++ b/plugins/compound-engineering/.claude-plugin/plugin.json
@@ -1,6 +1,6 @@
{
"name": "compound-engineering",
- "version": "2.38.1",
+ "version": "2.38.2",
"description": "AI-powered development tools. 29 agents, 22 commands, 20 skills, 1 MCP server for code review, research, design, and workflow automation.",
"author": {
"name": "Kieran Klaassen",
diff --git a/plugins/compound-engineering/CHANGELOG.md b/plugins/compound-engineering/CHANGELOG.md
index e7664980..83f7b782 100644
--- a/plugins/compound-engineering/CHANGELOG.md
+++ b/plugins/compound-engineering/CHANGELOG.md
@@ -5,6 +5,15 @@ All notable changes to the compound-engineering plugin will be documented in thi
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
+## [2.38.2] - 2026-03-06
+
+### Fixed
+
+- **`/ce:review` context budget guardrails** — Review agents now build and share a compact review packet instead of receiving the full PR content by default, dedupe always-on agents, and stage follow-up agents for large PRs to reduce context-limit failures during high-effort reviews. ([#166](https://github.com/EveryInc/compound-engineering-plugin/issues/166))
+- **`setup` review depth dedupe** — Comprehensive review configs no longer add `agent-native-reviewer` to `review_agents`, because `/ce:review` already runs it automatically alongside `learnings-researcher`.
+
+---
+
## [2.38.1] - 2026-03-01
### Fixed
diff --git a/plugins/compound-engineering/commands/ce/review.md b/plugins/compound-engineering/commands/ce/review.md
index cf4a0614..00012622 100644
--- a/plugins/compound-engineering/commands/ce/review.md
+++ b/plugins/compound-engineering/commands/ce/review.md
@@ -65,19 +65,67 @@ Read `compound-engineering.local.md` in the project root. If found, use `review_
If no settings file exists, invoke the `setup` skill to create one. Then read the newly created file and continue.
+#### Build Review Packet (REQUIRED BEFORE SPAWNING AGENTS)
+
+
+
+Before launching any review agent, create a compact review packet from local repo inspection and `gh pr view --json` output.
+
+The packet should contain:
+- PR title, body summary, and linked issues in 5 bullets or fewer
+- Changed files grouped by subsystem, plus churn totals (file count / additions / deletions)
+- High-risk files and why they matter
+- Test coverage summary: existing tests touched, new tests added, missing test areas
+- Open questions or suspicious patterns that need deeper inspection
+
+Keep the packet lean:
+- Target under 200 lines and under ~3k tokens
+- Do NOT paste the full diff, full PR body, or full file contents into every Task
+- Omit generated files, lockfiles, snapshots, vendored assets, and build artifacts unless they are the source of risk
+- For large files, include only the specific functions/classes/line ranges that matter
+
+Each Task should receive:
+- the review packet
+- the project-specific review context from `compound-engineering.local.md`
+- the exact file paths it should inspect next
+
+If an agent needs more detail, instruct it to read files from disk directly rather than relying on pasted context.
+
+
+
#### Parallel Agents to review the PR:
-Run all configured review agents in parallel using Task tool. For each agent in the `review_agents` list:
+Build the final base agent set as:
+
+1. `review_agents` from config
+2. Always-on agents: `agent-native-reviewer`, `learnings-researcher`
+
+Deduplicate this list while preserving order. Never run the same agent twice.
+
+Run the deduped agent set in parallel using Task tool. For each agent:
```
-Task {agent-name}(PR content + review context from settings body)
+Task {agent-name}(review packet + exact file paths to inspect + review context from settings body)
```
-Additionally, always run these regardless of settings:
-- Task agent-native-reviewer(PR content) - Verify new features are agent-accessible
-- Task learnings-researcher(PR content) - Search docs/solutions/ for past issues related to this PR's modules and patterns
+Additionally:
+- `agent-native-reviewer` verifies that new features are agent-accessible
+- `learnings-researcher` searches `docs/solutions/` for past issues related to this PR's modules and patterns
+
+#### Large-PR Context Guardrails
+
+If the PR is large (for example: >25 files changed, >800 changed lines, multiple subsystems, or the model has already warned about compaction/context pressure), do NOT fan out to every configured agent immediately.
+
+Instead:
+
+1. Start with a first wave: stack-specific reviewer(s), `agent-native-reviewer`, `learnings-researcher`, and only the most relevant focus agent(s) for the risky files.
+2. Wait for first-wave results and identify unresolved hot spots.
+3. Launch second-wave agents only for those hot spots, passing a narrower follow-up packet and the specific file paths.
+4. Prefer targeted follow-up Tasks over repeating a full-repo review.
+
+When context pressure is visible, breadth yields to precision. It is better to run fewer well-targeted agents than many shallow agents that compact and lose the actual code under review.
@@ -89,9 +137,9 @@ These agents are run ONLY when the PR matches specific criteria. Check the PR fi
**MIGRATIONS: If PR contains database migrations, schema.rb, or data backfills:**
-- Task schema-drift-detector(PR content) - Detects unrelated schema.rb changes by cross-referencing against included migrations (run FIRST)
-- Task data-migration-expert(PR content) - Validates ID mappings match production, checks for swapped values, verifies rollback safety
-- Task deployment-verification-agent(PR content) - Creates Go/No-Go deployment checklist with SQL verification queries
+- Task schema-drift-detector(review packet + migration file paths) - Detects unrelated schema.rb changes by cross-referencing against included migrations (run FIRST)
+- Task data-migration-expert(review packet + migration file paths) - Validates ID mappings match production, checks for swapped values, verifies rollback safety
+- Task deployment-verification-agent(review packet + migration file paths) - Creates Go/No-Go deployment checklist with SQL verification queries
**When to run:**
- PR includes files matching `db/migrate/*.rb` or `db/schema.rb`
@@ -203,7 +251,9 @@ Complete system context map with component interactions
### 4. Simplification and Minimalism Review
-Run the Task code-simplicity-reviewer() to see if we can simplify the code.
+If `code-simplicity-reviewer` is NOT already in the deduped agent set, run it now with the same review packet.
+
+If it already ran in the main review wave, reuse that result. Do not spawn `code-simplicity-reviewer` twice for the same PR.
### 5. Findings Synthesis and Todo Creation Using file-todos Skill
diff --git a/plugins/compound-engineering/skills/setup/SKILL.md b/plugins/compound-engineering/skills/setup/SKILL.md
index 73fc0fb7..ab6e2f42 100644
--- a/plugins/compound-engineering/skills/setup/SKILL.md
+++ b/plugins/compound-engineering/skills/setup/SKILL.md
@@ -114,9 +114,9 @@ options:
- label: "Thorough (Recommended)"
description: "Stack reviewers + all selected focus agents."
- label: "Fast"
- description: "Stack reviewers + code simplicity only. Less context, quicker."
+ description: "Stack reviewers + code simplicity only. Lowest context use for large PRs."
- label: "Comprehensive"
- description: "All above + git history, data integrity, agent-native checks."
+ description: "All above + git history and data integrity. Always-on review agents stay deduped."
```
## Step 4: Build Agent List and Write File
@@ -136,7 +136,9 @@ options:
**Depth:**
- Thorough: stack + selected focus areas
- Fast: stack + `code-simplicity-reviewer` only
-- Comprehensive: all above + `git-history-analyzer, data-integrity-guardian, agent-native-reviewer`
+- Comprehensive: all above + `git-history-analyzer, data-integrity-guardian`
+
+`agent-native-reviewer` and `learnings-researcher` are always added by `/ce:review`, so do not include them in `review_agents`.
**Plan review agents:** stack-specific reviewer + `code-simplicity-reviewer`.
@@ -169,6 +171,10 @@ Review depth: {depth}
Agents: {count} configured
{agent list, one per line}
+Always-on during /ce:review:
+ agent-native-reviewer
+ learnings-researcher
+
Tip: Edit the "Review Context" section to add project-specific instructions.
Re-run this setup anytime to reconfigure.
```
diff --git a/tests/cli.test.ts b/tests/cli.test.ts
index 390d06ce..9fe477e3 100644
--- a/tests/cli.test.ts
+++ b/tests/cli.test.ts
@@ -310,6 +310,56 @@ describe("CLI", () => {
expect(await exists(path.join(codexRoot, "AGENTS.md"))).toBe(true)
})
+ test("convert preserves compound-engineering review guardrails in codex output", async () => {
+ const tempRoot = await fs.mkdtemp(path.join(os.tmpdir(), "cli-ce-codex-home-"))
+ const codexRoot = path.join(tempRoot, ".codex")
+ const pluginRoot = path.join(import.meta.dir, "..", "plugins", "compound-engineering")
+
+ const proc = Bun.spawn([
+ "bun",
+ "run",
+ "src/index.ts",
+ "convert",
+ pluginRoot,
+ "--to",
+ "codex",
+ "--codex-home",
+ codexRoot,
+ ], {
+ cwd: path.join(import.meta.dir, ".."),
+ stdout: "pipe",
+ stderr: "pipe",
+ })
+
+ const exitCode = await proc.exited
+ const stdout = await new Response(proc.stdout).text()
+ const stderr = await new Response(proc.stderr).text()
+
+ if (exitCode !== 0) {
+ throw new Error(`CLI failed (exit ${exitCode}).\nstdout: ${stdout}\nstderr: ${stderr}`)
+ }
+
+ const reviewPromptPath = path.join(codexRoot, "prompts", "ce-review.md")
+ const reviewSkillPath = path.join(codexRoot, "skills", "ce-review", "SKILL.md")
+ const setupSkillPath = path.join(codexRoot, "skills", "setup", "SKILL.md")
+
+ expect(stdout).toContain("Converted compound-engineering")
+ expect(await exists(reviewPromptPath)).toBe(true)
+ expect(await exists(reviewSkillPath)).toBe(true)
+ expect(await exists(setupSkillPath)).toBe(true)
+
+ const reviewPrompt = await fs.readFile(reviewPromptPath, "utf8")
+ const reviewSkill = await fs.readFile(reviewSkillPath, "utf8")
+ const setupSkill = await fs.readFile(setupSkillPath, "utf8")
+
+ expect(reviewPrompt).toContain("create a compact review packet")
+ expect(reviewPrompt).toContain("Deduplicate this list while preserving order. Never run the same agent twice.")
+ expect(reviewPrompt).toContain("Do not spawn `code-simplicity-reviewer` twice for the same PR.")
+ expect(reviewSkill).toContain("Task {agent-name}(review packet + exact file paths to inspect + review context from settings body)")
+ expect(setupSkill).toContain("`agent-native-reviewer` and `learnings-researcher` are always added by `/ce:review`, so do not include them in `review_agents`.")
+ expect(setupSkill).toContain("Always-on during /ce:review:")
+ })
+
test("install supports --also with codex output", async () => {
const tempRoot = await fs.mkdtemp(path.join(os.tmpdir(), "cli-also-"))
const fixtureRoot = path.join(import.meta.dir, "fixtures", "sample-plugin")
diff --git a/tests/compound-review-command.test.ts b/tests/compound-review-command.test.ts
new file mode 100644
index 00000000..c8d7cc84
--- /dev/null
+++ b/tests/compound-review-command.test.ts
@@ -0,0 +1,40 @@
+import { describe, expect, test } from "bun:test"
+import { promises as fs } from "fs"
+import path from "path"
+
+const repoRoot = path.join(import.meta.dir, "..")
+const reviewCommandPath = path.join(
+ repoRoot,
+ "plugins",
+ "compound-engineering",
+ "commands",
+ "ce",
+ "review.md",
+)
+const setupSkillPath = path.join(
+ repoRoot,
+ "plugins",
+ "compound-engineering",
+ "skills",
+ "setup",
+ "SKILL.md",
+)
+
+describe("compound-engineering review workflow content", () => {
+ test("ce:review uses a compact review packet and dedupes agents", async () => {
+ const reviewCommand = await fs.readFile(reviewCommandPath, "utf8")
+
+ expect(reviewCommand).toContain("#### Build Review Packet (REQUIRED BEFORE SPAWNING AGENTS)")
+ expect(reviewCommand).toContain("Deduplicate this list while preserving order. Never run the same agent twice.")
+ expect(reviewCommand).toContain("Task {agent-name}(review packet + exact file paths to inspect + review context from settings body)")
+ expect(reviewCommand).toContain("Do not spawn `code-simplicity-reviewer` twice for the same PR.")
+ })
+
+ test("setup skill avoids duplicating always-on review agents", async () => {
+ const setupSkill = await fs.readFile(setupSkillPath, "utf8")
+
+ expect(setupSkill).toContain("Comprehensive: all above + `git-history-analyzer, data-integrity-guardian`")
+ expect(setupSkill).toContain("`agent-native-reviewer` and `learnings-researcher` are always added by `/ce:review`, so do not include them in `review_agents`.")
+ expect(setupSkill).toContain("Always-on during /ce:review:")
+ })
+})