atris 3.53.0 → 3.56.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.
Files changed (119) hide show
  1. package/FOR_AGENTS.md +7 -0
  2. package/README.md +1 -1
  3. package/atris/policies/ANTISLOP.md +2 -1
  4. package/atris/skills/copy-editor/SKILL.md +2 -1
  5. package/atris/skills/design/SKILL.md +1 -1
  6. package/atris/skills/x-search/SKILL.md +24 -22
  7. package/atris/skills/youtube/SKILL.md +82 -33
  8. package/atris/team/_template/SOUL.md +40 -0
  9. package/atris/team/validator/MEMBER.md +1 -2
  10. package/bin/atris +21 -0
  11. package/bin/atris.js +563 -373
  12. package/commands/api-key.js +170 -0
  13. package/commands/auth.js +453 -43
  14. package/commands/autoland.js +3 -1
  15. package/commands/autopilot-front.js +58 -11
  16. package/commands/avail.js +5 -4
  17. package/commands/balance.js +55 -0
  18. package/commands/bench.js +29 -1
  19. package/commands/brain.js +63 -12
  20. package/commands/brainstorm.js +18 -0
  21. package/commands/business.js +149 -1
  22. package/commands/chat-scan.js +17 -4
  23. package/commands/close.js +5 -1
  24. package/commands/doctor.js +174 -0
  25. package/commands/dream.js +7 -0
  26. package/commands/drill.js +34 -2
  27. package/commands/engine.js +47 -35
  28. package/commands/errors.js +58 -8
  29. package/commands/experiments.js +14 -0
  30. package/commands/feedback.js +61 -2
  31. package/commands/fleet-report.js +27 -7
  32. package/commands/fleet.js +98 -11
  33. package/commands/founder.js +60 -21
  34. package/commands/human-missions.js +79 -4
  35. package/commands/improve.js +54 -4
  36. package/commands/init.js +68 -92
  37. package/commands/install.js +40 -0
  38. package/commands/integrations.js +565 -30
  39. package/commands/interview.js +8 -0
  40. package/commands/land.js +48 -17
  41. package/commands/learn.js +29 -4
  42. package/commands/log.js +51 -0
  43. package/commands/member.js +68 -10
  44. package/commands/mission.js +287 -50
  45. package/commands/now.js +15 -3
  46. package/commands/orb.js +97 -2
  47. package/commands/pack.js +83 -9
  48. package/commands/playbook.js +381 -0
  49. package/commands/plugin.js +16 -0
  50. package/commands/radar.js +31 -7
  51. package/commands/recap.js +128 -21
  52. package/commands/release.js +102 -2
  53. package/commands/review.js +5 -10
  54. package/commands/revisions.js +55 -0
  55. package/commands/run-front.js +12 -4
  56. package/commands/scout.js +12 -1
  57. package/commands/search.js +123 -28
  58. package/commands/sign.js +2 -2
  59. package/commands/signup.js +12 -3
  60. package/commands/site-deploy.js +17 -4
  61. package/commands/site.js +2 -2
  62. package/commands/skill-eval.js +289 -0
  63. package/commands/skill.js +56 -6
  64. package/commands/social.js +603 -0
  65. package/commands/spaceship.js +69 -6
  66. package/commands/stream.js +8 -1
  67. package/commands/study.js +32 -19
  68. package/commands/sync.js +28 -22
  69. package/commands/task.js +435 -60
  70. package/commands/teach.js +72 -63
  71. package/commands/terminal.js +25 -9
  72. package/commands/topup.js +88 -0
  73. package/commands/truth.js +52 -6
  74. package/commands/usage.js +91 -0
  75. package/commands/verify.js +3 -2
  76. package/commands/version.js +3 -1
  77. package/commands/voice.js +5 -1
  78. package/commands/who.js +69 -11
  79. package/commands/wiki.js +7 -4
  80. package/commands/wish.js +76 -5
  81. package/commands/workflow.js +327 -145
  82. package/commands/worktree.js +1 -0
  83. package/commands/write.js +5 -0
  84. package/commands/x-search.js +340 -0
  85. package/commands/xp.js +5 -1
  86. package/commands/youtube.js +551 -25
  87. package/lib/account-bound.js +47 -0
  88. package/lib/auto-accept-certified.js +8 -1
  89. package/lib/auto-lessons.js +186 -0
  90. package/lib/autoland.js +4 -2
  91. package/lib/chat-log-scan.js +7 -4
  92. package/lib/cli-json.js +77 -0
  93. package/lib/cli-scope.js +26 -0
  94. package/lib/codex-flight.js +1 -0
  95. package/lib/conductor-artifacts.js +1 -1
  96. package/lib/context-gatherer.js +11 -0
  97. package/lib/developer-api.js +116 -0
  98. package/lib/feedback-triage.js +274 -0
  99. package/lib/first-minute.js +398 -0
  100. package/lib/fleet.js +115 -34
  101. package/lib/functional-owner.js +22 -0
  102. package/lib/known-commands.js +31 -5
  103. package/lib/member-scaffold.js +197 -0
  104. package/lib/mission-root.js +4 -2
  105. package/lib/noninteractive.js +88 -0
  106. package/lib/policy-lessons.js +4 -1
  107. package/lib/revision-metric.js +279 -0
  108. package/lib/scratch-root.js +48 -0
  109. package/lib/skill-eval-gate.js +249 -0
  110. package/lib/task-db.js +4 -0
  111. package/lib/task-proof.js +69 -8
  112. package/lib/verifier-quality.js +69 -0
  113. package/lib/wish-audit.js +2 -2
  114. package/lib/wish-delegate.js +10 -1
  115. package/lib/workspace-scaffold.js +270 -0
  116. package/package.json +3 -2
  117. package/scripts/det/checklist-score.js +191 -0
  118. package/scripts/det/ytsearch +31 -0
  119. package/utils/update-check.js +15 -0
package/commands/init.js CHANGED
@@ -1,7 +1,7 @@
1
1
  const fs = require('fs');
2
2
  const path = require('path');
3
3
  const { ensureExperimentsFramework } = require('./experiments');
4
- const { ensureWikiScaffold } = require('../lib/wiki');
4
+ const { ensureWorkspaceBrain } = require('../lib/workspace-scaffold');
5
5
  const { upsertAtrisClaudeBootBlock } = require('../lib/claude-boot-block');
6
6
  const {
7
7
  upsertAgentVoiceCard,
@@ -257,21 +257,55 @@ ${profile.hasCode ? `**Validation:** Run \`${profile.testCommand}\` to verify ch
257
257
  } catch {}
258
258
  }
259
259
 
260
+ function mapStubFromTree(projectRoot = process.cwd()) {
261
+ let entries = [];
262
+ try {
263
+ entries = fs.readdirSync(projectRoot, { withFileTypes: true })
264
+ .filter((entry) => !entry.name.startsWith('.') && entry.name !== 'node_modules' && entry.name !== 'atris')
265
+ .slice(0, 40)
266
+ .map((entry) => `- \`${entry.name}${entry.isDirectory() ? '/' : ''}\``);
267
+ } catch {
268
+ entries = [];
269
+ }
270
+ const body = entries.length
271
+ ? entries.join('\n')
272
+ : '- (empty project — add file:line refs as you explore)';
273
+ // Keep the classic placeholder markers so post-init does not treat this as a
274
+ // finished MAP and auto-run `atris do` before team members exist.
275
+ return `# MAP.md
276
+
277
+ > Generated by your AI agent after reading atris.md
278
+ > Lean stub from \`atris init --minimal\`. Expand with file:line refs as you work.
279
+
280
+ Run your AI agent with atris.md to populate this file.
281
+
282
+ ## Top level
283
+
284
+ ${body}
285
+ `;
286
+ }
287
+
260
288
  function initAtris() {
261
289
  // Print usage on -h / --help / help instead of running init (which scaffolds
262
290
  // many files, including atris/now.md and atris/team/). Asking for help
263
291
  // shouldn't have file-system side effects.
264
292
  const args = process.argv.slice(3);
265
293
  if (args[0] === '-h' || args[0] === '--help' || args[0] === 'help') {
266
- console.log('Usage: atris init [--force] [--yes|-y] [--verbose]');
294
+ console.log('Usage: atris init [--force] [--yes|-y] [--verbose] [--minimal] [--full] [--with-adapters] [--with-skills]');
267
295
  console.log('');
268
296
  console.log(' Scaffold the atris/ workspace in the current directory.');
269
297
  console.log(' Refuses to run inside an existing atris/ folder unless --force is passed.');
270
298
  console.log(' Use --yes or -y to skip the interactive context gatherer after scaffolding.');
271
299
  console.log(' Use --verbose to list every file installed.');
300
+ console.log(' Use --minimal for atris.md + MAP + TODO + today journal + .atris/state (no IDE farm).');
301
+ console.log(' Use --with-adapters / --with-skills with --minimal, or --full for the default full scaffold.');
272
302
  return;
273
303
  }
274
304
  const verbose = args.includes('--verbose');
305
+ const minimal = args.includes('--minimal') && !args.includes('--full');
306
+ const withAdapters = !minimal || args.includes('--with-adapters');
307
+ const withSkills = !minimal || args.includes('--with-skills');
308
+ const withTeam = !minimal;
275
309
  const ready = {
276
310
  workspace: new Set(),
277
311
  team: new Set(),
@@ -287,10 +321,19 @@ function initAtris() {
287
321
  };
288
322
  const printReadyCounts = () => {
289
323
  console.log(`workspace files ready (${ready.workspace.size})`);
290
- console.log(`team members ready (${ready.team.size})`);
291
- console.log('more members are available with atris member create <name>');
292
- console.log(`agent adapters ready (${ready.adapters.size})`);
293
- console.log(`skills installed (${ready.skills.size})`);
324
+ if (withTeam || ready.team.size > 0) {
325
+ console.log(`team members ready (${ready.team.size})`);
326
+ console.log('more members are available with atris member create <name>');
327
+ }
328
+ if (withAdapters || ready.adapters.size > 0) {
329
+ console.log(`agent adapters ready (${ready.adapters.size})`);
330
+ }
331
+ if (withSkills || ready.skills.size > 0) {
332
+ console.log(`skills installed (${ready.skills.size})`);
333
+ }
334
+ if (minimal) {
335
+ console.log('minimal scaffold (add --with-adapters / --with-skills or init --full for the rest)');
336
+ }
294
337
  };
295
338
  // GUARD: Refuse nested init.
296
339
  // Bug: running `atris init` inside an existing `atris/` folder creates
@@ -385,8 +428,6 @@ function initAtris() {
385
428
  const gettingStartedFile = path.join(targetDir, 'GETTING_STARTED.md');
386
429
  const forAgentsFile = path.join(targetDir, 'FOR_AGENTS.md');
387
430
  const personaFile = path.join(targetDir, 'PERSONA.md');
388
- const mapFile = path.join(targetDir, 'MAP.md');
389
- const todoFile = path.join(targetDir, 'TODO.md');
390
431
  const navigatorFile = path.join(teamDir, 'navigator.md');
391
432
  const executorFile = path.join(teamDir, 'executor.md');
392
433
  const validatorFile = path.join(teamDir, 'validator.md');
@@ -412,16 +453,19 @@ function initAtris() {
412
453
  markReady('workspace', 'PERSONA.md', '✓ Created PERSONA.md');
413
454
  }
414
455
 
415
- const wikiDir = path.join(targetDir, 'wiki');
416
- const wikiAlreadyExists = fs.existsSync(wikiDir);
417
- ensureWikiScaffold(process.cwd());
418
- if (!wikiAlreadyExists) {
419
- markReady('workspace', 'wiki/', '✓ Created wiki/ scaffold');
456
+ const brain = ensureWorkspaceBrain(cwd);
457
+ for (const rel of brain.created) {
458
+ const name = rel.replace(/^atris\//, '').replace(/\/$/, '');
459
+ markReady('workspace', name, `✓ Created ${name}`);
420
460
  }
421
461
 
422
- if (!fs.existsSync(mapFile)) {
423
- fs.writeFileSync(mapFile, '# MAP.md\n\n> Generated by your AI agent after reading atris.md\n\nRun your AI agent with atris.md to populate this file.\n');
424
- markReady('workspace', 'MAP.md', ' Created MAP.md placeholder');
462
+ if (minimal) {
463
+ const mapFile = path.join(targetDir, 'MAP.md');
464
+ const currentMap = fs.existsSync(mapFile) ? fs.readFileSync(mapFile, 'utf8') : '';
465
+ if (!currentMap || /Generated by your AI agent after reading atris\.md/i.test(currentMap)) {
466
+ fs.writeFileSync(mapFile, mapStubFromTree(cwd));
467
+ markReady('workspace', 'MAP.md', '✓ Wrote lean MAP.md stub from the project tree');
468
+ }
425
469
  }
426
470
 
427
471
  // Create INTUITION.md - captures learnings, preferences, dead ends
@@ -460,42 +504,6 @@ function initAtris() {
460
504
  markReady('workspace', 'INTUITION.md', '✓ Created INTUITION.md');
461
505
  }
462
506
 
463
- if (!fs.existsSync(todoFile)) {
464
- fs.writeFileSync(todoFile, `# TODO.md
465
-
466
- > Working task queue for this project. Target state = 0.
467
- > Note: Daily tasks live in \`atris/logs/YYYY/YYYY-MM-DD.md\`
468
-
469
- ---
470
-
471
- ## Backlog
472
-
473
- (See today's journal)
474
-
475
- ---
476
-
477
- ## In Progress
478
-
479
- (See today's journal)
480
-
481
- ---
482
-
483
- ## Completed
484
-
485
- (Validator deletes after verification)
486
-
487
- ---
488
- `);
489
- markReady('workspace', 'TODO.md', '✓ Created TODO.md placeholder');
490
- }
491
-
492
- const nowFile = path.join(targetDir, 'now.md');
493
- if (!fs.existsSync(nowFile)) {
494
- const { renderDefaultNow } = require('./now');
495
- fs.writeFileSync(nowFile, renderDefaultNow(cwd), 'utf8');
496
- markReady('workspace', 'now.md', '✓ Created now.md');
497
- }
498
-
499
507
  // Create lessons.md (feedback loop for learning across features)
500
508
  const lessonsFile = path.join(targetDir, 'lessons.md');
501
509
  if (!fs.existsSync(lessonsFile)) {
@@ -509,46 +517,6 @@ function initAtris() {
509
517
  markReady('workspace', 'lessons.md', '✓ Created lessons.md');
510
518
  }
511
519
 
512
- // Create logs directory and today's journal with bootstrap tasks
513
- const logsDir = path.join(targetDir, 'logs');
514
- const yearDir = path.join(logsDir, new Date().getFullYear().toString());
515
- const today = new Date().toISOString().split('T')[0];
516
- const journalFile = path.join(yearDir, `${today}.md`);
517
-
518
- if (!fs.existsSync(yearDir)) {
519
- fs.mkdirSync(yearDir, { recursive: true });
520
- detail(`✓ Created logs/${new Date().getFullYear()}/ folder`);
521
- }
522
-
523
- if (!fs.existsSync(journalFile)) {
524
- fs.writeFileSync(journalFile, `# Log — ${today}
525
-
526
- ## Completed ✅
527
-
528
- ---
529
-
530
- ## In Progress 🔄
531
-
532
- ---
533
-
534
- ## Backlog
535
-
536
- - **T1:** Generate MAP.md — scan codebase, create navigation index with file:line refs
537
-
538
- ---
539
-
540
- ## Notes
541
-
542
- **Bootstrap:** Say "atris next" to start. After MAP.md is generated, system will brainstorm ideas for your first build.
543
-
544
- ---
545
-
546
- ## Inbox
547
-
548
- `);
549
- markReady('workspace', `logs/${today}.md`, `✓ Created today's journal with bootstrap tasks`);
550
- }
551
-
552
520
  // Create features directory and README
553
521
  const featuresDir = path.join(targetDir, 'features');
554
522
  const templatesDir = path.join(featuresDir, '_templates');
@@ -608,6 +576,7 @@ function initAtris() {
608
576
 
609
577
 
610
578
  // Copy team members (MEMBER.md format — directory per member with skills/tools/context)
579
+ if (withTeam) {
611
580
  const starterMembers = ['navigator', 'executor', 'validator', 'mission-lead', 'improver', 'customer-lead'];
612
581
  const starterMemberFiles = ['MEMBER.md', 'SOUL.md', 'START_HERE.md'];
613
582
  const starterMemberDirs = ['skills', 'tools', 'context'];
@@ -662,6 +631,7 @@ tools: []
662
631
  fs.writeFileSync(path.join(templateTargetDir, 'MEMBER.md'), templateContent);
663
632
  markReady('workspace', 'team/_template/MEMBER.md', '✓ Created team/_template/MEMBER.md');
664
633
  }
634
+ }
665
635
 
666
636
  // Detect project context and generate profile
667
637
  const profile = detectProjectContext(process.cwd());
@@ -674,6 +644,7 @@ tools: []
674
644
  detail('✓ Injected project patterns into team specs');
675
645
 
676
646
  // Create agent instruction files for different tools
647
+ if (withAdapters) {
677
648
  const agentInstructions = `# AGENTS.md — Universal Agent Instructions
678
649
 
679
650
  > Works with: Claude Code, Cursor, Codex, OpenClaw, Windsurf, and any AI coding agent.
@@ -969,8 +940,10 @@ Read atris/MAP.md. Begin iteration 1.`;
969
940
  fs.writeFileSync(autopilotCommandFile, autopilotCommand);
970
941
  markReady('adapters', '.claude/commands/atris-autopilot.md', '✓ Created .claude/commands/atris-autopilot.md (autonomous loops)');
971
942
  }
943
+ }
972
944
 
973
945
  // Copy skills from package to atris/skills/ and symlink to .claude/skills/
946
+ if (withSkills) {
974
947
  const skillsSourceDir = path.join(__dirname, '..', 'atris', 'skills');
975
948
  const skillsTargetDir = path.join(targetDir, 'skills');
976
949
  const claudeSkillsDir = path.join(process.cwd(), '.claude', 'skills');
@@ -1051,8 +1024,10 @@ Read atris/MAP.md. Begin iteration 1.`;
1051
1024
  }
1052
1025
  }
1053
1026
  }
1027
+ }
1054
1028
 
1055
1029
  // CLAUDE.md for Claude Code (copy from atris/)
1030
+ if (withAdapters) {
1056
1031
  const claudeMdSource = path.join(__dirname, '..', 'atris', 'CLAUDE.md');
1057
1032
  const claudeMdFile = path.join(targetDir, 'CLAUDE.md');
1058
1033
  if (!fs.existsSync(claudeMdFile) && fs.existsSync(claudeMdSource)) {
@@ -1118,6 +1093,7 @@ Read atris/MAP.md. Begin iteration 1.`;
1118
1093
  fs.writeFileSync(rootClaudeMd, upsertAtrisClaudeBootBlock().content);
1119
1094
  markReady('adapters', 'CLAUDE.md', '✓ created CLAUDE.md with atris block');
1120
1095
  }
1096
+ }
1121
1097
 
1122
1098
  if (fs.existsSync(sourceFile)) {
1123
1099
  fs.copyFileSync(sourceFile, targetFile);
@@ -0,0 +1,40 @@
1
+ const { ensureWorkspaceBrain, workspaceBrainPresent } = require('../lib/workspace-scaffold');
2
+
3
+ function printInstallUsage(stream = console.log) {
4
+ stream('Usage: atris install');
5
+ stream('alias: atris workspace install');
6
+ stream('');
7
+ stream('installs the atris/ brain into the current directory if missing.');
8
+ }
9
+
10
+ function installCommand(args = [], { verb } = {}) {
11
+ const sub = args[0];
12
+ if (verb === 'workspace' && sub && sub !== 'install' && sub !== '-h' && sub !== '--help' && sub !== 'help') {
13
+ console.error('Usage: atris workspace install');
14
+ process.exit(1);
15
+ }
16
+
17
+ const flags = verb === 'workspace' && sub === 'install' ? args.slice(1) : args;
18
+ if (flags[0] === '-h' || flags[0] === '--help' || flags[0] === 'help') {
19
+ printInstallUsage();
20
+ return 0;
21
+ }
22
+
23
+ const root = process.cwd();
24
+ if (workspaceBrainPresent(root)) {
25
+ console.log('Atris already installed.');
26
+ return 0;
27
+ }
28
+
29
+ const { created } = ensureWorkspaceBrain(root);
30
+ if (created.length === 0) {
31
+ console.log('Atris already installed.');
32
+ return 0;
33
+ }
34
+ for (const rel of created) {
35
+ console.log(rel);
36
+ }
37
+ return 0;
38
+ }
39
+
40
+ module.exports = { installCommand };