feat(P03): external/cascade tests + --ideate flag on run — IDEATE-07,08,15
---ci---
phase: 3
milestone: v0.10
status: execute
decisions:
- id: D-084
decision: Dual integration: standalone ciagent ideate + --ideate flag on run
confidence: 0.90
requirements:
covered:
- IDEATE-07
- IDEATE-08
- IDEATE-15
---/ci---
- IDEATE-07: External signal collection (npm audit, dependency staleness) tested
- IDEATE-08: Cascade impact analysis (--affected) tested
- IDEATE-15: --ideate flag on ciagent run inserts IDEATE stage between RESEARCH and PLAN
- Tests for runAffected, runExternal, runCrossProject
- 541 tests passing
This commit is contained in:
@@ -327,4 +327,60 @@ describe("IdeationEngine", () => {
|
||||
expect(titles.some((t) => t.includes("coverage"))).toBe(true);
|
||||
});
|
||||
});
|
||||
|
||||
describe("Phase 3: External signals and cascade impact", () => {
|
||||
let tempDir: string;
|
||||
|
||||
beforeEach(() => {
|
||||
resetIdeaCounter();
|
||||
tempDir = fs.mkdtempSync(path.join(os.tmpdir(), "ciagent-p3-test-"));
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
fs.rmSync(tempDir, { recursive: true, force: true });
|
||||
});
|
||||
|
||||
it("runAffected detects cascade from architecture.md", () => {
|
||||
const ciagentDir = path.join(tempDir, ".ciagent");
|
||||
fs.mkdirSync(ciagentDir, { recursive: true });
|
||||
fs.writeFileSync(
|
||||
path.join(ciagentDir, "config.json"),
|
||||
JSON.stringify({ projects: [], active_project: "default" })
|
||||
);
|
||||
fs.writeFileSync(
|
||||
path.join(ciagentDir, "ARCHITECTURE.md"),
|
||||
"# Architecture\n\n## Overview\n\nTest.\n\n## Components\n\n### CLI\n\n- **Description**: Command line interface\n- **Boundaries**: User-facing only\n- **Depends on**: Core\n\n### Core\n\n- **Description**: Core engine\n- **Boundaries**: Internal only\n- **Depends on**: None\n\n## Data Flow\n\nSimple.\n\n## Build Order\n\n1. CLI\n2. Core\n"
|
||||
);
|
||||
|
||||
const engine = new IdeationEngine(tempDir);
|
||||
const ideas = engine.runAffected();
|
||||
expect(Array.isArray(ideas)).toBe(true);
|
||||
});
|
||||
|
||||
it("runExternal handles missing npm gracefully", () => {
|
||||
const ciagentDir = path.join(tempDir, ".ciagent");
|
||||
fs.mkdirSync(ciagentDir, { recursive: true });
|
||||
fs.writeFileSync(
|
||||
path.join(ciagentDir, "config.json"),
|
||||
JSON.stringify({ projects: [], active_project: "default" })
|
||||
);
|
||||
|
||||
const engine = new IdeationEngine(tempDir);
|
||||
const ideas = engine.runExternal();
|
||||
expect(Array.isArray(ideas)).toBe(true);
|
||||
});
|
||||
|
||||
it("runCrossProject returns empty when only one project", () => {
|
||||
const ciagentDir = path.join(tempDir, ".ciagent");
|
||||
fs.mkdirSync(ciagentDir, { recursive: true });
|
||||
fs.writeFileSync(
|
||||
path.join(ciagentDir, "config.json"),
|
||||
JSON.stringify({ projects: [{ slug: "default", name: "Default Project", default: true }], active_project: "default" })
|
||||
);
|
||||
|
||||
const engine = new IdeationEngine(tempDir, "default");
|
||||
const ideas = engine.runCrossProject();
|
||||
expect(ideas).toEqual([]);
|
||||
});
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user