feat(FN-1540): add lint as inline quality gate in task prompts

- Add ESLint configuration (eslint.config.mjs) for TypeScript/JavaScript linting
- Update executor prompts to include lint instruction before code submission
- Add lint check to triage prompt validation workflow
- Update agent prompts to emphasize lint compliance as quality requirement
- Add lint tool to agent toolset with file-level rule disabling capability
- Include lint in CI workflow with non-blocking status
- Update tests to verify lint-inclusive prompt behavior
- Add documentation for lint integration in contributing.md
- Add changeset for @gsxdsm/fusion minor release
This commit is contained in:
gsxdsm
2026-04-10 12:48:27 -07:00
parent e685745aa3
commit d9acc10c49
13 changed files with 726 additions and 33 deletions

View File

@@ -124,15 +124,15 @@ describe("resolveAgentPrompt", () => {
expect(result).toContain("task execution agent");
});
it("built-in executor prompt requires resolving ALL test failures including unrelated", () => {
it("built-in executor prompt requires resolving ALL lint and test failures including unrelated", () => {
const result = resolveAgentPrompt("executor");
// The stricter language must be present to prevent "unrelated failure" deferrals
expect(result).toContain("Resolve ALL test failures");
expect(result).toContain("Resolve ALL lint failures and test failures");
expect(result).toContain("even if they appear unrelated or pre-existing");
expect(result).toContain("do not defer them to a separate task");
});
it("senior-engineer prompt requires resolving ALL test failures including unrelated", () => {
it("senior-engineer prompt requires resolving ALL lint and test failures including unrelated", () => {
const config: AgentPromptsConfig = {
roleAssignments: {
executor: "senior-engineer",
@@ -140,7 +140,7 @@ describe("resolveAgentPrompt", () => {
};
const result = resolveAgentPrompt("executor", config);
expect(result).toContain("Resolve ALL test failures");
expect(result).toContain("Resolve ALL lint failures and test failures");
expect(result).toContain("even if they appear unrelated or pre-existing");
expect(result).toContain("do not defer them to a separate task");
});

View File

@@ -102,7 +102,7 @@ If you attempt to write to a path outside the worktree, the file tools will reje
- Treat the File Scope in PROMPT.md as the expected starting scope, not a hard boundary when quality gates fail
- Read "Context to Read First" files before starting
- Follow the "Do NOT" section strictly
- If tests, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green
- If tests, lint, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green
- Use \`task_create\` for genuinely separate follow-up work, not for mandatory fixes required to make this task land cleanly
- Update documentation listed in "Must Update" and check "Check If Affected"
- NEVER delete, remove, or gut modules, interfaces, settings, exports, or test files outside your File Scope
@@ -139,7 +139,7 @@ spawn_agent({
- Max 20 total spawned agents system-wide (configurable via settings)
## Completion
After all steps are done, tests pass, typecheck passes, and docs are updated:
After all steps are done, lint passes, tests pass, typecheck passes, and docs are updated:
\`\`\`bash
Call \`task_done()\` to signal completion.
\`\`\`
@@ -149,11 +149,11 @@ If a project build command is listed in the prompt, it is a hard completion gate
- Do not claim the build passes unless you actually ran it and got exit code 0
- If the build fails, do NOT call \`task_done()\`; keep working until it passes
Tests and typecheck are also hard quality gates:
- Keep fixing failures until the configured/full test suite passes
Lint, tests, and typecheck are also hard quality gates:
- Keep fixing failures until lint, the configured/full test suite, and typecheck all pass
- If the repository exposes a typecheck command, run it and keep fixing failures until it passes
- Do not stop at "out of scope" if additional fixes are required to restore green tests, build, or typecheck
- **CRITICAL: Resolve ALL test failures before completing the task, even if they appear unrelated or pre-existing.** Unrelated failures left unfixed accumulate technical debt and block future integrations. Investigate and fix or suppress them — do not defer them to a separate task.`;
- Do not stop at "out of scope" if additional fixes are required to restore green lint, tests, build, or typecheck
- **CRITICAL: Resolve ALL lint failures and test failures before completing the task, even if they appear unrelated or pre-existing.** Unrelated failures left unfixed accumulate technical debt and block future integrations. Investigate and fix or suppress them — do not defer them to a separate task.`;
const TRIAGE_PROMPT_TEXT = `You are a task specification agent for "fn", an AI-orchestrated task board.
@@ -221,8 +221,9 @@ Follow this structure exactly:
### Step {N-1}: Testing & Verification
> ZERO test failures allowed. Full test suite as quality gate.
> If keeping tests/build/typecheck green requires edits outside the initial File Scope, make those fixes as part of this task.
> If keeping lint/tests/build/typecheck green requires edits outside the initial File Scope, make those fixes as part of this task.
- [ ] Run lint check (\`pnpm lint\`)
- [ ] Run full test suite
- [ ] Run project typecheck if available
- [ ] Fix all failures
@@ -244,6 +245,7 @@ Follow this structure exactly:
## Completion Criteria
- [ ] All steps complete
- [ ] Lint passing
- [ ] All tests passing
- [ ] Build passing
- [ ] Documentation updated
@@ -486,7 +488,7 @@ If you attempt to write to a path outside the worktree, the file tools will reje
- Treat the File Scope in PROMPT.md as the expected starting scope, not a hard boundary when quality gates fail
- Read "Context to Read First" files before starting
- Follow the "Do NOT" section strictly
- If tests, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green
- If tests, lint, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green
- Use \`task_create\` for genuinely separate follow-up work, not for mandatory fixes required to make this task land cleanly
- NEVER delete, remove, or gut modules, interfaces, settings, exports, or test files outside your File Scope
- NEVER remove features as "cleanup" — if something seems unused, create a task for investigation instead
@@ -511,14 +513,14 @@ spawn_agent({
- When you end (task_done), all spawned children are terminated
## Completion
After all steps are done, tests pass, typecheck passes, and docs are updated:
After all steps are done, lint passes, tests pass, typecheck passes, and docs are updated:
\`\`\`bash
Call \`task_done()\` to signal completion.
\`\`\`
If a project build command is listed in the prompt, it is a hard completion gate.
Tests and typecheck are also hard quality gates — keep fixing until green.
**CRITICAL: Resolve ALL test failures before completing the task, even if they appear unrelated or pre-existing.** Unrelated failures left unfixed accumulate technical debt and block future integrations. Investigate and fix or suppress them — do not defer them to a separate task.`;
Lint, tests, and typecheck are also hard quality gates — keep fixing until green.
**CRITICAL: Resolve ALL lint failures and test failures before completing the task, even if they appear unrelated or pre-existing.** Unrelated failures left unfixed accumulate technical debt and block future integrations. Investigate and fix or suppress them — do not defer them to a separate task.`;
const STRICT_REVIEWER_PROMPT_TEXT = `You are a strict code and plan reviewer with rigorous standards.

View File

@@ -88,7 +88,7 @@ You are working in a git worktree isolated from the main branch. Your job is to
- Treat the File Scope in PROMPT.md as the expected starting scope, not a hard boundary when quality gates fail
- Read "Context to Read First" files before starting
- Follow the "Do NOT" section strictly
- If tests, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green`,
- If tests, lint, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green`,
},
"executor-spawning": {
key: "executor-spawning",
@@ -119,7 +119,7 @@ spawn_agent({
roles: ["executor"],
description: "Completion criteria and signaling for executor",
defaultContent: `## Completion
After all steps are done, tests pass, typecheck passes, and docs are updated:
After all steps are done, lint passes, tests pass, typecheck passes, and docs are updated:
\`\`\`bash
Call \`task_done()\` to signal completion.
\`\`\``,

View File

@@ -218,7 +218,7 @@ If you attempt to write to a path outside the worktree, the file tools will reje
- Treat the File Scope in PROMPT.md as the expected starting scope, not a hard boundary when quality gates fail
- Read "Context to Read First" files before starting
- Follow the "Do NOT" section strictly
- If tests, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green
- If tests, lint, build, or typecheck fail and the fix requires touching code outside the declared File Scope, fix those failures directly and keep the repo green
- Use \`task_create\` for genuinely separate follow-up work, not for mandatory fixes required to make this task land cleanly
- Update documentation listed in "Must Update" and check "Check If Affected"
- NEVER delete, remove, or gut modules, interfaces, settings, exports, or test files outside your File Scope
@@ -255,7 +255,7 @@ spawn_agent({
- Max 20 total spawned agents system-wide (configurable via settings)
## Completion
After all steps are done, tests pass, typecheck passes, and docs are updated:
After all steps are done, lint passes, tests pass, typecheck passes, and docs are updated:
\`\`\`bash
Call \`task_done()\` to signal completion.
\`\`\`
@@ -265,11 +265,11 @@ If a project build command is listed in the prompt, it is a hard completion gate
- Do not claim the build passes unless you actually ran it and got exit code 0
- If the build fails, do NOT call \`task_done()\`; keep working until it passes
Tests and typecheck are also hard quality gates:
- Keep fixing failures until the configured/full test suite passes
Lint, tests, and typecheck are also hard quality gates:
- Keep fixing failures until lint, the configured/full test suite, and typecheck all pass
- If the repository exposes a typecheck command, run it and keep fixing failures until it passes
- Do not stop at "out of scope" if additional fixes are required to restore green tests, build, or typecheck
- **CRITICAL: Resolve ALL test failures before completing the task, even if they appear unrelated or pre-existing.** Unrelated failures left unfixed accumulate technical debt and block future integrations. Investigate and fix or suppress them — do not defer them to a separate task.`;
- Do not stop at "out of scope" if additional fixes are required to restore green lint, tests, build, or typecheck
- **CRITICAL: Resolve ALL lint failures and test failures before completing the task, even if they appear unrelated or pre-existing.** Unrelated failures left unfixed accumulate technical debt and block future integrations. Investigate and fix or suppress them — do not defer them to a separate task.`;
/** Resolve the executor system prompt from settings, falling back to the hardcoded constant. */
function getExecutorSystemPrompt(settings: Settings): string {

View File

@@ -375,11 +375,13 @@ describe("buildSpecificationPrompt", () => {
});
describe("TRIAGE_SYSTEM_PROMPT", () => {
it("requires specs to keep tests, build, and typecheck green even outside initial file scope", () => {
expect(TRIAGE_SYSTEM_PROMPT).toContain("If keeping tests/build/typecheck green requires edits outside the initial File Scope");
it("requires specs to keep lint, tests, build, and typecheck green even outside initial file scope", () => {
expect(TRIAGE_SYSTEM_PROMPT).toContain("If keeping lint/tests/build/typecheck green requires edits outside the initial File Scope");
expect(TRIAGE_SYSTEM_PROMPT).toContain("Run lint check");
expect(TRIAGE_SYSTEM_PROMPT).toContain("Run project typecheck if available");
expect(TRIAGE_SYSTEM_PROMPT).toContain("Lint passing");
expect(TRIAGE_SYSTEM_PROMPT).toContain("Typecheck passing (if available)");
expect(TRIAGE_SYSTEM_PROMPT).toContain("Specs must instruct executors to fix quality-gate failures directly");
expect(TRIAGE_SYSTEM_PROMPT).toContain("Specs must instruct executors to fix lint failures and quality-gate failures directly");
expect(TRIAGE_SYSTEM_PROMPT).toContain("Refuse necessary fixes just because they touch files outside the initial File Scope");
});
});

View File

@@ -100,8 +100,9 @@ Follow this structure exactly:
### Step {N-1}: Testing & Verification
> ZERO test failures allowed. Full test suite as quality gate.
> If keeping tests/build/typecheck green requires edits outside the initial File Scope, make those fixes as part of this task.
> If keeping lint/tests/build/typecheck green requires edits outside the initial File Scope, make those fixes as part of this task.
- [ ] Run lint check (\`pnpm lint\`)
- [ ] Run full test suite
- [ ] Run project typecheck if available
- [ ] Fix all failures
@@ -123,6 +124,7 @@ Follow this structure exactly:
## Completion Criteria
- [ ] All steps complete
- [ ] Lint passing
- [ ] All tests passing
- [ ] Typecheck passing (if available)
- [ ] Documentation updated
@@ -158,9 +160,8 @@ files with assertions that run via a test runner. Typechecks and builds are NOT
tests. Manual verification is NOT a test.
- Each implementation step should include writing tests for the code being changed
- The final Testing step runs the FULL test suite
- The final Testing step also runs project typecheck when the repo exposes one
- Specs must instruct executors to fix quality-gate failures directly, even when the required edits extend beyond the original File Scope
- The final Testing step runs lint, the FULL test suite, and project typecheck when the repo exposes one
- Specs must instruct executors to fix lint failures and quality-gate failures directly, even when the required edits extend beyond the original File Scope
- If the project has no test framework, the Testing step must include setting one up
as part of this task (not just skipping tests)