tempo-agent 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md ADDED
@@ -0,0 +1,129 @@
1
+ # Tempo
2
+
3
+ AI-driven code generation CLI. Give Tempo a goal, and it writes, validates, and retries code changes step by step using Claude.
4
+
5
+ ## Install
6
+
7
+ ```bash
8
+ npm install -g tempo-agent
9
+ ```
10
+
11
+ ## Requirements
12
+
13
+ Set your Anthropic API key:
14
+
15
+ ```bash
16
+ export ANTHROPIC_API_KEY=your-key-here
17
+ ```
18
+
19
+ ## Usage
20
+
21
+ ### 1. Initialize a project
22
+
23
+ Run this inside any existing project:
24
+
25
+ ```bash
26
+ tempo init
27
+ ```
28
+
29
+ Creates a `.tempo/` directory with config and folders for scores, sessions, and ideation files.
30
+
31
+ ### 2. Write an ideation file
32
+
33
+ Create a markdown file in `.tempo/ideation/my-feature.md`:
34
+
35
+ ```markdown
36
+ # Goal
37
+ Build a REST API for a todo list
38
+
39
+ # Context
40
+ - Use Express.js
41
+ - Use TypeScript
42
+ - Store data in memory
43
+
44
+ # Ideas
45
+ - Add pagination
46
+ - Add filtering by status
47
+
48
+ # Final Plan
49
+ 1. Create Express server entry point
50
+ 2. Add todo routes (GET, POST, PUT, DELETE)
51
+ 3. Add in-memory store module
52
+ ```
53
+
54
+ ### 3. Compile it into a score
55
+
56
+ ```bash
57
+ tempo compile my-feature.md
58
+ ```
59
+
60
+ Generates `.tempo/scores/my-feature.json` — a structured execution plan.
61
+
62
+ ### 4. Edit the score
63
+
64
+ Open `.tempo/scores/my-feature.json` and fill in `files_allowed` for each step — the list of files Claude is permitted to create or modify:
65
+
66
+ ```json
67
+ {
68
+ "steps": [
69
+ {
70
+ "id": 1,
71
+ "description": "Create Express server entry point",
72
+ "files_allowed": ["src/index.ts"]
73
+ }
74
+ ]
75
+ }
76
+ ```
77
+
78
+ ### 5. Run it
79
+
80
+ ```bash
81
+ tempo run my-feature
82
+ ```
83
+
84
+ Tempo will:
85
+ - Send each step to Claude with the current file contents
86
+ - Write Claude's response back to disk
87
+ - Run lint, build, and tests
88
+ - Retry up to 3 times on failure, feeding errors back to Claude
89
+ - Save a full session log to `.tempo/sessions/`
90
+
91
+ ## Config
92
+
93
+ `.tempo/config.json` controls which commands are used for validation:
94
+
95
+ ```json
96
+ {
97
+ "testCommand": "npm test",
98
+ "buildCommand": "npm run build",
99
+ "lintCommand": "npm run lint"
100
+ }
101
+ ```
102
+
103
+ Set any value to `null` to skip that step.
104
+
105
+ ## Session History
106
+
107
+ Every run is saved to `.tempo/sessions/session-{timestamp}/`:
108
+
109
+ | File | Contents |
110
+ |---|---|
111
+ | `step-N.md` | Prompt sent, files used, Claude response, result |
112
+ | `errors-step-N.md` | Validation errors and retry attempts |
113
+ | `diff-N.patch` | Git diff after each step |
114
+
115
+ Add to your `.gitignore`:
116
+
117
+ ```
118
+ .tempo/sessions/
119
+ .tempo/runs/
120
+ ```
121
+
122
+ ## How it works
123
+
124
+ 1. Reads the files listed in `files_allowed` for the current step
125
+ 2. Sends them to Claude with the step instruction
126
+ 3. Claude returns full file replacements
127
+ 4. Tempo writes them to disk
128
+ 5. Runs validation — if it fails, sends the errors back to Claude and retries
129
+ 6. Moves to the next step once validation passes
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":""}
@@ -0,0 +1,136 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ var __importDefault = (this && this.__importDefault) || function (mod) {
4
+ return (mod && mod.__esModule) ? mod : { "default": mod };
5
+ };
6
+ Object.defineProperty(exports, "__esModule", { value: true });
7
+ const fs_1 = __importDefault(require("fs"));
8
+ const path_1 = __importDefault(require("path"));
9
+ const chalk_1 = __importDefault(require("chalk"));
10
+ const schema_1 = require("../spec/schema");
11
+ const runPipeline_1 = require("../controller/runPipeline");
12
+ const compile_1 = require("../ideation/compile");
13
+ const cwd = process.cwd();
14
+ function printHelp() {
15
+ console.log(chalk_1.default.bold('\nTempo — AI-driven code generation CLI\n'));
16
+ console.log('Usage:');
17
+ console.log(' tempo init Initialize .tempo/ in current directory');
18
+ console.log(' tempo compile <file> Compile a markdown ideation file to a score');
19
+ console.log(' tempo run <score-name> Run a score from .tempo/scores/<name>.json');
20
+ console.log('');
21
+ }
22
+ function cmdInit() {
23
+ const tempoDir = path_1.default.join(cwd, '.tempo');
24
+ const dirs = ['ideation', 'scores', 'sessions', 'runs'];
25
+ fs_1.default.mkdirSync(tempoDir, { recursive: true });
26
+ for (const d of dirs) {
27
+ fs_1.default.mkdirSync(path_1.default.join(tempoDir, d), { recursive: true });
28
+ }
29
+ const configPath = path_1.default.join(tempoDir, 'config.json');
30
+ if (!fs_1.default.existsSync(configPath)) {
31
+ fs_1.default.writeFileSync(configPath, JSON.stringify({
32
+ testCommand: 'npm test',
33
+ buildCommand: 'npm run build',
34
+ lintCommand: 'npm run lint',
35
+ }, null, 2), 'utf-8');
36
+ }
37
+ const rulesPath = path_1.default.join(tempoDir, 'rules.md');
38
+ if (!fs_1.default.existsSync(rulesPath)) {
39
+ fs_1.default.writeFileSync(rulesPath, `# Tempo Rules
40
+
41
+ ## Code Style
42
+ - Use TypeScript
43
+ - Use async/await
44
+ - Keep functions small and focused
45
+
46
+ ## Safety
47
+ - Only modify files listed in files_allowed
48
+ - Never delete files not explicitly listed
49
+
50
+ ## .gitignore suggestions
51
+ Add these to your .gitignore:
52
+ .tempo/sessions/
53
+ .tempo/runs/
54
+ `, 'utf-8');
55
+ }
56
+ console.log(chalk_1.default.green('✓ Initialized .tempo/ directory'));
57
+ console.log(chalk_1.default.blue(' .tempo/config.json — validation commands'));
58
+ console.log(chalk_1.default.blue(' .tempo/rules.md — agent behavior rules'));
59
+ console.log(chalk_1.default.blue(' .tempo/ideation/ — place your .md ideation files here'));
60
+ console.log(chalk_1.default.blue(' .tempo/scores/ — compiled score JSONs'));
61
+ console.log(chalk_1.default.blue(' .tempo/sessions/ — execution history per run'));
62
+ console.log('');
63
+ console.log(chalk_1.default.yellow('Tip: add .tempo/sessions/ and .tempo/runs/ to your .gitignore'));
64
+ }
65
+ function cmdCompile(args) {
66
+ const fileName = args[0];
67
+ if (!fileName) {
68
+ console.error(chalk_1.default.red('Usage: tempo compile <file>'));
69
+ process.exit(1);
70
+ }
71
+ const filePath = path_1.default.isAbsolute(fileName)
72
+ ? fileName
73
+ : path_1.default.join(cwd, '.tempo', 'ideation', fileName);
74
+ try {
75
+ const outPath = (0, compile_1.compileIdeation)(filePath, cwd);
76
+ console.log(chalk_1.default.green(`✓ Score compiled → ${outPath}`));
77
+ }
78
+ catch (err) {
79
+ console.error(chalk_1.default.red(`Error: ${err.message}`));
80
+ process.exit(1);
81
+ }
82
+ }
83
+ async function cmdRun(args) {
84
+ const scoreName = args[0];
85
+ if (!scoreName) {
86
+ console.error(chalk_1.default.red('Usage: tempo run <score-name>'));
87
+ process.exit(1);
88
+ }
89
+ const scorePath = path_1.default.join(cwd, '.tempo', 'scores', `${scoreName}.json`);
90
+ if (!fs_1.default.existsSync(scorePath)) {
91
+ console.error(chalk_1.default.red(`Score not found: ${scorePath}`));
92
+ process.exit(1);
93
+ }
94
+ let raw;
95
+ try {
96
+ raw = JSON.parse(fs_1.default.readFileSync(scorePath, 'utf-8'));
97
+ }
98
+ catch {
99
+ console.error(chalk_1.default.red('Failed to parse score JSON'));
100
+ process.exit(1);
101
+ }
102
+ const parsed = schema_1.SpecSchema.safeParse(raw);
103
+ if (!parsed.success) {
104
+ console.error(chalk_1.default.red('Invalid score:'));
105
+ console.error(parsed.error.format());
106
+ process.exit(1);
107
+ }
108
+ await (0, runPipeline_1.runPipeline)(parsed.data, cwd);
109
+ }
110
+ async function main() {
111
+ const [, , command, ...args] = process.argv;
112
+ if (!command || command === 'help' || command === '--help') {
113
+ printHelp();
114
+ return;
115
+ }
116
+ switch (command) {
117
+ case 'init':
118
+ cmdInit();
119
+ break;
120
+ case 'compile':
121
+ cmdCompile(args);
122
+ break;
123
+ case 'run':
124
+ await cmdRun(args);
125
+ break;
126
+ default:
127
+ console.error(chalk_1.default.red(`Unknown command: ${command}`));
128
+ printHelp();
129
+ process.exit(1);
130
+ }
131
+ }
132
+ main().catch((err) => {
133
+ console.error(chalk_1.default.red('Fatal error:'), err.message);
134
+ process.exit(1);
135
+ });
136
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":";;;;;;AAEA,4CAAoB;AACpB,gDAAwB;AACxB,kDAA0B;AAC1B,2CAA4C;AAC5C,2DAAwD;AACxD,iDAAsD;AAEtD,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC;AAE1B,SAAS,SAAS;IAChB,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,2CAA2C,CAAC,CAAC,CAAC;IACrE,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;IACtB,OAAO,CAAC,GAAG,CAAC,uEAAuE,CAAC,CAAC;IACrF,OAAO,CAAC,GAAG,CAAC,2EAA2E,CAAC,CAAC;IACzF,OAAO,CAAC,GAAG,CAAC,0EAA0E,CAAC,CAAC;IACxF,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;AAClB,CAAC;AAED,SAAS,OAAO;IACd,MAAM,QAAQ,GAAG,cAAI,CAAC,IAAI,CAAC,GAAG,EAAE,QAAQ,CAAC,CAAC;IAC1C,MAAM,IAAI,GAAG,CAAC,UAAU,EAAE,QAAQ,EAAE,UAAU,EAAE,MAAM,CAAC,CAAC;IAExD,YAAE,CAAC,SAAS,CAAC,QAAQ,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC5C,KAAK,MAAM,CAAC,IAAI,IAAI,EAAE,CAAC;QACrB,YAAE,CAAC,SAAS,CAAC,cAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC5D,CAAC;IAED,MAAM,UAAU,GAAG,cAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,aAAa,CAAC,CAAC;IACtD,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QAC/B,YAAE,CAAC,aAAa,CACd,UAAU,EACV,IAAI,CAAC,SAAS,CACZ;YACE,WAAW,EAAE,UAAU;YACvB,YAAY,EAAE,eAAe;YAC7B,WAAW,EAAE,cAAc;SAC5B,EACD,IAAI,EACJ,CAAC,CACF,EACD,OAAO,CACR,CAAC;IACJ,CAAC;IAED,MAAM,SAAS,GAAG,cAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAC;IAClD,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;QAC9B,YAAE,CAAC,aAAa,CACd,SAAS,EACT;;;;;;;;;;;;;;;CAeL,EACK,OAAO,CACR,CAAC;IACJ,CAAC;IAED,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,KAAK,CAAC,iCAAiC,CAAC,CAAC,CAAC;IAC5D,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,6CAA6C,CAAC,CAAC,CAAC;IACvE,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,8CAA8C,CAAC,CAAC,CAAC;IACxE,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,4DAA4D,CAAC,CAAC,CAAC;IACtF,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,8CAA8C,CAAC,CAAC,CAAC;IACxE,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,mDAAmD,CAAC,CAAC,CAAC;IAC7E,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;IAChB,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,MAAM,CAAC,+DAA+D,CAAC,CAAC,CAAC;AAC7F,CAAC;AAED,SAAS,UAAU,CAAC,IAAc;IAChC,MAAM,QAAQ,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IACzB,IAAI,CAAC,QAAQ,EAAE,CAAC;QACd,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,6BAA6B,CAAC,CAAC,CAAC;QACxD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,MAAM,QAAQ,GAAG,cAAI,CAAC,UAAU,CAAC,QAAQ,CAAC;QACxC,CAAC,CAAC,QAAQ;QACV,CAAC,CAAC,cAAI,CAAC,IAAI,CAAC,GAAG,EAAE,QAAQ,EAAE,UAAU,EAAE,QAAQ,CAAC,CAAC;IAEnD,IAAI,CAAC;QACH,MAAM,OAAO,GAAG,IAAA,yBAAe,EAAC,QAAQ,EAAE,GAAG,CAAC,CAAC;QAC/C,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,KAAK,CAAC,sBAAsB,OAAO,EAAE,CAAC,CAAC,CAAC;IAC5D,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,UAAW,GAAa,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;QAC7D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;AACH,CAAC;AAED,KAAK,UAAU,MAAM,CAAC,IAAc;IAClC,MAAM,SAAS,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IAC1B,IAAI,CAAC,SAAS,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,+BAA+B,CAAC,CAAC,CAAC;QAC1D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,MAAM,SAAS,GAAG,cAAI,CAAC,IAAI,CAAC,GAAG,EAAE,QAAQ,EAAE,QAAQ,EAAE,GAAG,SAAS,OAAO,CAAC,CAAC;IAC1E,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;QAC9B,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,oBAAoB,SAAS,EAAE,CAAC,CAAC,CAAC;QAC1D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,IAAI,GAAY,CAAC;IACjB,IAAI,CAAC;QACH,GAAG,GAAG,IAAI,CAAC,KAAK,CAAC,YAAE,CAAC,YAAY,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC,CAAC;IACxD,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,4BAA4B,CAAC,CAAC,CAAC;QACvD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,MAAM,MAAM,GAAG,mBAAU,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC;IACzC,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE,CAAC;QACpB,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,gBAAgB,CAAC,CAAC,CAAC;QAC3C,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC;QACrC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IAED,MAAM,IAAA,yBAAW,EAAC,MAAM,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;AACtC,CAAC;AAED,KAAK,UAAU,IAAI;IACjB,MAAM,CAAC,EAAE,AAAD,EAAG,OAAO,EAAE,GAAG,IAAI,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC;IAE5C,IAAI,CAAC,OAAO,IAAI,OAAO,KAAK,MAAM,IAAI,OAAO,KAAK,QAAQ,EAAE,CAAC;QAC3D,SAAS,EAAE,CAAC;QACZ,OAAO;IACT,CAAC;IAED,QAAQ,OAAO,EAAE,CAAC;QAChB,KAAK,MAAM;YACT,OAAO,EAAE,CAAC;YACV,MAAM;QACR,KAAK,SAAS;YACZ,UAAU,CAAC,IAAI,CAAC,CAAC;YACjB,MAAM;QACR,KAAK,KAAK;YACR,MAAM,MAAM,CAAC,IAAI,CAAC,CAAC;YACnB,MAAM;QACR;YACE,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,oBAAoB,OAAO,EAAE,CAAC,CAAC,CAAC;YACxD,SAAS,EAAE,CAAC;YACZ,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IACpB,CAAC;AACH,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;IACnB,OAAO,CAAC,KAAK,CAAC,eAAK,CAAC,GAAG,CAAC,cAAc,CAAC,EAAE,GAAG,CAAC,OAAO,CAAC,CAAC;IACtD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC,CAAC,CAAC"}
@@ -0,0 +1,3 @@
1
+ import { Spec } from '../spec/schema';
2
+ export declare function runPipeline(spec: Spec, cwd: string): Promise<void>;
3
+ //# sourceMappingURL=runPipeline.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runPipeline.d.ts","sourceRoot":"","sources":["../../src/controller/runPipeline.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,IAAI,EAAE,MAAM,gBAAgB,CAAC;AA2EtC,wBAAsB,WAAW,CAAC,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAkExE"}
@@ -0,0 +1,109 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.runPipeline = runPipeline;
7
+ const path_1 = __importDefault(require("path"));
8
+ const fs_1 = __importDefault(require("fs"));
9
+ const execa_1 = __importDefault(require("execa"));
10
+ const runStep_1 = require("../executor/runStep");
11
+ const runValidation_1 = require("../validator/runValidation");
12
+ const logger_1 = require("../utils/logger");
13
+ const MAX_RETRIES = 3;
14
+ function ensureHistoryDir(cwd, runTimestamp) {
15
+ const dir = path_1.default.join(cwd, '.tempo', 'sessions', `session-${runTimestamp}`);
16
+ fs_1.default.mkdirSync(dir, { recursive: true });
17
+ return dir;
18
+ }
19
+ function saveStepHistory(historyDir, stepId, instruction, filesAllowed, claudeResponse, result) {
20
+ const content = `# Step ${stepId}
21
+
22
+ ## Instruction Sent to Claude
23
+
24
+ \`\`\`
25
+ ${instruction}
26
+ \`\`\`
27
+
28
+ ## Files Allowed
29
+
30
+ ${filesAllowed.map((f) => `- ${f}`).join('\n')}
31
+
32
+ ## Claude Response
33
+
34
+ \`\`\`
35
+ ${claudeResponse}
36
+ \`\`\`
37
+
38
+ ## Result
39
+
40
+ ${result}
41
+ `;
42
+ fs_1.default.writeFileSync(path_1.default.join(historyDir, `step-${stepId}.md`), content, 'utf-8');
43
+ }
44
+ function saveErrors(historyDir, stepId, errors, retries) {
45
+ const content = `# Errors for Step ${stepId}
46
+
47
+ Retries attempted: ${retries}
48
+
49
+ ## Raw Output
50
+
51
+ \`\`\`
52
+ ${errors}
53
+ \`\`\`
54
+ `;
55
+ fs_1.default.writeFileSync(path_1.default.join(historyDir, `errors-step-${stepId}.md`), content, 'utf-8');
56
+ }
57
+ async function captureAndSaveDiff(historyDir, stepId, cwd) {
58
+ try {
59
+ const result = await (0, execa_1.default)('git', ['diff'], { cwd, reject: false });
60
+ if (result.stdout) {
61
+ fs_1.default.writeFileSync(path_1.default.join(historyDir, `diff-${stepId}.patch`), result.stdout, 'utf-8');
62
+ }
63
+ }
64
+ catch {
65
+ // git not available — skip diff
66
+ }
67
+ }
68
+ async function runPipeline(spec, cwd) {
69
+ const runTimestamp = new Date().toISOString().replace(/[:.]/g, '-');
70
+ const historyDir = ensureHistoryDir(cwd, runTimestamp);
71
+ (0, logger_1.logInfo)(`Starting pipeline: ${spec.goal}`);
72
+ (0, logger_1.logInfo)(`Session: .tempo/sessions/session-${runTimestamp}`);
73
+ let passed = 0;
74
+ let failed = 0;
75
+ for (const step of spec.steps) {
76
+ (0, logger_1.logStep)(step.id, step.description);
77
+ let lastErrors = '';
78
+ let succeeded = false;
79
+ for (let attempt = 1; attempt <= MAX_RETRIES; attempt++) {
80
+ const extraContext = attempt > 1
81
+ ? `Fix only these errors:\n${lastErrors}`
82
+ : undefined;
83
+ const stepResult = await (0, runStep_1.runStep)(step, spec, cwd, extraContext);
84
+ await captureAndSaveDiff(historyDir, step.id, cwd);
85
+ const validation = await (0, runValidation_1.runValidation)(cwd);
86
+ if (validation.success) {
87
+ (0, logger_1.logSuccess)(`Step ${step.id} passed validation`);
88
+ saveStepHistory(historyDir, step.id, stepResult.instruction, stepResult.filesAllowed, stepResult.claudeResponse, 'success');
89
+ succeeded = true;
90
+ passed++;
91
+ break;
92
+ }
93
+ lastErrors = validation.errors;
94
+ (0, logger_1.logRetry)(attempt, MAX_RETRIES, validation.errors);
95
+ if (attempt === MAX_RETRIES) {
96
+ saveErrors(historyDir, step.id, validation.errors, attempt);
97
+ saveStepHistory(historyDir, step.id, stepResult.instruction, stepResult.filesAllowed, stepResult.claudeResponse, 'failure');
98
+ }
99
+ }
100
+ if (!succeeded) {
101
+ (0, logger_1.logFailure)(`Step ${step.id} failed after ${MAX_RETRIES} retries. Stopping pipeline.`);
102
+ failed++;
103
+ (0, logger_1.logSummary)(passed, failed, spec.steps.length);
104
+ process.exit(1);
105
+ }
106
+ }
107
+ (0, logger_1.logSummary)(passed, failed, spec.steps.length);
108
+ }
109
+ //# sourceMappingURL=runPipeline.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runPipeline.js","sourceRoot":"","sources":["../../src/controller/runPipeline.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function callClaude(systemPrompt: string, userPrompt: string): Promise<string>;
2
+ //# sourceMappingURL=claudeClient.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"claudeClient.d.ts","sourceRoot":"","sources":["../../src/executor/claudeClient.ts"],"names":[],"mappings":"AAKA,wBAAsB,UAAU,CAAC,YAAY,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CA4B1F"}
@@ -0,0 +1,33 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.callClaude = callClaude;
7
+ const axios_1 = __importDefault(require("axios"));
8
+ const CLAUDE_API_URL = 'https://api.anthropic.com/v1/messages';
9
+ const DEFAULT_MODEL = 'claude-sonnet-4-6';
10
+ async function callClaude(systemPrompt, userPrompt) {
11
+ const apiKey = process.env.ANTHROPIC_API_KEY;
12
+ if (!apiKey) {
13
+ throw new Error('ANTHROPIC_API_KEY environment variable is not set');
14
+ }
15
+ const response = await axios_1.default.post(CLAUDE_API_URL, {
16
+ model: DEFAULT_MODEL,
17
+ max_tokens: 8192,
18
+ system: systemPrompt,
19
+ messages: [{ role: 'user', content: userPrompt }],
20
+ }, {
21
+ headers: {
22
+ 'x-api-key': apiKey,
23
+ 'anthropic-version': '2023-06-01',
24
+ 'content-type': 'application/json',
25
+ },
26
+ });
27
+ const block = response.data.content?.[0];
28
+ if (!block || block.type !== 'text') {
29
+ throw new Error('Unexpected response format from Claude API');
30
+ }
31
+ return block.text;
32
+ }
33
+ //# sourceMappingURL=claudeClient.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"claudeClient.js","sourceRoot":"","sources":["../../src/executor/claudeClient.ts"],"names":[],"mappings":";;;;;AAKA,gCA4BC;AAjCD,kDAA0B;AAE1B,MAAM,cAAc,GAAG,uCAAuC,CAAC;AAC/D,MAAM,aAAa,GAAG,mBAAmB,CAAC;AAEnC,KAAK,UAAU,UAAU,CAAC,YAAoB,EAAE,UAAkB;IACvE,MAAM,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,iBAAiB,CAAC;IAC7C,IAAI,CAAC,MAAM,EAAE,CAAC;QACZ,MAAM,IAAI,KAAK,CAAC,mDAAmD,CAAC,CAAC;IACvE,CAAC;IAED,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,IAAI,CAC/B,cAAc,EACd;QACE,KAAK,EAAE,aAAa;QACpB,UAAU,EAAE,IAAI;QAChB,MAAM,EAAE,YAAY;QACpB,QAAQ,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,CAAC;KAClD,EACD;QACE,OAAO,EAAE;YACP,WAAW,EAAE,MAAM;YACnB,mBAAmB,EAAE,YAAY;YACjC,cAAc,EAAE,kBAAkB;SACnC;KACF,CACF,CAAC;IAEF,MAAM,KAAK,GAAG,QAAQ,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,CAAC;IACzC,IAAI,CAAC,KAAK,IAAI,KAAK,CAAC,IAAI,KAAK,MAAM,EAAE,CAAC;QACpC,MAAM,IAAI,KAAK,CAAC,4CAA4C,CAAC,CAAC;IAChE,CAAC;IACD,OAAO,KAAK,CAAC,IAAc,CAAC;AAC9B,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { Step, Spec } from '../spec/schema';
2
+ export interface StepResult {
3
+ stepId: number;
4
+ instruction: string;
5
+ filesAllowed: string[];
6
+ claudeResponse: string;
7
+ filesWritten: string[];
8
+ }
9
+ export declare function runStep(step: Step, spec: Spec, cwd: string, extraContext?: string): Promise<StepResult>;
10
+ //# sourceMappingURL=runStep.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runStep.d.ts","sourceRoot":"","sources":["../../src/executor/runStep.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,MAAM,gBAAgB,CAAC;AAqB5C,MAAM,WAAW,UAAU;IACzB,MAAM,EAAE,MAAM,CAAC;IACf,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,cAAc,EAAE,MAAM,CAAC;IACvB,YAAY,EAAE,MAAM,EAAE,CAAC;CACxB;AA0CD,wBAAsB,OAAO,CAC3B,IAAI,EAAE,IAAI,EACV,IAAI,EAAE,IAAI,EACV,GAAG,EAAE,MAAM,EACX,YAAY,CAAC,EAAE,MAAM,GACpB,OAAO,CAAC,UAAU,CAAC,CAoCrB"}
@@ -0,0 +1,97 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.runStep = runStep;
7
+ const fs_1 = __importDefault(require("fs"));
8
+ const path_1 = __importDefault(require("path"));
9
+ const claudeClient_1 = require("./claudeClient");
10
+ const logger_1 = require("../utils/logger");
11
+ const SYSTEM_PROMPT = `You are an expert software engineer. You will receive:
12
+ 1. A task description
13
+ 2. The contents of files you are allowed to modify
14
+ 3. Project constraints
15
+
16
+ Respond ONLY with complete file replacements in this exact format for each file:
17
+
18
+ ===FILE: path/to/file.ts===
19
+ <full file content here>
20
+ ===END===
21
+
22
+ Rules:
23
+ - Output FULL file content, never partial edits
24
+ - Only output files listed in "files_allowed"
25
+ - Do not add explanations outside the file blocks
26
+ - Preserve existing code that is not being changed`;
27
+ function readAllowedFiles(filesAllowed, cwd) {
28
+ const contents = {};
29
+ for (const filePath of filesAllowed) {
30
+ const abs = path_1.default.resolve(cwd, filePath);
31
+ if (fs_1.default.existsSync(abs)) {
32
+ contents[filePath] = fs_1.default.readFileSync(abs, 'utf-8');
33
+ }
34
+ else {
35
+ contents[filePath] = '(file does not exist yet — create it)';
36
+ }
37
+ }
38
+ return contents;
39
+ }
40
+ function parseClaudeResponse(response) {
41
+ const files = {};
42
+ const regex = /===FILE: (.+?)===\n([\s\S]*?)===END===/g;
43
+ let match;
44
+ while ((match = regex.exec(response)) !== null) {
45
+ const filePath = match[1].trim();
46
+ const content = match[2];
47
+ files[filePath] = content;
48
+ }
49
+ return files;
50
+ }
51
+ function writeFiles(files, cwd, allowed) {
52
+ const written = [];
53
+ for (const [filePath, content] of Object.entries(files)) {
54
+ if (!allowed.includes(filePath)) {
55
+ (0, logger_1.logInfo)(`Skipping non-allowed file: ${filePath}`);
56
+ continue;
57
+ }
58
+ const abs = path_1.default.resolve(cwd, filePath);
59
+ fs_1.default.mkdirSync(path_1.default.dirname(abs), { recursive: true });
60
+ fs_1.default.writeFileSync(abs, content, 'utf-8');
61
+ written.push(filePath);
62
+ }
63
+ return written;
64
+ }
65
+ async function runStep(step, spec, cwd, extraContext) {
66
+ const fileContents = readAllowedFiles(step.files_allowed, cwd);
67
+ const fileSection = Object.entries(fileContents)
68
+ .map(([f, c]) => `### ${f}\n\`\`\`\n${c}\n\`\`\``)
69
+ .join('\n\n');
70
+ const instruction = `
71
+ Goal: ${spec.goal}
72
+
73
+ Constraints:
74
+ ${spec.constraints.map((c) => `- ${c}`).join('\n')}
75
+
76
+ Step ${step.id}: ${step.description}
77
+
78
+ Files you may modify:
79
+ ${step.files_allowed.join(', ')}
80
+
81
+ Current file contents:
82
+ ${fileSection}
83
+ ${extraContext ? `\nAdditional context:\n${extraContext}` : ''}
84
+ `.trim();
85
+ (0, logger_1.logInfo)(`Sending step ${step.id} to Claude...`);
86
+ const claudeResponse = await (0, claudeClient_1.callClaude)(SYSTEM_PROMPT, instruction);
87
+ const parsedFiles = parseClaudeResponse(claudeResponse);
88
+ const filesWritten = writeFiles(parsedFiles, cwd, step.files_allowed);
89
+ return {
90
+ stepId: step.id,
91
+ instruction,
92
+ filesAllowed: step.files_allowed,
93
+ claudeResponse,
94
+ filesWritten,
95
+ };
96
+ }
97
+ //# sourceMappingURL=runStep.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runStep.js","sourceRoot":"","sources":["../../src/executor/runStep.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function compileIdeation(filePath: string, cwd: string): string;
2
+ //# sourceMappingURL=compile.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compile.d.ts","sourceRoot":"","sources":["../../src/ideation/compile.ts"],"names":[],"mappings":"AAoFA,wBAAgB,eAAe,CAAC,QAAQ,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAiBrE"}
@@ -0,0 +1,90 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.compileIdeation = compileIdeation;
7
+ const fs_1 = __importDefault(require("fs"));
8
+ const path_1 = __importDefault(require("path"));
9
+ function parseMarkdown(content) {
10
+ const sections = {
11
+ goal: '',
12
+ context: '',
13
+ ideas: [],
14
+ finalPlan: '',
15
+ };
16
+ const sectionMap = {
17
+ goal: 'goal',
18
+ context: 'context',
19
+ ideas: 'ideas',
20
+ 'final plan': 'finalPlan',
21
+ };
22
+ const lines = content.split('\n');
23
+ let currentSection = null;
24
+ const buffer = [];
25
+ function flush() {
26
+ if (!currentSection)
27
+ return;
28
+ const text = buffer.join('\n').trim();
29
+ if (currentSection === 'ideas') {
30
+ sections.ideas = text
31
+ .split('\n')
32
+ .map((l) => l.replace(/^[-*]\s*/, '').trim())
33
+ .filter(Boolean);
34
+ }
35
+ else {
36
+ sections[currentSection] = text;
37
+ }
38
+ buffer.length = 0;
39
+ }
40
+ for (const line of lines) {
41
+ const headingMatch = line.match(/^#{1,3}\s+(.+)/);
42
+ if (headingMatch) {
43
+ flush();
44
+ const heading = headingMatch[1].toLowerCase().trim();
45
+ currentSection = sectionMap[heading] ?? null;
46
+ }
47
+ else {
48
+ buffer.push(line);
49
+ }
50
+ }
51
+ flush();
52
+ return sections;
53
+ }
54
+ function buildSpec(parsed, name) {
55
+ const planLines = parsed.finalPlan.split('\n').filter(Boolean);
56
+ const steps = planLines
57
+ .map((line, i) => ({
58
+ id: i + 1,
59
+ description: line.replace(/^\d+[.)]\s*/, '').trim(),
60
+ files_allowed: [],
61
+ }))
62
+ .filter((s) => s.description.length > 0);
63
+ return {
64
+ goal: parsed.goal || name,
65
+ constraints: parsed.context
66
+ .split('\n')
67
+ .map((l) => l.replace(/^[-*]\s*/, '').trim())
68
+ .filter(Boolean),
69
+ steps: steps.length > 0
70
+ ? steps
71
+ : [{ id: 1, description: parsed.finalPlan || 'Implement the plan', files_allowed: [] }],
72
+ tests: [],
73
+ definition_of_done: parsed.ideas,
74
+ };
75
+ }
76
+ function compileIdeation(filePath, cwd) {
77
+ if (!fs_1.default.existsSync(filePath)) {
78
+ throw new Error(`File not found: ${filePath}`);
79
+ }
80
+ const content = fs_1.default.readFileSync(filePath, 'utf-8');
81
+ const name = path_1.default.basename(filePath, path_1.default.extname(filePath));
82
+ const parsed = parseMarkdown(content);
83
+ const spec = buildSpec(parsed, name);
84
+ const specsDir = path_1.default.join(cwd, '.tempo', 'scores');
85
+ fs_1.default.mkdirSync(specsDir, { recursive: true });
86
+ const outPath = path_1.default.join(specsDir, `${name}.json`);
87
+ fs_1.default.writeFileSync(outPath, JSON.stringify(spec, null, 2), 'utf-8');
88
+ return outPath;
89
+ }
90
+ //# sourceMappingURL=compile.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compile.js","sourceRoot":"","sources":["../../src/ideation/compile.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,56 @@
1
+ import { z } from 'zod';
2
+ export declare const StepSchema: z.ZodObject<{
3
+ id: z.ZodNumber;
4
+ description: z.ZodString;
5
+ files_allowed: z.ZodArray<z.ZodString, "many">;
6
+ }, "strip", z.ZodTypeAny, {
7
+ id: number;
8
+ description: string;
9
+ files_allowed: string[];
10
+ }, {
11
+ id: number;
12
+ description: string;
13
+ files_allowed: string[];
14
+ }>;
15
+ export declare const SpecSchema: z.ZodObject<{
16
+ goal: z.ZodString;
17
+ constraints: z.ZodArray<z.ZodString, "many">;
18
+ steps: z.ZodArray<z.ZodObject<{
19
+ id: z.ZodNumber;
20
+ description: z.ZodString;
21
+ files_allowed: z.ZodArray<z.ZodString, "many">;
22
+ }, "strip", z.ZodTypeAny, {
23
+ id: number;
24
+ description: string;
25
+ files_allowed: string[];
26
+ }, {
27
+ id: number;
28
+ description: string;
29
+ files_allowed: string[];
30
+ }>, "many">;
31
+ tests: z.ZodArray<z.ZodString, "many">;
32
+ definition_of_done: z.ZodArray<z.ZodString, "many">;
33
+ }, "strip", z.ZodTypeAny, {
34
+ goal: string;
35
+ constraints: string[];
36
+ steps: {
37
+ id: number;
38
+ description: string;
39
+ files_allowed: string[];
40
+ }[];
41
+ tests: string[];
42
+ definition_of_done: string[];
43
+ }, {
44
+ goal: string;
45
+ constraints: string[];
46
+ steps: {
47
+ id: number;
48
+ description: string;
49
+ files_allowed: string[];
50
+ }[];
51
+ tests: string[];
52
+ definition_of_done: string[];
53
+ }>;
54
+ export type Step = z.infer<typeof StepSchema>;
55
+ export type Spec = z.infer<typeof SpecSchema>;
56
+ //# sourceMappingURL=schema.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"schema.d.ts","sourceRoot":"","sources":["../../src/spec/schema.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,eAAO,MAAM,UAAU;;;;;;;;;;;;EAIrB,CAAC;AAEH,eAAO,MAAM,UAAU;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAMrB,CAAC;AAEH,MAAM,MAAM,IAAI,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,UAAU,CAAC,CAAC;AAC9C,MAAM,MAAM,IAAI,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,UAAU,CAAC,CAAC"}
@@ -0,0 +1,17 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.SpecSchema = exports.StepSchema = void 0;
4
+ const zod_1 = require("zod");
5
+ exports.StepSchema = zod_1.z.object({
6
+ id: zod_1.z.number(),
7
+ description: zod_1.z.string(),
8
+ files_allowed: zod_1.z.array(zod_1.z.string()),
9
+ });
10
+ exports.SpecSchema = zod_1.z.object({
11
+ goal: zod_1.z.string(),
12
+ constraints: zod_1.z.array(zod_1.z.string()),
13
+ steps: zod_1.z.array(exports.StepSchema),
14
+ tests: zod_1.z.array(zod_1.z.string()),
15
+ definition_of_done: zod_1.z.array(zod_1.z.string()),
16
+ });
17
+ //# sourceMappingURL=schema.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"schema.js","sourceRoot":"","sources":["../../src/spec/schema.ts"],"names":[],"mappings":";;;AAAA,6BAAwB;AAEX,QAAA,UAAU,GAAG,OAAC,CAAC,MAAM,CAAC;IACjC,EAAE,EAAE,OAAC,CAAC,MAAM,EAAE;IACd,WAAW,EAAE,OAAC,CAAC,MAAM,EAAE;IACvB,aAAa,EAAE,OAAC,CAAC,KAAK,CAAC,OAAC,CAAC,MAAM,EAAE,CAAC;CACnC,CAAC,CAAC;AAEU,QAAA,UAAU,GAAG,OAAC,CAAC,MAAM,CAAC;IACjC,IAAI,EAAE,OAAC,CAAC,MAAM,EAAE;IAChB,WAAW,EAAE,OAAC,CAAC,KAAK,CAAC,OAAC,CAAC,MAAM,EAAE,CAAC;IAChC,KAAK,EAAE,OAAC,CAAC,KAAK,CAAC,kBAAU,CAAC;IAC1B,KAAK,EAAE,OAAC,CAAC,KAAK,CAAC,OAAC,CAAC,MAAM,EAAE,CAAC;IAC1B,kBAAkB,EAAE,OAAC,CAAC,KAAK,CAAC,OAAC,CAAC,MAAM,EAAE,CAAC;CACxC,CAAC,CAAC"}
@@ -0,0 +1,7 @@
1
+ export declare function logStep(stepId: number, description: string): void;
2
+ export declare function logSuccess(message: string): void;
3
+ export declare function logFailure(message: string): void;
4
+ export declare function logRetry(attempt: number, max: number, errors: string): void;
5
+ export declare function logInfo(message: string): void;
6
+ export declare function logSummary(passed: number, failed: number, total: number): void;
7
+ //# sourceMappingURL=logger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../../src/utils/logger.ts"],"names":[],"mappings":"AAEA,wBAAgB,OAAO,CAAC,MAAM,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,IAAI,CAEjE;AAED,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAEhD;AAED,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAEhD;AAED,wBAAgB,QAAQ,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI,CAG3E;AAED,wBAAgB,OAAO,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAE7C;AAED,wBAAgB,UAAU,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,IAAI,CAU9E"}
@@ -0,0 +1,40 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.logStep = logStep;
7
+ exports.logSuccess = logSuccess;
8
+ exports.logFailure = logFailure;
9
+ exports.logRetry = logRetry;
10
+ exports.logInfo = logInfo;
11
+ exports.logSummary = logSummary;
12
+ const chalk_1 = __importDefault(require("chalk"));
13
+ function logStep(stepId, description) {
14
+ console.log(chalk_1.default.cyan(`\n[STEP ${stepId}] ${description}`));
15
+ }
16
+ function logSuccess(message) {
17
+ console.log(chalk_1.default.green(`✓ ${message}`));
18
+ }
19
+ function logFailure(message) {
20
+ console.log(chalk_1.default.red(`✗ ${message}`));
21
+ }
22
+ function logRetry(attempt, max, errors) {
23
+ console.log(chalk_1.default.yellow(`↻ Retry ${attempt}/${max}`));
24
+ console.log(chalk_1.default.yellow(` Errors: ${errors.slice(0, 200)}...`));
25
+ }
26
+ function logInfo(message) {
27
+ console.log(chalk_1.default.blue(`ℹ ${message}`));
28
+ }
29
+ function logSummary(passed, failed, total) {
30
+ console.log(chalk_1.default.bold('\n─────────────────────────────'));
31
+ console.log(chalk_1.default.bold('Pipeline Summary'));
32
+ console.log(chalk_1.default.bold('─────────────────────────────'));
33
+ console.log(`Total steps : ${total}`);
34
+ console.log(chalk_1.default.green(`Passed : ${passed}`));
35
+ if (failed > 0) {
36
+ console.log(chalk_1.default.red(`Failed : ${failed}`));
37
+ }
38
+ console.log(chalk_1.default.bold('─────────────────────────────\n'));
39
+ }
40
+ //# sourceMappingURL=logger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../../src/utils/logger.ts"],"names":[],"mappings":";;;;;AAEA,0BAEC;AAED,gCAEC;AAED,gCAEC;AAED,4BAGC;AAED,0BAEC;AAED,gCAUC;AAjCD,kDAA0B;AAE1B,SAAgB,OAAO,CAAC,MAAc,EAAE,WAAmB;IACzD,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,WAAW,MAAM,KAAK,WAAW,EAAE,CAAC,CAAC,CAAC;AAC/D,CAAC;AAED,SAAgB,UAAU,CAAC,OAAe;IACxC,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,KAAK,CAAC,KAAK,OAAO,EAAE,CAAC,CAAC,CAAC;AAC3C,CAAC;AAED,SAAgB,UAAU,CAAC,OAAe;IACxC,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,GAAG,CAAC,KAAK,OAAO,EAAE,CAAC,CAAC,CAAC;AACzC,CAAC;AAED,SAAgB,QAAQ,CAAC,OAAe,EAAE,GAAW,EAAE,MAAc;IACnE,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,MAAM,CAAC,WAAW,OAAO,IAAI,GAAG,EAAE,CAAC,CAAC,CAAC;IACvD,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,MAAM,CAAC,aAAa,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC;AACpE,CAAC;AAED,SAAgB,OAAO,CAAC,OAAe;IACrC,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,KAAK,OAAO,EAAE,CAAC,CAAC,CAAC;AAC1C,CAAC;AAED,SAAgB,UAAU,CAAC,MAAc,EAAE,MAAc,EAAE,KAAa;IACtE,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC,CAAC;IAC3D,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,kBAAkB,CAAC,CAAC,CAAC;IAC5C,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,+BAA+B,CAAC,CAAC,CAAC;IACzD,OAAO,CAAC,GAAG,CAAC,iBAAiB,KAAK,EAAE,CAAC,CAAC;IACtC,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,KAAK,CAAC,iBAAiB,MAAM,EAAE,CAAC,CAAC,CAAC;IACpD,IAAI,MAAM,GAAG,CAAC,EAAE,CAAC;QACf,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,GAAG,CAAC,iBAAiB,MAAM,EAAE,CAAC,CAAC,CAAC;IACpD,CAAC;IACD,OAAO,CAAC,GAAG,CAAC,eAAK,CAAC,IAAI,CAAC,iCAAiC,CAAC,CAAC,CAAC;AAC7D,CAAC"}
@@ -0,0 +1,6 @@
1
+ export interface ValidationResult {
2
+ success: boolean;
3
+ errors: string;
4
+ }
5
+ export declare function runValidation(cwd: string): Promise<ValidationResult>;
6
+ //# sourceMappingURL=runValidation.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runValidation.d.ts","sourceRoot":"","sources":["../../src/validator/runValidation.ts"],"names":[],"mappings":"AAKA,MAAM,WAAW,gBAAgB;IAC/B,OAAO,EAAE,OAAO,CAAC;IACjB,MAAM,EAAE,MAAM,CAAC;CAChB;AAyBD,wBAAsB,aAAa,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAuB1E"}
@@ -0,0 +1,50 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.runValidation = runValidation;
7
+ const execa_1 = __importDefault(require("execa"));
8
+ const fs_1 = __importDefault(require("fs"));
9
+ const path_1 = __importDefault(require("path"));
10
+ const logger_1 = require("../utils/logger");
11
+ async function runCommand(command, cwd) {
12
+ const [cmd, ...args] = command.split(' ');
13
+ try {
14
+ const result = await (0, execa_1.default)(cmd, args, { cwd, reject: false });
15
+ const output = [result.stdout, result.stderr].filter(Boolean).join('\n');
16
+ return { ok: result.exitCode === 0, output };
17
+ }
18
+ catch (err) {
19
+ return { ok: false, output: String(err) };
20
+ }
21
+ }
22
+ function loadConfig(cwd) {
23
+ const configPath = path_1.default.join(cwd, '.tempo', 'config.json');
24
+ if (!fs_1.default.existsSync(configPath))
25
+ return {};
26
+ return JSON.parse(fs_1.default.readFileSync(configPath, 'utf-8'));
27
+ }
28
+ async function runValidation(cwd) {
29
+ const config = loadConfig(cwd);
30
+ const errors = [];
31
+ const commands = [
32
+ { label: 'lint', cmd: config.lintCommand },
33
+ { label: 'build', cmd: config.buildCommand },
34
+ { label: 'test', cmd: config.testCommand },
35
+ ];
36
+ for (const { label, cmd } of commands) {
37
+ if (!cmd)
38
+ continue;
39
+ (0, logger_1.logInfo)(`Running ${label}: ${cmd}`);
40
+ const { ok, output } = await runCommand(cmd, cwd);
41
+ if (!ok) {
42
+ errors.push(`[${label}] ${output}`);
43
+ }
44
+ }
45
+ return {
46
+ success: errors.length === 0,
47
+ errors: errors.join('\n\n'),
48
+ };
49
+ }
50
+ //# sourceMappingURL=runValidation.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runValidation.js","sourceRoot":"","sources":["../../src/validator/runValidation.ts"],"names":[],"mappings":";;;;;AAiCA,sCAuBC;AAxDD,kDAA0B;AAC1B,4CAAoB;AACpB,gDAAwB;AACxB,4CAA0C;AAa1C,KAAK,UAAU,UAAU,CAAC,OAAe,EAAE,GAAW;IACpD,MAAM,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC,GAAG,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAC1C,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,MAAM,IAAA,eAAK,EAAC,GAAG,EAAE,IAAI,EAAE,EAAE,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,CAAC;QAC9D,MAAM,MAAM,GAAG,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACzE,OAAO,EAAE,EAAE,EAAE,MAAM,CAAC,QAAQ,KAAK,CAAC,EAAE,MAAM,EAAE,CAAC;IAC/C,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,GAAG,CAAC,EAAE,CAAC;IAC5C,CAAC;AACH,CAAC;AAED,SAAS,UAAU,CAAC,GAAW;IAC7B,MAAM,UAAU,GAAG,cAAI,CAAC,IAAI,CAAC,GAAG,EAAE,QAAQ,EAAE,aAAa,CAAC,CAAC;IAC3D,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,UAAU,CAAC;QAAE,OAAO,EAAE,CAAC;IAC1C,OAAO,IAAI,CAAC,KAAK,CAAC,YAAE,CAAC,YAAY,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC,CAAC;AAC1D,CAAC;AAEM,KAAK,UAAU,aAAa,CAAC,GAAW;IAC7C,MAAM,MAAM,GAAG,UAAU,CAAC,GAAG,CAAC,CAAC;IAC/B,MAAM,MAAM,GAAa,EAAE,CAAC;IAE5B,MAAM,QAAQ,GAAsD;QAClE,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,CAAC,WAAW,EAAE;QAC1C,EAAE,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,CAAC,YAAY,EAAE;QAC5C,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,CAAC,WAAW,EAAE;KAC3C,CAAC;IAEF,KAAK,MAAM,EAAE,KAAK,EAAE,GAAG,EAAE,IAAI,QAAQ,EAAE,CAAC;QACtC,IAAI,CAAC,GAAG;YAAE,SAAS;QACnB,IAAA,gBAAO,EAAC,WAAW,KAAK,KAAK,GAAG,EAAE,CAAC,CAAC;QACpC,MAAM,EAAE,EAAE,EAAE,MAAM,EAAE,GAAG,MAAM,UAAU,CAAC,GAAG,EAAE,GAAG,CAAC,CAAC;QAClD,IAAI,CAAC,EAAE,EAAE,CAAC;YACR,MAAM,CAAC,IAAI,CAAC,IAAI,KAAK,KAAK,MAAM,EAAE,CAAC,CAAC;QACtC,CAAC;IACH,CAAC;IAED,OAAO;QACL,OAAO,EAAE,MAAM,CAAC,MAAM,KAAK,CAAC;QAC5B,MAAM,EAAE,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC;KAC5B,CAAC;AACJ,CAAC"}
package/package.json ADDED
@@ -0,0 +1,34 @@
1
+ {
2
+ "name": "tempo-agent",
3
+ "version": "1.0.0",
4
+ "description": "A modular CLI tool for AI-driven code generation and validation",
5
+ "main": "dist/cli/index.js",
6
+ "bin": {
7
+ "tempo": "dist/cli/index.js"
8
+ },
9
+ "scripts": {
10
+ "dev": "ts-node src/cli/index.ts",
11
+ "build": "tsc",
12
+ "start": "node dist/cli/index.js",
13
+ "prepublishOnly": "npm run build"
14
+ },
15
+ "files": [
16
+ "dist/"
17
+ ],
18
+ "engines": {
19
+ "node": ">=18.0.0"
20
+ },
21
+ "keywords": ["cli", "tempo", "orchestrator", "claude", "ai"],
22
+ "license": "MIT",
23
+ "dependencies": {
24
+ "axios": "^1.7.2",
25
+ "chalk": "^4.1.2",
26
+ "execa": "^5.1.1",
27
+ "zod": "^3.23.8"
28
+ },
29
+ "devDependencies": {
30
+ "@types/node": "^20.14.0",
31
+ "ts-node": "^10.9.2",
32
+ "typescript": "^5.4.5"
33
+ }
34
+ }