Enforces test quality rules (TEST-1 through TEST-8). Loaded by the conductor for review and test operations. Detects weak assertions, insufficient coverage, missing property tests, slow unit tests, I/O in unit tests, missing boundary conditions, and test ratio imbalances. Complements tdd-check (workflow enforcement) by enforcing the quality of tests that already exist.
From clean-code-codexnpx claudepluginhub mikecubed/agent-orchestration --plugin clean-code-codexThis skill uses the workspace's default tool permissions.
Guides Next.js Cache Components and Partial Prerendering (PPR) with cacheComponents enabled. Implements 'use cache', cacheLife(), cacheTag(), revalidateTag(), static/dynamic optimization, and cache debugging.
Migrates code, prompts, and API calls from Claude Sonnet 4.0/4.5 or Opus 4.1 to Opus 4.5, updating model strings on Anthropic, AWS, GCP, Azure platforms.
Details PluginEval's skill quality evaluation: 3 layers (static, LLM judge), 10 dimensions, rubrics, formulas, anti-patterns, badges. Use to interpret scores, improve triggering, calibrate thresholds.
Precedence in the overall system: SEC → TDD → ARCH/TYPE → TEST-1, TEST-2 (BLOCK) → TEST-3 through TEST-8.
Severity: BLOCK | Languages: * | Source: CCC
What it prohibits: Assertions that pass without verifying meaningful behaviour. Weak assertion patterns by language:
| Language | Prohibited | Preferred |
|---|---|---|
| TypeScript/JavaScript | toBeTruthy(), toBeFalsy(), toBeDefined() without semantic reason | toBe(exact), toEqual(structure), toStrictEqual(...) |
| Python | assert x (bare assert), assertTrue(x) without message | assertEqual(a, b), assertRaises(ErrorType, fn) |
| Go | if result == nil { t.Fatal(...) } replacing a table comparison | if result != expected { t.Errorf("got %v, want %v", ...) } |
| Rust | assert!(result.is_some()) | assert_eq!(result, Some(expected_value)) |
Exemptions:
toBeDefined() / assertIsNotNone() when the contract is that a value exists
but its exact type is a separate concern — only if a comment explains the intentDetection:
toBeTruthy(), toBeFalsy(), toBeDefined() with no
subsequent assertion on the same valueassert x (no == comparison) or
assertTrue(x) / assertFalse(x) on non-boolean expressionsassert!(result.is_some()), assert!(result.is_ok())
where a assert_eq! with the inner value would be more informativeagent_action:
TEST-1 (BLOCK): Weak assertion at {file}:{line}. '{assertion}' does not verify the expected value.expect(result).toBeTruthy() → expect(result).toBe('expected-string')--fix: replace assertion with the specific matcher (requires knowing the expected value from context)Bypass prohibition: "It's just a smoke test", "I only need to check it doesn't throw" → If the behaviour has no verifiable output, the test is incomplete. Add a meaningful assertion or document as a pending test with a TEST-1 waiver and issue reference.
Severity: BLOCK | Languages: * | Source: CCC
What it prohibits: A domain layer (pure business logic, entities, value objects, use cases) with line or branch coverage below 90%. Domain code is the heart of the application and has no infrastructure dependencies — there is no excuse for low coverage here.
Domain layer heuristics (file path patterns):
src/domain/, domain/, core/, entities/, models/, use-cases/Detection:
coverage/lcov.info, .coverage,
coverage.out, tarpaulin-report.json)agent_action:
TEST-2 (BLOCK): Domain file '{file}' has {pct}% coverage (minimum: 90%).TEST-2 (BLOCK): No coverage report found. Run coverage and ensure domain layer reaches 90% before review completes.Severity: WARN | Languages: * | Source: CCC
What it prohibits: Application-layer code (controllers, services, handlers, repositories) with line or branch coverage below 80%.
Application layer heuristics (file path patterns):
src/application/, services/, controllers/, handlers/, repositories/Detection: Same as TEST-2, applied to application-layer file patterns.
agent_action:
TEST-3 (WARN): Application file '{file}' has {pct}% coverage (target: 80%).--fix: generate test stubs (not implementations) referencing the uncovered pathsSeverity: WARN | Languages: * | Source: CCC (mirrors TDD-8)
What it prohibits: Entity or value object types that lack at least one property-based test verifying their invariants. Example-based tests cannot exhaustively verify structural invariants — property tests can.
Applicable to:
Email, Money, OrderId)Language tooling:
fast-checkhypothesistesting/quick or rapidproptest or quickcheckDetection:
fc.property(, @given(, proptest!, quickcheck!, rapid.Check(agent_action:
TEST-4 (WARN): Entity '{name}' at {file} has no property tests. Invariants are not exhaustively verified.Severity: WARN | Languages: * | Source: CCC
What it prohibits: Individual unit tests that take longer than 100ms to execute. Slow unit tests signal hidden I/O, uncontrolled concurrency, or unnecessary real-time waits. Slow tests are skipped under deadline pressure.
Note: This rule applies to unit tests only — integration and end-to-end tests are exempt.
Unit test heuristics: Tests that do not spin up servers, connect to databases,
or invoke file system operations. File naming: *.test.ts, *.unit.test.*,
test_*.py (no @pytest.mark.integration).
Detection:
sleep(), time.sleep(), asyncio.sleep(),
setTimeout() inside unit test bodies — these are indicatorsagent_action:
TEST-5 (WARN): Unit test '{name}' at {file}:{line} ran in {ms}ms (limit: 100ms).--fix and cause is a sleep(N): remove the sleep and use an event-driven assertionSeverity: BLOCK | Languages: * | Source: CCC
What it prohibits: Unit tests that perform real I/O operations:
Exemptions:
@pytest.mark.integration, //go:build integration, etc.)tests/integration/ or __tests__/integration/ directoriesDetection:
fs.readFile, fs.writeFile, open(, os.path, pathlib.Path (outside mocking context)fetch(, axios., httpx., http.Get(, reqwest:: (outside mocking context)postgres://, mysql://, mongodb://)agent_action:
TEST-6 (BLOCK): Unit test '{test_name}' at {file}:{line} performs real I/O: '{call}'.jest.mock('../db/connection') / unittest.mock.patch / httptest.NewServer--fix: add the mock wrapper — but DO NOT guess the return value without contextSeverity: WARN | Languages: * | Source: CCC
What it prohibits: Functions with numeric, string, or collection inputs that lack test cases for boundary values. Boundary conditions are the most common source of off-by-one errors and null pointer exceptions.
Required boundary cases (if the function accepts the type):
| Input type | Required boundary cases |
|---|---|
| Integer / float | 0, negative, max int, min int, overflow |
| String | empty string "", single character, max-length, unicode |
| List / array | empty list, single element, maximum size |
| Optional / nullable | null / None / nil / Option::None |
| Date / time | epoch, end-of-month, leap day, timezone boundary |
Detection:
agent_action:
TEST-7 (WARN): Function '{name}' at {file}:{line} lacks boundary condition tests.--fix: generate the test stubs with the boundary values filled inSeverity: INFO | Languages: * | Source: CCC (mirrors TDD-9)
What it monitors: The ratio of test lines to implementation lines. A ratio below 1:1 does not automatically trigger a violation but indicates the test suite is likely underpowered relative to the code it covers.
Target: ≥ 1:1 (test lines : implementation lines) Report threshold: < 1:1 triggers INFO; no auto-fix; no BLOCK.
Detection:
agent_action:
TEST-8 (INFO): Test-to-implementation ratio is {ratio}:1 (target: ≥ 1:1).Report schema: see skills/conductor/shared-contracts.md.
Severity: INFO when score is 60–79%; WARN when score is < 60%
Applies to: test and review operations only (NOT write or refactor — too expensive)
What it checks: Whether the test suite can detect incorrect implementations. A mutation testing
tool introduces small code changes (e.g., flipping > to >=, removing a return statement) and
checks if at least one test fails. High mutation survival means tests are passing on wrong
implementations.
Tool detection order (stop at first available):
npx stryker --version 2>/dev/null (TypeScript/JavaScript)python3 -m mutmut --version 2>/dev/null (Python)cargo mutants --version 2>/dev/null (Rust)go-mutesting --version 2>/dev/null (Go)If no tool available: emit INFO: "Install {tool} for mutation score reporting (TEST-9)" and skip.
When tool is available: Run with --timeout 120 (time-boxed at 120 seconds; partial results acceptable).
Score thresholds:
| Score | Severity | Message |
|---|---|---|
| ≥ 80% | Pass | No finding |
| 60–79% | INFO | "Mutation score {X}% for {layer}: consider strengthening assertions" |
| < 60% | WARN | "Mutation score {X}% for {layer}: tests pass on wrong implementations — see surviving mutants" |
| Not available | INFO | "Install {tool} for mutation score reporting (TEST-9)" |
Parse output:
"Mutation score: XX.XX%" from stdoutcaught / (caught + survived) * 100 from "X out of Y mutants survived"caught / (caught + missed) * 100 from "X caught, Y missed""The mutation score is X.XX" from stdout