atris 3.15.13 → 3.15.22
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/AGENTS.md +84 -8
- package/README.md +5 -1
- package/atris/AGENTS.md +46 -1
- package/atris/CLAUDE.md +36 -1
- package/atris/GEMINI.md +14 -1
- package/atris/atris.md +12 -1
- package/atris/atrisDev.md +3 -2
- package/atris/context/README.md +11 -0
- package/atris/features/company-brain-sync/validate.md +5 -5
- package/atris/learnings.jsonl +1 -0
- package/atris/policies/atris-design.md +2 -0
- package/atris/skills/aeo/SKILL.md +2 -2
- package/atris/skills/atris/SKILL.md +15 -62
- package/atris/skills/design/SKILL.md +2 -0
- package/atris/skills/imessage/SKILL.md +19 -2
- package/atris/skills/loop/SKILL.md +6 -5
- package/atris/skills/magic-inbox/SKILL.md +1 -1
- package/atris/team/_template/MEMBER.md +23 -1
- package/atris/team/brainstormer/START_HERE.md +6 -0
- package/atris/team/executor/MEMBER.md +13 -0
- package/atris/team/executor/START_HERE.md +6 -0
- package/atris/team/launcher/START_HERE.md +6 -0
- package/atris/team/mission-lead/MEMBER.md +39 -0
- package/atris/team/mission-lead/MISSION.md +33 -0
- package/atris/team/mission-lead/START_HERE.md +6 -0
- package/atris/team/navigator/MEMBER.md +11 -0
- package/atris/team/navigator/START_HERE.md +6 -0
- package/atris/team/opus-overnight/MEMBER.md +39 -0
- package/atris/team/opus-overnight/MISSION.md +61 -0
- package/atris/team/opus-overnight/START_HERE.md +6 -0
- package/atris/team/opus-overnight/STEERING.md +35 -0
- package/atris/team/researcher/START_HERE.md +6 -0
- package/atris/team/validator/MEMBER.md +26 -6
- package/atris/team/validator/START_HERE.md +6 -0
- package/atris/wiki/concepts/agent-activation-contract.md +79 -0
- package/atris/wiki/concepts/workspace-initialization-contract.md +73 -0
- package/atris/wiki/index.md +27 -0
- package/atris/wiki/sources/atris-labs-2026-05-10.txt +17 -0
- package/atris/wiki/sources/atris-labs-goals-2026-05-10.txt +15 -0
- package/atris/wiki/sources/atrisos-generative-ui-product-surface-2026-05-10.txt +10 -0
- package/atris/wiki/sources/jack-dorsey-2026-05-10.txt +12 -0
- package/atris.md +49 -13
- package/bin/atris.js +660 -22
- package/commands/activate.js +12 -3
- package/commands/aeo.js +1 -1
- package/commands/align.js +10 -10
- package/commands/analytics.js +9 -4
- package/commands/app.js +2 -0
- package/commands/apps.js +276 -0
- package/commands/auth.js +1 -1
- package/commands/autopilot.js +74 -5
- package/commands/brain.js +536 -61
- package/commands/brainstorm.js +12 -12
- package/commands/business-sync.js +142 -24
- package/commands/clean.js +9 -6
- package/commands/codex-goal.js +311 -0
- package/commands/errors.js +11 -1
- package/commands/feedback.js +55 -17
- package/commands/fork.js +2 -2
- package/commands/gm.js +376 -0
- package/commands/init.js +80 -3
- package/commands/integrations.js +524 -0
- package/commands/learn.js +25 -16
- package/commands/lesson.js +41 -0
- package/commands/lifecycle.js +2 -2
- package/commands/member.js +2416 -9
- package/commands/mission.js +1776 -0
- package/commands/now.js +48 -7
- package/commands/play.js +425 -0
- package/commands/publish.js +2 -1
- package/commands/pull.js +72 -29
- package/commands/push.js +199 -17
- package/commands/review.js +51 -13
- package/commands/skill.js +2 -2
- package/commands/soul.js +19 -13
- package/commands/status.js +6 -1
- package/commands/sync.js +5 -4
- package/commands/task.js +1041 -147
- package/commands/terminal.js +5 -5
- package/commands/verify.js +7 -5
- package/commands/visualize.js +7 -0
- package/commands/wiki.js +53 -16
- package/commands/workflow.js +298 -54
- package/commands/workspace-clean.js +1 -1
- package/commands/worktree.js +468 -0
- package/commands/xp.js +1608 -0
- package/lib/manifest.js +34 -4
- package/lib/scorecard.js +3 -2
- package/lib/task-db.js +408 -27
- package/lib/todo-fallback.js +28 -2
- package/lib/todo.js +5 -3
- package/package.json +23 -2
- package/utils/update-check.js +51 -1
package/commands/workflow.js
CHANGED
|
@@ -41,6 +41,131 @@ function printWorkflowBrief(lines) {
|
|
|
41
41
|
console.log('');
|
|
42
42
|
}
|
|
43
43
|
|
|
44
|
+
const CONFIDENCE_GATE_LINES = [
|
|
45
|
+
'Confidence Gate:',
|
|
46
|
+
'1) Ask: am I factually confident enough to move this forward?',
|
|
47
|
+
'2) Find loopholes: stale sources, missing owner, weak proof, bad rollback, hidden risk.',
|
|
48
|
+
'3) Patch every known loophole with proof, verifier, owner, rollback, or an explicit blocked note.',
|
|
49
|
+
'4) Only advance when confidence is earned; never use 100% as a vibe.'
|
|
50
|
+
];
|
|
51
|
+
|
|
52
|
+
function printConfidenceGate(indent = '') {
|
|
53
|
+
for (const line of CONFIDENCE_GATE_LINES) console.log(`${indent}${line}`);
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
function confidenceGatePrompt(stage) {
|
|
57
|
+
return [
|
|
58
|
+
`Confidence Gate (${stage}):`,
|
|
59
|
+
`- Ask whether you are factually confident enough to advance this ${stage}.`,
|
|
60
|
+
'- List every plausible loophole: stale source, missing owner, weak proof, bad rollback, hidden side effect, ambiguous done condition.',
|
|
61
|
+
'- Patch each loophole with a source read, verifier, proof requirement, owner, rollback, or explicit blocked note.',
|
|
62
|
+
'- Do not claim 100% confidence unless every known loophole is patched, verified, or named as residual risk.'
|
|
63
|
+
].join('\n');
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
function printAtris2Result(response) {
|
|
67
|
+
if (!response || !Array.isArray(response.result)) {
|
|
68
|
+
console.log(JSON.stringify(response, null, 2));
|
|
69
|
+
return;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
let wroteText = false;
|
|
73
|
+
for (const event of response.result) {
|
|
74
|
+
if (event && event.type === 'text' && event.content) {
|
|
75
|
+
process.stdout.write(event.content);
|
|
76
|
+
wroteText = true;
|
|
77
|
+
} else if (event && event.type === 'assistant' && Array.isArray(event.content)) {
|
|
78
|
+
for (const block of event.content) {
|
|
79
|
+
if (block && block.type === 'text' && block.text) {
|
|
80
|
+
process.stdout.write(block.text);
|
|
81
|
+
wroteText = true;
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
if (wroteText) {
|
|
88
|
+
console.log('');
|
|
89
|
+
} else {
|
|
90
|
+
console.log(JSON.stringify(response.result, null, 2));
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
async function runAtris2Local(userInput, atris2Mode) {
|
|
95
|
+
console.log(`🚀 EXECUTING VIA ATRIS 2 ${atris2Mode.toUpperCase()}`);
|
|
96
|
+
console.log('');
|
|
97
|
+
|
|
98
|
+
const actualCommand = String(userInput || '').trim().replace(/^2\s+(fast|pro)\b/i, '').trim();
|
|
99
|
+
if (!actualCommand) {
|
|
100
|
+
console.log(`⚠ No command provided after "2 ${atris2Mode}"`);
|
|
101
|
+
console.log(`Usage: atris 2 ${atris2Mode} <your command>`);
|
|
102
|
+
process.exit(1);
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
console.log(`Running: ${actualCommand}`);
|
|
106
|
+
console.log('');
|
|
107
|
+
|
|
108
|
+
try {
|
|
109
|
+
const http = require('http');
|
|
110
|
+
const response = await new Promise((resolve, reject) => {
|
|
111
|
+
const postData = JSON.stringify({
|
|
112
|
+
message: actualCommand,
|
|
113
|
+
workspace_path: process.cwd(),
|
|
114
|
+
model: `atris-2-${atris2Mode}`
|
|
115
|
+
});
|
|
116
|
+
|
|
117
|
+
const options = {
|
|
118
|
+
hostname: '127.0.0.1',
|
|
119
|
+
port: 8000,
|
|
120
|
+
path: '/api/agent-sdk/fast',
|
|
121
|
+
method: 'POST',
|
|
122
|
+
headers: {
|
|
123
|
+
'Content-Type': 'application/json',
|
|
124
|
+
'Content-Length': Buffer.byteLength(postData)
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
|
|
128
|
+
const req = http.request(options, (res) => {
|
|
129
|
+
let data = '';
|
|
130
|
+
res.on('data', (chunk) => data += chunk);
|
|
131
|
+
res.on('end', () => {
|
|
132
|
+
try {
|
|
133
|
+
const parsed = JSON.parse(data);
|
|
134
|
+
if (res.statusCode < 200 || res.statusCode >= 300) {
|
|
135
|
+
reject(new Error(parsed.detail || parsed.error || `HTTP ${res.statusCode}`));
|
|
136
|
+
return;
|
|
137
|
+
}
|
|
138
|
+
resolve(parsed);
|
|
139
|
+
} catch (e) {
|
|
140
|
+
reject(new Error(`Failed to parse response: ${data}`));
|
|
141
|
+
}
|
|
142
|
+
});
|
|
143
|
+
});
|
|
144
|
+
|
|
145
|
+
req.on('error', reject);
|
|
146
|
+
const timeoutMs = atris2Mode === 'pro' ? 30000 : 10000;
|
|
147
|
+
req.setTimeout(timeoutMs, () => {
|
|
148
|
+
req.destroy();
|
|
149
|
+
reject(new Error(`Request timeout after ${timeoutMs / 1000}s`));
|
|
150
|
+
});
|
|
151
|
+
req.write(postData);
|
|
152
|
+
req.end();
|
|
153
|
+
});
|
|
154
|
+
|
|
155
|
+
if (response.error) {
|
|
156
|
+
throw new Error(response.error);
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
console.log(`✅ Atris 2 ${atris2Mode} completed`);
|
|
160
|
+
printAtris2Result(response);
|
|
161
|
+
} catch (error) {
|
|
162
|
+
console.error(`✗ Error: ${error.message}`);
|
|
163
|
+
console.error(`Atris 2 ${atris2Mode} failed before completion.`);
|
|
164
|
+
console.error(`Refusing to run the prompt as a shell command. Start the backend on port 8000 or retry without "2 ${atris2Mode}".`);
|
|
165
|
+
process.exit(1);
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
|
|
44
169
|
async function planAtris(userInput = null) {
|
|
45
170
|
const { loadConfig } = require('../utils/config');
|
|
46
171
|
const { loadCredentials, ensureValidCredentials } = require('../utils/auth');
|
|
@@ -49,10 +174,19 @@ async function planAtris(userInput = null) {
|
|
|
49
174
|
const args = process.argv.slice(3);
|
|
50
175
|
const executeFlag = args.includes('--execute');
|
|
51
176
|
const showFull = args.includes('--full') || args.includes('--verbose');
|
|
52
|
-
|
|
177
|
+
|
|
53
178
|
const config = loadConfig();
|
|
54
|
-
|
|
55
|
-
|
|
179
|
+
// Auto-enable local execution mode for "2 fast" / "2 pro" product aliases.
|
|
180
|
+
const atris2ModeMatch = userInput && String(userInput).trim().match(/^2\s+(fast|pro)\b/i);
|
|
181
|
+
const atris2Mode = atris2ModeMatch ? atris2ModeMatch[1].toLowerCase() : null;
|
|
182
|
+
const configuredMode = config.execution_mode || 'prompt';
|
|
183
|
+
const executionMode = executeFlag ? 'agent' : (atris2Mode ? 'local' : (configuredMode === 'agent' ? 'agent' : 'prompt'));
|
|
184
|
+
|
|
185
|
+
if (executionMode === 'local') {
|
|
186
|
+
await runAtris2Local(userInput, atris2Mode);
|
|
187
|
+
return;
|
|
188
|
+
}
|
|
189
|
+
|
|
56
190
|
const targetDir = path.join(process.cwd(), 'atris');
|
|
57
191
|
const navigatorFile = fs.existsSync(path.join(targetDir, 'team', 'navigator', 'MEMBER.md'))
|
|
58
192
|
? path.join(targetDir, 'team', 'navigator', 'MEMBER.md')
|
|
@@ -224,11 +358,17 @@ async function planAtris(userInput = null) {
|
|
|
224
358
|
}
|
|
225
359
|
console.log('Workflow:');
|
|
226
360
|
console.log('1) ASCII visualize + wait for approval');
|
|
227
|
-
console.log('2)
|
|
361
|
+
console.log('2) Run the Confidence Gate before writing tasks');
|
|
362
|
+
printConfidenceGate(' ');
|
|
363
|
+
console.log('3) Write tasks to atris/TODO.md under ## Backlog');
|
|
228
364
|
console.log(' Format: - **T#:** Description [explore|execute]');
|
|
229
|
-
console.log('
|
|
365
|
+
console.log('4) Log to atris/team/navigator/journal/YYYY-MM-DD.md');
|
|
230
366
|
console.log(' (Task, Delivered, User reaction, Pattern)');
|
|
231
|
-
|
|
367
|
+
if (atris2Mode) {
|
|
368
|
+
console.log('5) EXECUTE MODE ENABLED: Will execute tasks directly.');
|
|
369
|
+
} else {
|
|
370
|
+
console.log('5) Stop. Do NOT execute (run `atris do` to build).');
|
|
371
|
+
}
|
|
232
372
|
console.log('');
|
|
233
373
|
console.log('━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━');
|
|
234
374
|
console.log('💡 After planning: Run "atris do" to execute the build');
|
|
@@ -237,7 +377,7 @@ async function planAtris(userInput = null) {
|
|
|
237
377
|
}
|
|
238
378
|
console.log('━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━');
|
|
239
379
|
console.log('');
|
|
240
|
-
|
|
380
|
+
|
|
241
381
|
// Check execution mode
|
|
242
382
|
if (executionMode === 'agent') {
|
|
243
383
|
// Agent mode: execute via backend API
|
|
@@ -258,12 +398,12 @@ async function planAtris(userInput = null) {
|
|
|
258
398
|
if (navigatorSpec) {
|
|
259
399
|
systemPrompt += navigatorSpec + '\n\n';
|
|
260
400
|
}
|
|
261
|
-
|
|
401
|
+
|
|
262
402
|
// Reference MAP.md and PERSONA.md
|
|
263
403
|
if (fs.existsSync(personaPath)) {
|
|
264
404
|
systemPrompt += '## PERSONA.md\n' + fs.readFileSync(personaPath, 'utf8') + '\n\n';
|
|
265
405
|
}
|
|
266
|
-
|
|
406
|
+
|
|
267
407
|
if (mapFileRef) {
|
|
268
408
|
systemPrompt += `## MAP.md\nRead this file for file:line references: ${mapFileRef}\n\n`;
|
|
269
409
|
}
|
|
@@ -271,7 +411,7 @@ async function planAtris(userInput = null) {
|
|
|
271
411
|
// Build user prompt with context
|
|
272
412
|
let userPrompt = `You are the Navigator. Take ideas from Inbox → break them down into perfect, manageable tasks.\n\n`;
|
|
273
413
|
userPrompt += `⚠️ CRITICAL: You MUST create visualizations BEFORE writing tasks!\n\n`;
|
|
274
|
-
|
|
414
|
+
|
|
275
415
|
if (userInput) {
|
|
276
416
|
userPrompt += `## DIRECT REQUEST:\n${userInput}\n\n`;
|
|
277
417
|
}
|
|
@@ -281,26 +421,28 @@ async function planAtris(userInput = null) {
|
|
|
281
421
|
} else {
|
|
282
422
|
userPrompt += `## INBOX CONTEXT:\n(No items in Inbox - check logs/YYYY/YYYY-MM-DD.md for inbox items)\n\n`;
|
|
283
423
|
}
|
|
284
|
-
|
|
424
|
+
|
|
285
425
|
if (taskContexts) {
|
|
286
426
|
userPrompt += `## CURRENT TODO.md:\n${taskContexts}\n\n`;
|
|
287
427
|
}
|
|
288
|
-
|
|
428
|
+
|
|
289
429
|
userPrompt += `Your job (execute these steps):\n\n`;
|
|
290
430
|
userPrompt += `STEP 1: Generate ASCII visualizations for user approval\n`;
|
|
291
431
|
userPrompt += ` Create diagrams showing architecture, flows, schemas, UI/UX.\n`;
|
|
292
432
|
userPrompt += ` SHOW these diagrams and wait for approval before proceeding.\n\n`;
|
|
293
|
-
userPrompt += `STEP 2:
|
|
433
|
+
userPrompt += `STEP 2: Run the Confidence Gate before writing tasks\n`;
|
|
434
|
+
userPrompt += confidenceGatePrompt('plan') + `\n\n`;
|
|
435
|
+
userPrompt += `STEP 3: Break approved ideas into concrete tasks\n`;
|
|
294
436
|
userPrompt += ` - Each task should be: Specific, Measurable, Actionable\n`;
|
|
295
437
|
userPrompt += ` - Include file:line references from MAP.md\n`;
|
|
296
438
|
userPrompt += ` - List dependencies between tasks\n`;
|
|
297
439
|
userPrompt += ` - Add acceptance criteria for each task\n\n`;
|
|
298
|
-
userPrompt += `STEP
|
|
440
|
+
userPrompt += `STEP 4: Write tasks to atris/TODO.md\n`;
|
|
299
441
|
userPrompt += ` - Add to ## Backlog section\n`;
|
|
300
442
|
userPrompt += ` - Format: - **T#:** Description [explore|execute]\n`;
|
|
301
443
|
userPrompt += ` - Each task: one job, clear exit condition\n`;
|
|
302
444
|
userPrompt += ` - Include file:line references from MAP.md\n\n`;
|
|
303
|
-
userPrompt += `STEP
|
|
445
|
+
userPrompt += `STEP 5: Log to your journal\n`;
|
|
304
446
|
userPrompt += ` - Write to atris/team/navigator/journal/YYYY-MM-DD.md\n`;
|
|
305
447
|
userPrompt += ` - Include: Task, Delivered, User reaction, Pattern\n`;
|
|
306
448
|
userPrompt += ` - Your journal is how you learn — record what worked\n\n`;
|
|
@@ -351,7 +493,7 @@ async function planAtris(userInput = null) {
|
|
|
351
493
|
console.error(`\n❌ Execution error: ${error.message}`);
|
|
352
494
|
},
|
|
353
495
|
});
|
|
354
|
-
|
|
496
|
+
|
|
355
497
|
console.log('\n');
|
|
356
498
|
console.log('━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━');
|
|
357
499
|
console.log('');
|
|
@@ -373,10 +515,10 @@ async function doAtris() {
|
|
|
373
515
|
const args = process.argv.slice(3);
|
|
374
516
|
const executeFlag = args.includes('--execute');
|
|
375
517
|
const showFull = args.includes('--full') || args.includes('--verbose');
|
|
376
|
-
|
|
518
|
+
|
|
377
519
|
const config = loadConfig();
|
|
378
520
|
const executionMode = executeFlag ? 'agent' : (config.execution_mode || 'prompt');
|
|
379
|
-
|
|
521
|
+
|
|
380
522
|
const cwd = process.cwd();
|
|
381
523
|
const targetDir = path.join(cwd, 'atris');
|
|
382
524
|
const executorFile = fs.existsSync(path.join(targetDir, 'team', 'executor', 'MEMBER.md'))
|
|
@@ -405,7 +547,7 @@ async function doAtris() {
|
|
|
405
547
|
context = 'ROOT';
|
|
406
548
|
}
|
|
407
549
|
}
|
|
408
|
-
|
|
550
|
+
|
|
409
551
|
// Load executor spec
|
|
410
552
|
const executorSpec = fs.readFileSync(executorFile, 'utf8');
|
|
411
553
|
|
|
@@ -446,7 +588,7 @@ async function doAtris() {
|
|
|
446
588
|
if (!taskSource) {
|
|
447
589
|
taskSource = 'atris/TODO.md';
|
|
448
590
|
}
|
|
449
|
-
|
|
591
|
+
|
|
450
592
|
// All tasks available (no tag filtering)
|
|
451
593
|
const filteredTasks = tasksContent;
|
|
452
594
|
|
|
@@ -486,7 +628,7 @@ async function doAtris() {
|
|
|
486
628
|
} catch {
|
|
487
629
|
workspaceSummary = null;
|
|
488
630
|
}
|
|
489
|
-
|
|
631
|
+
|
|
490
632
|
// Prompt-mode output (keep concise by default)
|
|
491
633
|
console.log('');
|
|
492
634
|
console.log('┌─────────────────────────────────────────────────────────────┐');
|
|
@@ -560,9 +702,12 @@ async function doAtris() {
|
|
|
560
702
|
console.log('Workflow:');
|
|
561
703
|
console.log('1) Read atris/TODO.md — claim next unclaimed Backlog task');
|
|
562
704
|
console.log(' Move to ## In Progress: add "Claimed by: executor at YYYY-MM-DD HH:MM"');
|
|
563
|
-
console.log('2)
|
|
564
|
-
|
|
565
|
-
console.log('
|
|
705
|
+
console.log('2) Run the Confidence Gate against the task before editing');
|
|
706
|
+
printConfidenceGate(' ');
|
|
707
|
+
console.log('3) Execute step-by-step. Run tests as you go.');
|
|
708
|
+
console.log('4) Before completion, rerun the gate against proof and residual risk');
|
|
709
|
+
console.log('5) When done, move task to ## Completed');
|
|
710
|
+
console.log('6) Log to atris/team/executor/journal/YYYY-MM-DD.md');
|
|
566
711
|
console.log(' (Task, Delivered, Errors hit, Learned)');
|
|
567
712
|
console.log('');
|
|
568
713
|
console.log('⛔ Do NOT plan — just execute what\'s written.');
|
|
@@ -602,7 +747,7 @@ async function doAtris() {
|
|
|
602
747
|
}
|
|
603
748
|
console.log('━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━');
|
|
604
749
|
console.log('');
|
|
605
|
-
|
|
750
|
+
|
|
606
751
|
// Check execution mode
|
|
607
752
|
if (executionMode === 'agent') {
|
|
608
753
|
// Agent mode: execute via backend API
|
|
@@ -636,21 +781,24 @@ async function doAtris() {
|
|
|
636
781
|
// Build user prompt with context
|
|
637
782
|
let userPrompt = `⚠️ CRITICAL: Execute tasks NOW. Use file tools to edit code, terminal to run commands.\n\n`;
|
|
638
783
|
userPrompt += `You are the Executor. Get it done, precisely, following instructions perfectly.\n\n`;
|
|
639
|
-
|
|
784
|
+
|
|
640
785
|
if (filteredTasks) {
|
|
641
786
|
userPrompt += `## TASKS TO EXECUTE (from ${taskSource}):\n${filteredTasks}\n\n`;
|
|
642
787
|
} else {
|
|
643
788
|
userPrompt += `## TASKS TO EXECUTE:\n(No tasks found - check TODO.md)\n\n`;
|
|
644
789
|
}
|
|
645
|
-
|
|
790
|
+
|
|
646
791
|
userPrompt += `Your process (EXECUTE these steps):\n`;
|
|
647
792
|
userPrompt += `1. Read tasks from TODO.md (shown above)\n`;
|
|
648
793
|
userPrompt += `2. For each task: Show ASCII visualization first (especially complex changes)\n`;
|
|
649
|
-
userPrompt += `3.
|
|
650
|
-
userPrompt +=
|
|
651
|
-
userPrompt += `
|
|
794
|
+
userPrompt += `3. Run the Confidence Gate before editing\n`;
|
|
795
|
+
userPrompt += confidenceGatePrompt('do') + `\n`;
|
|
796
|
+
userPrompt += `4. Execute task: Use file edit tools, terminal commands, etc.\n`;
|
|
797
|
+
userPrompt += `5. Before completion, rerun the gate against proof and residual risk\n`;
|
|
798
|
+
userPrompt += `6. Move task to ## Completed in TODO.md\n`;
|
|
799
|
+
userPrompt += `7. Log to atris/team/executor/journal/YYYY-MM-DD.md\n`;
|
|
652
800
|
userPrompt += ` (Task, Delivered, Errors hit, Learned)\n`;
|
|
653
|
-
userPrompt += `
|
|
801
|
+
userPrompt += `8. Use MAP.md to navigate codebase\n\n`;
|
|
654
802
|
userPrompt += `DO NOT just describe what you would do - actually edit files and execute commands!\n`;
|
|
655
803
|
userPrompt += `Context: ${context}\n`;
|
|
656
804
|
userPrompt += `Start executing tasks now.`;
|
|
@@ -700,7 +848,7 @@ async function doAtris() {
|
|
|
700
848
|
console.error(`\n❌ Execution error: ${error.message}`);
|
|
701
849
|
},
|
|
702
850
|
});
|
|
703
|
-
|
|
851
|
+
|
|
704
852
|
console.log('\n');
|
|
705
853
|
console.log('━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━');
|
|
706
854
|
console.log('');
|
|
@@ -720,10 +868,10 @@ async function reviewAtris() {
|
|
|
720
868
|
const args = process.argv.slice(3);
|
|
721
869
|
const executeFlag = args.includes('--execute');
|
|
722
870
|
const showFull = args.includes('--full') || args.includes('--verbose');
|
|
723
|
-
|
|
871
|
+
|
|
724
872
|
const config = loadConfig();
|
|
725
873
|
const executionMode = executeFlag ? 'agent' : (config.execution_mode || 'prompt');
|
|
726
|
-
|
|
874
|
+
|
|
727
875
|
const targetDir = path.join(process.cwd(), 'atris');
|
|
728
876
|
const validatorFile = fs.existsSync(path.join(targetDir, 'team', 'validator', 'MEMBER.md'))
|
|
729
877
|
? path.join(targetDir, 'team', 'validator', 'MEMBER.md')
|
|
@@ -768,7 +916,7 @@ async function reviewAtris() {
|
|
|
768
916
|
// Read journal for timestamp context (History)
|
|
769
917
|
const { logFile, dateFormatted } = getLogPath();
|
|
770
918
|
let journalHistory = '';
|
|
771
|
-
|
|
919
|
+
|
|
772
920
|
// Load today's log
|
|
773
921
|
if (fs.existsSync(logFile)) {
|
|
774
922
|
journalHistory += `## TODAY (${dateFormatted}):\n` + fs.readFileSync(logFile, 'utf8') + '\n\n';
|
|
@@ -791,7 +939,7 @@ async function reviewAtris() {
|
|
|
791
939
|
// Sort desc, take top 3
|
|
792
940
|
allLogs.sort().reverse();
|
|
793
941
|
const recentLogs = allLogs.slice(0, 3);
|
|
794
|
-
|
|
942
|
+
|
|
795
943
|
if (recentLogs.length > 0) {
|
|
796
944
|
journalHistory += `## RECENT HISTORY (Drift Check):\n`;
|
|
797
945
|
for (const log of recentLogs) {
|
|
@@ -896,7 +1044,8 @@ async function reviewAtris() {
|
|
|
896
1044
|
readinessBits.join(', ') + '.',
|
|
897
1045
|
'',
|
|
898
1046
|
'This step prepares the validator. It does not mean the change has passed review yet.',
|
|
899
|
-
'
|
|
1047
|
+
'Confidence Gate: review must find loopholes, patch or name each one, and state residual risk before completion.',
|
|
1048
|
+
'Next I will run tests, walk each validate.md, and refresh the task projection/TODO view if durable state changed.',
|
|
900
1049
|
'',
|
|
901
1050
|
decision,
|
|
902
1051
|
'Run `atris review --verbose` for the full prompt and appendix.'
|
|
@@ -921,13 +1070,16 @@ async function reviewAtris() {
|
|
|
921
1070
|
console.log('Workflow:');
|
|
922
1071
|
console.log('1) Run the project test suite (follow TESTING_GUIDE if present).');
|
|
923
1072
|
console.log('2) Execute any `atris/features/*/validate.md` scripts; if a step fails, fix + rerun.');
|
|
924
|
-
console.log('3)
|
|
925
|
-
|
|
926
|
-
console.log('4)
|
|
1073
|
+
console.log('3) Run the Confidence Gate before approving completion.');
|
|
1074
|
+
printConfidenceGate(' ');
|
|
1075
|
+
console.log('4) Confirm active task state is clean: no unresolved Backlog/In Progress/Blocked rows for the reviewed work.');
|
|
1076
|
+
console.log(' If durable task state changed, regenerate the readable view with `atris task render --out atris/TODO.md`.');
|
|
1077
|
+
console.log(' Do not hand-delete rendered completed history; use `atris task list --status done` for the ledger.');
|
|
1078
|
+
console.log('5) Log to atris/team/validator/journal/YYYY-MM-DD.md');
|
|
927
1079
|
console.log(' (Task, Result, Issues found, Learned)');
|
|
928
|
-
console.log('
|
|
1080
|
+
console.log('6) If anything surprised you, append to atris/lessons.md.');
|
|
929
1081
|
console.log('');
|
|
930
|
-
console.log('Done when: ✅ All good.
|
|
1082
|
+
console.log('Done when: ✅ All good. Active task state clean. Ready for human testing.');
|
|
931
1083
|
console.log('');
|
|
932
1084
|
}
|
|
933
1085
|
|
|
@@ -963,7 +1115,7 @@ async function reviewAtris() {
|
|
|
963
1115
|
console.log('━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━');
|
|
964
1116
|
console.log('');
|
|
965
1117
|
}
|
|
966
|
-
|
|
1118
|
+
|
|
967
1119
|
// Check execution mode
|
|
968
1120
|
if (executionMode === 'agent') {
|
|
969
1121
|
// Agent mode: execute via backend API
|
|
@@ -987,12 +1139,12 @@ async function reviewAtris() {
|
|
|
987
1139
|
if (testingGuide) {
|
|
988
1140
|
systemPrompt += '## TESTING GUIDE\n' + testingGuide + '\n\n';
|
|
989
1141
|
}
|
|
990
|
-
|
|
1142
|
+
|
|
991
1143
|
const personaFile = path.join(targetDir, 'PERSONA.md');
|
|
992
1144
|
if (fs.existsSync(personaFile)) {
|
|
993
1145
|
systemPrompt += '## PERSONA.md\n' + fs.readFileSync(personaFile, 'utf8') + '\n\n';
|
|
994
1146
|
}
|
|
995
|
-
|
|
1147
|
+
|
|
996
1148
|
if (mapPath) {
|
|
997
1149
|
systemPrompt += `## MAP.md\nRead this file for file:line references: ${mapPath}\n\n`;
|
|
998
1150
|
}
|
|
@@ -1003,10 +1155,12 @@ async function reviewAtris() {
|
|
|
1003
1155
|
userPrompt += ` 1. Ultrathink (say "ultrathink", think 3 times)\n`;
|
|
1004
1156
|
userPrompt += ` 2. Check requirements → build → edge cases → errors → integration\n`;
|
|
1005
1157
|
userPrompt += ` 3. Run tests (unit, integration, linting, type checking)\n`;
|
|
1006
|
-
userPrompt += ` 4.
|
|
1007
|
-
userPrompt +=
|
|
1008
|
-
userPrompt += `
|
|
1009
|
-
|
|
1158
|
+
userPrompt += ` 4. Run the Confidence Gate before approving completion\n`;
|
|
1159
|
+
userPrompt += confidenceGatePrompt('review') + `\n`;
|
|
1160
|
+
userPrompt += ` 5. Detect Drift: Scan the Journal History below. Do you see the same friction 2x?\n`;
|
|
1161
|
+
userPrompt += ` 6. If issues found: report → "atris do" fixes → "atris review" again\n`;
|
|
1162
|
+
userPrompt += ` 7. Repeat until: "✅ All good. Ready for human testing."\n\n`;
|
|
1163
|
+
|
|
1010
1164
|
if (taskContexts) {
|
|
1011
1165
|
userPrompt += `## TODO.md:\n${taskContexts}\n\n`;
|
|
1012
1166
|
}
|
|
@@ -1014,12 +1168,14 @@ async function reviewAtris() {
|
|
|
1014
1168
|
if (journalHistory) {
|
|
1015
1169
|
userPrompt += `## JOURNAL HISTORY (For Evolution/Drift Check):\n${journalHistory}\n\n`;
|
|
1016
1170
|
}
|
|
1017
|
-
|
|
1171
|
+
|
|
1018
1172
|
userPrompt += `Your job:\n`;
|
|
1019
1173
|
userPrompt += ` • Verify everything works\n`;
|
|
1174
|
+
userPrompt += ` • Find all plausible loopholes; patch them or name residual risk\n`;
|
|
1020
1175
|
userPrompt += ` • Test thoroughly (unless user says no)\n`;
|
|
1021
|
-
userPrompt += ` •
|
|
1022
|
-
userPrompt += ` If
|
|
1176
|
+
userPrompt += ` • Confirm active task state is clean — no unresolved Backlog/In Progress/Blocked rows for reviewed work.\n`;
|
|
1177
|
+
userPrompt += ` If durable task state changed, regenerate the readable view with \`atris task render --out atris/TODO.md\`.\n`;
|
|
1178
|
+
userPrompt += ` Do not hand-delete rendered completed history; if a task fails, move or mark it blocked with a note.\n`;
|
|
1023
1179
|
userPrompt += ` • Log to atris/team/validator/journal/YYYY-MM-DD.md\n`;
|
|
1024
1180
|
userPrompt += ` (Task, Result, Issues found, Learned)\n`;
|
|
1025
1181
|
userPrompt += ` • If anything surprised you, append to atris/lessons.md\n`;
|
|
@@ -1072,7 +1228,7 @@ async function reviewAtris() {
|
|
|
1072
1228
|
console.error(`\n❌ Execution error: ${error.message}`);
|
|
1073
1229
|
},
|
|
1074
1230
|
});
|
|
1075
|
-
|
|
1231
|
+
|
|
1076
1232
|
console.log('\n');
|
|
1077
1233
|
console.log('━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━');
|
|
1078
1234
|
console.log('');
|
|
@@ -1175,9 +1331,97 @@ async function reviewAtris() {
|
|
|
1175
1331
|
});
|
|
1176
1332
|
}
|
|
1177
1333
|
|
|
1334
|
+
/**
|
|
1335
|
+
* Fast Agent SDK execution - for "atris go" command.
|
|
1336
|
+
* Direct execution without planning workflow, like "devin" or "cursor agent".
|
|
1337
|
+
*/
|
|
1338
|
+
async function executeAgentSDKFast(userInput) {
|
|
1339
|
+
const http = require('http');
|
|
1340
|
+
|
|
1341
|
+
console.log(`⚡ Executing: ${userInput}`);
|
|
1342
|
+
console.log('');
|
|
1343
|
+
|
|
1344
|
+
try {
|
|
1345
|
+
const postData = JSON.stringify({
|
|
1346
|
+
message: userInput,
|
|
1347
|
+
workspace_path: process.cwd(),
|
|
1348
|
+
model: 'claude-sonnet-4-6'
|
|
1349
|
+
});
|
|
1350
|
+
|
|
1351
|
+
const options = {
|
|
1352
|
+
hostname: '127.0.0.1',
|
|
1353
|
+
port: 8000,
|
|
1354
|
+
path: '/api/agent-sdk/execute',
|
|
1355
|
+
method: 'POST',
|
|
1356
|
+
headers: {
|
|
1357
|
+
'Content-Type': 'application/json',
|
|
1358
|
+
'Content-Length': Buffer.byteLength(postData)
|
|
1359
|
+
}
|
|
1360
|
+
};
|
|
1361
|
+
|
|
1362
|
+
const response = await new Promise((resolve, reject) => {
|
|
1363
|
+
const req = http.request(options, (res) => {
|
|
1364
|
+
let data = '';
|
|
1365
|
+
res.on('data', (chunk) => data += chunk);
|
|
1366
|
+
res.on('end', () => {
|
|
1367
|
+
try {
|
|
1368
|
+
const parsed = JSON.parse(data);
|
|
1369
|
+
if (res.statusCode < 200 || res.statusCode >= 300) {
|
|
1370
|
+
reject(new Error(parsed.detail || parsed.error || `HTTP ${res.statusCode}`));
|
|
1371
|
+
return;
|
|
1372
|
+
}
|
|
1373
|
+
resolve(parsed);
|
|
1374
|
+
} catch (e) {
|
|
1375
|
+
reject(new Error(`Failed to parse response: ${data}`));
|
|
1376
|
+
}
|
|
1377
|
+
});
|
|
1378
|
+
});
|
|
1379
|
+
|
|
1380
|
+
req.on('error', reject);
|
|
1381
|
+
req.setTimeout(120000, () => {
|
|
1382
|
+
req.destroy();
|
|
1383
|
+
reject(new Error('Request timeout after 120s'));
|
|
1384
|
+
});
|
|
1385
|
+
req.write(postData);
|
|
1386
|
+
req.end();
|
|
1387
|
+
});
|
|
1388
|
+
|
|
1389
|
+
if (response.error) {
|
|
1390
|
+
throw new Error(response.error);
|
|
1391
|
+
}
|
|
1392
|
+
|
|
1393
|
+
// Display results in a clean format
|
|
1394
|
+
if (response.result && Array.isArray(response.result)) {
|
|
1395
|
+
for (const event of response.result) {
|
|
1396
|
+
if (event.type === 'assistant' && event.content) {
|
|
1397
|
+
for (const block of event.content) {
|
|
1398
|
+
if (block.type === 'text') {
|
|
1399
|
+
console.log(block.text);
|
|
1400
|
+
} else if (block.type === 'tool_use') {
|
|
1401
|
+
console.log(`\n⚙️ ${block.tool_name}`);
|
|
1402
|
+
}
|
|
1403
|
+
}
|
|
1404
|
+
} else if (event.type === 'result') {
|
|
1405
|
+
console.log(`\n✅ Done in ${event.duration_ms}ms`);
|
|
1406
|
+
if (event.cost_usd) {
|
|
1407
|
+
console.log(`💰 Cost: $${event.cost_usd.toFixed(4)}`);
|
|
1408
|
+
}
|
|
1409
|
+
}
|
|
1410
|
+
}
|
|
1411
|
+
}
|
|
1412
|
+
|
|
1413
|
+
} catch (error) {
|
|
1414
|
+
console.error(`✗ Error: ${error.message}`);
|
|
1415
|
+
console.log('');
|
|
1416
|
+
console.log('💡 Make sure the AtrisOS backend is running on port 8000');
|
|
1417
|
+
console.log(' Start it with: cd /Users/keshavrao/arena/atrisos-backend/backend && python -m uvicorn main:app --reload --port 8000');
|
|
1418
|
+
process.exit(1);
|
|
1419
|
+
}
|
|
1420
|
+
}
|
|
1178
1421
|
|
|
1179
1422
|
module.exports = {
|
|
1180
1423
|
planAtris,
|
|
1181
1424
|
doAtris,
|
|
1182
|
-
reviewAtris
|
|
1425
|
+
reviewAtris,
|
|
1426
|
+
executeAgentSDKFast
|
|
1183
1427
|
};
|
|
@@ -30,7 +30,7 @@ async function cleanWorkspace() {
|
|
|
30
30
|
const slug = process.argv[3];
|
|
31
31
|
const autoConfirm = process.argv.includes('--yes');
|
|
32
32
|
|
|
33
|
-
if (!slug || slug === '--help') {
|
|
33
|
+
if (!slug || slug === '--help' || slug === '-h' || slug === 'help') {
|
|
34
34
|
console.log('');
|
|
35
35
|
console.log('Usage: atris clean-workspace <business-slug> [--yes]');
|
|
36
36
|
console.log('');
|