@chinhae/atw-cli 0.3.5 → 0.4.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 (102) hide show
  1. package/README.md +188 -15
  2. package/dist/cli/index.d.ts.map +1 -1
  3. package/dist/cli/index.js +25 -1
  4. package/dist/cli/index.js.map +1 -1
  5. package/dist/commands/init.d.ts +3 -0
  6. package/dist/commands/init.d.ts.map +1 -1
  7. package/dist/commands/init.js +154 -17
  8. package/dist/commands/init.js.map +1 -1
  9. package/dist/commands/mode.d.ts +21 -0
  10. package/dist/commands/mode.d.ts.map +1 -0
  11. package/dist/commands/mode.js +401 -0
  12. package/dist/commands/mode.js.map +1 -0
  13. package/dist/commands/update.d.ts +7 -0
  14. package/dist/commands/update.d.ts.map +1 -1
  15. package/dist/commands/update.js +20 -13
  16. package/dist/commands/update.js.map +1 -1
  17. package/dist/commands/workflow.d.ts +17 -0
  18. package/dist/commands/workflow.d.ts.map +1 -1
  19. package/dist/commands/workflow.js +9 -3
  20. package/dist/commands/workflow.js.map +1 -1
  21. package/dist/configurators/claude.d.ts +3 -2
  22. package/dist/configurators/claude.d.ts.map +1 -1
  23. package/dist/configurators/claude.js +3 -3
  24. package/dist/configurators/claude.js.map +1 -1
  25. package/dist/configurators/codex.d.ts +4 -3
  26. package/dist/configurators/codex.d.ts.map +1 -1
  27. package/dist/configurators/codex.js +10 -10
  28. package/dist/configurators/codex.js.map +1 -1
  29. package/dist/configurators/index.d.ts +9 -3
  30. package/dist/configurators/index.d.ts.map +1 -1
  31. package/dist/configurators/index.js +95 -17
  32. package/dist/configurators/index.js.map +1 -1
  33. package/dist/configurators/shared.d.ts +13 -0
  34. package/dist/configurators/shared.d.ts.map +1 -1
  35. package/dist/configurators/shared.js +25 -0
  36. package/dist/configurators/shared.js.map +1 -1
  37. package/dist/configurators/workflow.d.ts +15 -1
  38. package/dist/configurators/workflow.d.ts.map +1 -1
  39. package/dist/configurators/workflow.js +23 -5
  40. package/dist/configurators/workflow.js.map +1 -1
  41. package/dist/configurators/zcode.d.ts +1 -1
  42. package/dist/configurators/zcode.d.ts.map +1 -1
  43. package/dist/configurators/zcode.js +2 -2
  44. package/dist/configurators/zcode.js.map +1 -1
  45. package/dist/constants/paths.d.ts +4 -0
  46. package/dist/constants/paths.d.ts.map +1 -1
  47. package/dist/constants/paths.js +4 -0
  48. package/dist/constants/paths.js.map +1 -1
  49. package/dist/migrations/manifests/0.3.6.json +9 -0
  50. package/dist/migrations/manifests/0.4.0.json +9 -0
  51. package/dist/templates/atw/index.d.ts +10 -1
  52. package/dist/templates/atw/index.d.ts.map +1 -1
  53. package/dist/templates/atw/index.js +11 -1
  54. package/dist/templates/atw/index.js.map +1 -1
  55. package/dist/templates/atw/scripts/add_session.py +34 -13
  56. package/dist/templates/atw/scripts/common/active_task.py +2 -2
  57. package/dist/templates/atw/scripts/common/config.py +13 -0
  58. package/dist/templates/atw/scripts/common/developer.py +15 -4
  59. package/dist/templates/atw/scripts/common/noob_mode.py +35 -15
  60. package/dist/templates/atw/scripts/common/packages_context.py +16 -3
  61. package/dist/templates/atw/scripts/common/session_context.py +77 -19
  62. package/dist/templates/atw/scripts/common/task_store.py +78 -27
  63. package/dist/templates/atw/scripts/noob_mode.py +16 -4
  64. package/dist/templates/atw/scripts/task.py +99 -38
  65. package/dist/templates/atw/workflow-general.md +554 -0
  66. package/dist/templates/atw/workflow.md +3 -3
  67. package/dist/templates/codex/hooks/session-start.py +69 -18
  68. package/dist/templates/common/bundled-skills/atw-noob-mode/SKILL.md +16 -9
  69. package/dist/templates/common/commands/start.md +43 -0
  70. package/dist/templates/copilot/hooks/session-start.py +69 -18
  71. package/dist/templates/dsh/DSH.md +43 -0
  72. package/dist/templates/markdown/agents.md +11 -0
  73. package/dist/templates/markdown/index.d.ts +9 -0
  74. package/dist/templates/markdown/index.d.ts.map +1 -1
  75. package/dist/templates/markdown/index.js +14 -1
  76. package/dist/templates/markdown/index.js.map +1 -1
  77. package/dist/templates/markdown/spec/conventions.md.txt +13 -0
  78. package/dist/templates/opencode/lib/atw-context.js +19 -0
  79. package/dist/templates/opencode/lib/session-utils.js +79 -24
  80. package/dist/templates/opencode/plugins/inject-workflow-state.js +18 -8
  81. package/dist/templates/pi/extensions/atw/index.ts.txt +20 -9
  82. package/dist/templates/shared-hooks/inject-shell-session-context.py +3 -3
  83. package/dist/templates/shared-hooks/inject-workflow-state.py +21 -2
  84. package/dist/templates/shared-hooks/session-start.py +70 -22
  85. package/dist/templates/snow/SNOW.md +30 -0
  86. package/dist/templates/snow/hooks/write-atw-context.py +64 -0
  87. package/dist/utils/manifest-prune.d.ts +2 -1
  88. package/dist/utils/manifest-prune.d.ts.map +1 -1
  89. package/dist/utils/manifest-prune.js +10 -7
  90. package/dist/utils/manifest-prune.js.map +1 -1
  91. package/dist/utils/optional-skills.d.ts.map +1 -1
  92. package/dist/utils/optional-skills.js +2 -1
  93. package/dist/utils/optional-skills.js.map +1 -1
  94. package/dist/utils/project-mode.d.ts +30 -0
  95. package/dist/utils/project-mode.d.ts.map +1 -0
  96. package/dist/utils/project-mode.js +86 -0
  97. package/dist/utils/project-mode.js.map +1 -0
  98. package/dist/utils/workflow-resolver.d.ts +9 -5
  99. package/dist/utils/workflow-resolver.d.ts.map +1 -1
  100. package/dist/utils/workflow-resolver.js +25 -11
  101. package/dist/utils/workflow-resolver.js.map +1 -1
  102. package/package.json +3 -3
@@ -0,0 +1,401 @@
1
+ /**
2
+ * `atw mode [dev|general]` — 查看或切换项目模式。
3
+ *
4
+ * 切换时的次序是这条命令的约定:
5
+ *
6
+ * - 确认之前只读不写:先把要做的事算出来、列给用户看。
7
+ * - 文件先删,哈希清单后动。清单里不属于当前模式的条目会被 `atw update` /
8
+ * `atw uninstall` 当成孤儿修剪掉;若文件还在,它就成了没人管的 ATW 文件。
9
+ * - 配置里的模式最后才改:它是"切换做完了"的标记。中途失败时配置仍是原模式,
10
+ * 重新运行同一条命令会按磁盘现状重新算一遍,把剩下的做完。
11
+ */
12
+ import fs from "node:fs";
13
+ import path from "node:path";
14
+ import chalk from "chalk";
15
+ import inquirer from "inquirer";
16
+ import { collectPlatformTemplates, getConfiguredPlatforms, } from "../configurators/index.js";
17
+ import { createConventionsFile, createSpecTemplates, } from "../configurators/workflow.js";
18
+ import { replacePythonCommandLiterals } from "../configurators/shared.js";
19
+ import { DIR_NAMES, FILE_NAMES, PATHS } from "../constants/paths.js";
20
+ import { conventionsContent } from "../templates/markdown/index.js";
21
+ import { writeFileAtomic } from "../utils/atomic-write.js";
22
+ import { detectMonorepo, detectProjectType, } from "../utils/project-detector.js";
23
+ import { isProjectMode, loadProjectMode, PROJECT_MODES, recordProjectMode, } from "../utils/project-mode.js";
24
+ import { computeHash, isTemplateModified, loadHashes, saveHashes, updateHashFromFile, } from "../utils/template-hash.js";
25
+ import { NATIVE_WORKFLOW_ID, resolveWorkflowTemplate, } from "../utils/workflow-resolver.js";
26
+ import { BOOTSTRAP_TASK_NAME } from "./init.js";
27
+ import { buildAgentsMdTemplate, getAtwManagedBlock } from "./update.js";
28
+ import { classifyExistingWorkflow, confirmOverwriteInteractively, writeWorkflow, } from "./workflow.js";
29
+ const CONFIG_FILE = `${DIR_NAMES.WORKFLOW}/config.yaml`;
30
+ function absolutePath(cwd, relPath) {
31
+ return path.join(cwd, ...relPath.split("/"));
32
+ }
33
+ /** `platforms` 在 `mode` 下装的全部文件,路径 → 内容。 */
34
+ function platformFiles(platforms, mode) {
35
+ const files = new Map();
36
+ for (const id of platforms) {
37
+ for (const [relPath, content] of collectPlatformTemplates(id, mode) ?? []) {
38
+ files.set(relPath, content);
39
+ }
40
+ }
41
+ return files;
42
+ }
43
+ function planFiles(cwd, from, to) {
44
+ const hashes = loadHashes(cwd);
45
+ const platforms = getConfiguredPlatforms(cwd);
46
+ const leaving = platformFiles(platforms, from);
47
+ const arriving = platformFiles(platforms, to);
48
+ const plan = {
49
+ remove: [],
50
+ add: new Map(),
51
+ replace: new Map(),
52
+ adopt: new Map(),
53
+ forget: [],
54
+ kept: [],
55
+ };
56
+ for (const relPath of leaving.keys()) {
57
+ if (arriving.has(relPath))
58
+ continue;
59
+ plan.forget.push(relPath);
60
+ if (!fs.existsSync(absolutePath(cwd, relPath)))
61
+ continue;
62
+ if (isTemplateModified(cwd, relPath, hashes)) {
63
+ plan.kept.push(relPath);
64
+ }
65
+ else {
66
+ plan.remove.push(relPath);
67
+ }
68
+ }
69
+ for (const [relPath, content] of arriving) {
70
+ if (leaving.get(relPath) === content)
71
+ continue;
72
+ const fullPath = absolutePath(cwd, relPath);
73
+ if (!fs.existsSync(fullPath)) {
74
+ // 两种模式都装的文件不在磁盘上,是用户自己删的,和 `atw update` 一样不装回来。
75
+ if (!leaving.has(relPath))
76
+ plan.add.set(relPath, content);
77
+ }
78
+ else if (fs.readFileSync(fullPath, "utf-8") === content) {
79
+ plan.adopt.set(relPath, content);
80
+ }
81
+ else if (isTemplateModified(cwd, relPath, hashes)) {
82
+ plan.kept.push(relPath);
83
+ }
84
+ else {
85
+ plan.replace.set(relPath, content);
86
+ }
87
+ }
88
+ planAgentsMd(cwd, from, to, hashes, plan);
89
+ return plan;
90
+ }
91
+ /**
92
+ * 根 `AGENTS.md` 不属于哪个平台,ATW 管的也只是其中的托管块:块随模式不同,
93
+ * 块外是用户自己写的,原样留着。
94
+ *
95
+ * 没有这个文件是用户删了;有而没有托管块,是初始化之前就在的用户自己的文件——
96
+ * 两种情况都没有可换的东西。有块时和别的文件一样,只在它仍是 ATW 写的那份时才
97
+ * 换:块本身还是原模式的原版,或整个文件与哈希清单一致。
98
+ */
99
+ function planAgentsMd(cwd, from, to, hashes, plan) {
100
+ const relPath = FILE_NAMES.AGENTS;
101
+ const fullPath = absolutePath(cwd, relPath);
102
+ if (!fs.existsSync(fullPath))
103
+ return;
104
+ const existing = fs.readFileSync(fullPath, "utf-8");
105
+ if (getAtwManagedBlock(existing) === null)
106
+ return;
107
+ const content = buildAgentsMdTemplate(cwd, to);
108
+ if (content === existing) {
109
+ plan.adopt.set(relPath, content);
110
+ }
111
+ else if (buildAgentsMdTemplate(cwd, from) === existing ||
112
+ !isTemplateModified(cwd, relPath, hashes)) {
113
+ plan.replace.set(relPath, content);
114
+ }
115
+ else {
116
+ plan.kept.push(relPath);
117
+ }
118
+ }
119
+ /** 清单里怎么称呼一个要换内容的文件:`AGENTS.md` 换的只是 ATW 管的那一块。 */
120
+ function replacedLabel(relPath) {
121
+ return relPath === FILE_NAMES.AGENTS
122
+ ? `${relPath} (the block ATW manages; the rest of the file stays)`
123
+ : relPath;
124
+ }
125
+ /** 还没归档的任务:`.atw/tasks/` 下除归档目录外的每个任务目录,带上它的状态。 */
126
+ function unarchivedTasks(cwd) {
127
+ const tasksDir = path.join(cwd, PATHS.TASKS);
128
+ const tasks = [];
129
+ for (const name of readDirOrEmpty(tasksDir)) {
130
+ if (name === DIR_NAMES.ARCHIVE)
131
+ continue;
132
+ let status;
133
+ try {
134
+ status = JSON.parse(fs.readFileSync(path.join(tasksDir, name, FILE_NAMES.TASK_JSON), "utf-8")).status;
135
+ }
136
+ catch {
137
+ continue; // 没有可读的 task.json,不是任务目录
138
+ }
139
+ tasks.push(typeof status === "string" ? `${name} (${status})` : name);
140
+ }
141
+ return tasks;
142
+ }
143
+ function planSpec(cwd, to) {
144
+ const conventionsPath = absolutePath(cwd, PATHS.CONVENTIONS_FILE);
145
+ const hasConventions = fs.existsSync(conventionsPath);
146
+ if (to === "general") {
147
+ return {
148
+ addConventions: !hasConventions,
149
+ removeConventions: false,
150
+ unusedConventions: false,
151
+ addGuidelines: false,
152
+ };
153
+ }
154
+ const untouched = hasConventions &&
155
+ fs.readFileSync(conventionsPath, "utf-8") === conventionsContent;
156
+ return {
157
+ addConventions: false,
158
+ removeConventions: untouched,
159
+ unusedConventions: hasConventions && !untouched,
160
+ addGuidelines: guidelineEntries(cwd).length === 0,
161
+ };
162
+ }
163
+ /** `.atw/spec/` 下约定文件之外的条目,也就是编码规范。 */
164
+ function guidelineEntries(cwd) {
165
+ return readDirOrEmpty(path.join(cwd, PATHS.SPEC)).filter((name) => name !== FILE_NAMES.CONVENTIONS);
166
+ }
167
+ /** 按 `atw init` 的口径建规范目录骨架:配置里记了子包的按子包建。 */
168
+ async function createGuidelineSkeleton(cwd) {
169
+ const detected = detectProjectType(cwd);
170
+ const isMonorepo = /^packages\s*:/m.test(fs.readFileSync(absolutePath(cwd, CONFIG_FILE), "utf-8"));
171
+ await createSpecTemplates(cwd, detected === "unknown" ? "fullstack" : detected, isMonorepo ? (detectMonorepo(cwd) ?? undefined) : undefined);
172
+ }
173
+ async function applySpecPlan(cwd, plan) {
174
+ if (plan.removeConventions) {
175
+ fs.unlinkSync(absolutePath(cwd, PATHS.CONVENTIONS_FILE));
176
+ }
177
+ if (plan.addConventions)
178
+ await createConventionsFile(cwd);
179
+ if (plan.addGuidelines)
180
+ await createGuidelineSkeleton(cwd);
181
+ }
182
+ /** 留在磁盘上、但目标模式用不到的东西:不删,只告诉用户。 */
183
+ function unusedIn(cwd, target, spec) {
184
+ const unused = [];
185
+ if (spec.unusedConventions) {
186
+ unused.push(`${PATHS.CONVENTIONS_FILE} (dev mode does not load it)`);
187
+ }
188
+ if (target === "general") {
189
+ if (guidelineEntries(cwd).length > 0) {
190
+ unused.push(`${PATHS.SPEC}/ (coding guidelines; general mode reads only ${FILE_NAMES.CONVENTIONS})`);
191
+ }
192
+ if (fs.existsSync(path.join(cwd, PATHS.TASKS, BOOTSTRAP_TASK_NAME))) {
193
+ unused.push(`${PATHS.TASKS}/${BOOTSTRAP_TASK_NAME} (the task for filling them in)`);
194
+ }
195
+ }
196
+ return unused;
197
+ }
198
+ function readDirOrEmpty(dir) {
199
+ try {
200
+ return fs.readdirSync(dir);
201
+ }
202
+ catch {
203
+ return [];
204
+ }
205
+ }
206
+ function printList(heading, marker, items) {
207
+ if (items.length === 0)
208
+ return;
209
+ console.log(`${heading} (${items.length}):`);
210
+ for (const item of [...items].sort()) {
211
+ console.log(` ${marker} ${item}`);
212
+ }
213
+ console.log();
214
+ }
215
+ /** 按做的先后列出切换的步骤。 */
216
+ function printSteps(heading, marker, labels) {
217
+ if (labels.length === 0)
218
+ return;
219
+ console.log(heading);
220
+ for (const label of labels) {
221
+ console.log(` ${marker} ${label}`);
222
+ }
223
+ console.log();
224
+ }
225
+ /**
226
+ * 文件删掉后,把因此空出来的目录一层层去掉,直到遇到还有东西的那一层。
227
+ * `rmdir` 只删空目录,所以目录里只要还有用户的文件就原样留着。
228
+ */
229
+ function removeEmptiedParents(cwd, relPath) {
230
+ let dir = path.posix.dirname(relPath);
231
+ while (dir !== ".") {
232
+ try {
233
+ fs.rmdirSync(absolutePath(cwd, dir));
234
+ }
235
+ catch {
236
+ return;
237
+ }
238
+ dir = path.posix.dirname(dir);
239
+ }
240
+ }
241
+ /** 删掉目标模式不装的文件,再把它们从哈希清单里去掉——次序见文件头。 */
242
+ function removeFiles(cwd, plan) {
243
+ for (const relPath of plan.remove) {
244
+ fs.unlinkSync(absolutePath(cwd, relPath));
245
+ removeEmptiedParents(cwd, relPath);
246
+ }
247
+ const hashes = loadHashes(cwd);
248
+ for (const relPath of plan.forget) {
249
+ Reflect.deleteProperty(hashes, relPath);
250
+ }
251
+ saveHashes(cwd, hashes);
252
+ }
253
+ /** 写入目标模式要装的文件,并记进哈希清单。 */
254
+ function writeFiles(cwd, plan) {
255
+ const written = [...plan.add, ...plan.replace];
256
+ for (const [relPath, content] of written) {
257
+ const fullPath = absolutePath(cwd, relPath);
258
+ fs.mkdirSync(path.dirname(fullPath), { recursive: true });
259
+ writeFileAtomic(fullPath, content);
260
+ }
261
+ const hashes = loadHashes(cwd);
262
+ for (const [relPath, content] of [...written, ...plan.adopt]) {
263
+ hashes[relPath] = computeHash(content);
264
+ }
265
+ saveHashes(cwd, hashes);
266
+ }
267
+ /**
268
+ * 把模式写进项目配置。配置在这之前若仍是 ATW 原版,写完后照样记成原版,
269
+ * `atw update` 才不会把这次改动当成用户的修改。
270
+ */
271
+ function recordMode(cwd, mode) {
272
+ const wasPristine = !isTemplateModified(cwd, CONFIG_FILE, loadHashes(cwd));
273
+ recordProjectMode(cwd, mode);
274
+ if (wasPristine)
275
+ updateHashFromFile(cwd, CONFIG_FILE);
276
+ }
277
+ export async function runModeCommand(options = {}) {
278
+ const cwd = process.cwd();
279
+ if (!fs.existsSync(path.join(cwd, DIR_NAMES.WORKFLOW))) {
280
+ throw new Error("No .atw/ directory found. Run `atw init` first.");
281
+ }
282
+ const current = loadProjectMode(cwd);
283
+ if (options.target === undefined) {
284
+ console.log(`Current mode: ${chalk.green(current)}`);
285
+ const others = PROJECT_MODES.filter((mode) => mode !== current);
286
+ console.log(chalk.gray(`Switch with ${others.map((mode) => `\`atw mode ${mode}\``).join(" or ")}.`));
287
+ return;
288
+ }
289
+ const target = options.target;
290
+ if (!isProjectMode(target)) {
291
+ throw new Error(`Unknown mode "${target}": expected ${PROJECT_MODES.map((mode) => `"${mode}"`).join(" or ")}.`);
292
+ }
293
+ if (target === current) {
294
+ console.log(chalk.gray(`This project is already in ${target} mode. Nothing to change.`));
295
+ return;
296
+ }
297
+ const plan = planFiles(cwd, current, target);
298
+ const workflow = await resolveWorkflowTemplate(NATIVE_WORKFLOW_ID, {
299
+ mode: target,
300
+ });
301
+ const workflowState = classifyExistingWorkflow(cwd, replacePythonCommandLiterals(workflow.content));
302
+ // 流程文件被改过、又没有 --force:换不换要问用户,问之前先不算进任何一类。
303
+ const workflowUndecided = workflowState.kind === "modified" && !options.force;
304
+ const workflowListedAs = (...kinds) => !workflowUndecided && kinds.includes(workflowState.kind)
305
+ ? [PATHS.WORKFLOW_GUIDE_FILE]
306
+ : [];
307
+ const spec = planSpec(cwd, target);
308
+ console.log(chalk.bold(`\nSwitching this project from ${current} to ${target} mode\n`));
309
+ const deleted = [
310
+ ...plan.remove,
311
+ ...(spec.removeConventions ? [PATHS.CONVENTIONS_FILE] : []),
312
+ ];
313
+ const added = [
314
+ ...plan.add.keys(),
315
+ ...(spec.addConventions ? [PATHS.CONVENTIONS_FILE] : []),
316
+ ...(spec.addGuidelines
317
+ ? [`${PATHS.SPEC}/ (coding guideline templates to fill in)`]
318
+ : []),
319
+ ...workflowListedAs("missing"),
320
+ ];
321
+ const replaced = [
322
+ ...[...plan.replace.keys()].map(replacedLabel),
323
+ ...workflowListedAs("pristine", "modified"),
324
+ ];
325
+ const kept = [...plan.kept];
326
+ printList("Will be deleted", chalk.red("-"), deleted);
327
+ printList("Will be added", chalk.green("+"), added);
328
+ printList("Will be replaced", chalk.cyan("~"), replaced);
329
+ printList("Kept, because you changed them", chalk.yellow("!"), kept);
330
+ if (workflowUndecided && process.stdin.isTTY) {
331
+ console.log(`${PATHS.WORKFLOW_GUIDE_FILE} has local edits; you will be asked what to do with it.\n`);
332
+ }
333
+ printList("Unarchived tasks", "•", unarchivedTasks(cwd));
334
+ printList(`Still on disk, but not used in ${target} mode`, "•", unusedIn(cwd, target, spec));
335
+ if (!options.yes) {
336
+ if (!process.stdin.isTTY) {
337
+ throw new Error("Switching modes deletes and adds files, and a non-interactive shell cannot be asked to confirm. Pass --yes/-y to switch.");
338
+ }
339
+ const { proceed } = await inquirer.prompt([
340
+ {
341
+ type: "confirm",
342
+ name: "proceed",
343
+ message: `Switch this project to ${target} mode?`,
344
+ default: true,
345
+ },
346
+ ]);
347
+ if (!proceed) {
348
+ console.log(chalk.yellow("Mode switch cancelled. No files were changed."));
349
+ return;
350
+ }
351
+ }
352
+ // 和 `atw workflow` 一样处理被改过的流程文件,但在动任何文件之前问完。
353
+ let workflowAction = "overwrite";
354
+ if (workflowUndecided) {
355
+ if (!process.stdin.isTTY) {
356
+ throw new Error(`${PATHS.WORKFLOW_GUIDE_FILE} has local edits. Re-run with --force to replace it with the ${target} workflow.`);
357
+ }
358
+ workflowAction = await confirmOverwriteInteractively();
359
+ (workflowAction === "overwrite" ? replaced : kept).push(PATHS.WORKFLOW_GUIDE_FILE);
360
+ }
361
+ // 次序见文件头:先删、后写,模式最后才记。
362
+ const steps = [
363
+ [
364
+ `delete the files ${target} mode does not install`,
365
+ () => removeFiles(cwd, plan),
366
+ ],
367
+ [`write the files ${target} mode installs`, () => writeFiles(cwd, plan)],
368
+ [
369
+ `bring ${PATHS.SPEC}/ in line with ${target} mode`,
370
+ () => applySpecPlan(cwd, spec),
371
+ ],
372
+ [
373
+ `switch ${PATHS.WORKFLOW_GUIDE_FILE} to the ${target} workflow`,
374
+ async () => {
375
+ if (workflowAction === "skip")
376
+ return;
377
+ await writeWorkflow(cwd, workflow, {
378
+ force: workflowAction === "overwrite",
379
+ createNew: workflowAction === "create-new",
380
+ });
381
+ },
382
+ ],
383
+ [`record the mode in ${CONFIG_FILE}`, () => recordMode(cwd, target)],
384
+ ];
385
+ for (const [index, [, run]] of steps.entries()) {
386
+ try {
387
+ await run();
388
+ }
389
+ catch (error) {
390
+ const labels = steps.map(([label]) => label);
391
+ printSteps("Done:", chalk.green("✓"), labels.slice(0, index));
392
+ printSteps("Not done:", chalk.red("✗"), labels.slice(index));
393
+ throw new Error(`The switch to ${target} mode did not finish: ${error instanceof Error ? error.message : String(error)}\nThe project is still in ${current} mode. Run \`atw mode ${target}\` again to finish the switch.`);
394
+ }
395
+ }
396
+ console.log(chalk.green(`Switched this project from ${current} to ${target} mode: ` +
397
+ `${deleted.length} deleted, ${added.length} added, ${replaced.length} replaced.`));
398
+ console.log();
399
+ printList("Kept as you left them", chalk.yellow("!"), kept);
400
+ }
401
+ //# sourceMappingURL=mode.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mode.js","sourceRoot":"","sources":["../../src/commands/mode.ts"],"names":[],"mappings":"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"}
@@ -1,4 +1,5 @@
1
1
  import type { ConfigSectionAdded, MigrationItem, ClassifiedMigrations, MigrationResult, TemplateHashes } from "../types/migration.js";
2
+ import { type ProjectMode } from "../utils/project-mode.js";
2
3
  export { cleanupEmptyDirs, ATW_BLOCK_END, ATW_BLOCK_START, } from "../utils/managed-paths.js";
3
4
  export interface UpdateOptions {
4
5
  dryRun?: boolean;
@@ -8,6 +9,12 @@ export interface UpdateOptions {
8
9
  allowDowngrade?: boolean;
9
10
  migrate?: boolean;
10
11
  }
12
+ export declare function getAtwManagedBlock(content: string): string | null;
13
+ /**
14
+ * 根 `AGENTS.md` 在 `mode` 下应有的内容:磁盘上的文件换上该模式的 ATW 托管块,
15
+ * 块外的内容原样保留。升级和模式切换都从这里取。
16
+ */
17
+ export declare function buildAgentsMdTemplate(cwd: string, mode: ProjectMode): string;
11
18
  /**
12
19
  * Load update.skip paths from .atw/config.yaml
13
20
  *
@@ -1 +1 @@
1
- {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../src/commands/update.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EACV,kBAAkB,EAClB,aAAa,EACb,oBAAoB,EACpB,eAAe,EAEf,cAAc,EACf,MAAM,uBAAuB,CAAC;AAwE/B,OAAO,EACL,gBAAgB,EAChB,aAAa,EACb,eAAe,GAChB,MAAM,2BAA2B,CAAC;AAEnC,MAAM,WAAW,aAAa;IAC5B,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AA0YD;;;;;;;;;;GAUG;AACH,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CA6DzD;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,oBAAoB,CAClC,QAAQ,EAAE,MAAM,EAChB,cAAc,EAAE,MAAM,GACrB,MAAM,GAAG,IAAI,CA2Bf;AAED;;;;;;;;;GASG;AACH,wBAAgB,wBAAwB,CACtC,OAAO,EAAE,kBAAkB,EAAE,EAC7B,GAAG,EAAE,MAAM,EACX,gBAAgB,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GACpC;IAAE,QAAQ,EAAE,MAAM,CAAA;CAAE,CA0CtB;AA6FD;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,wBAAgB,uBAAuB,CACrC,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,MAAM,GACf;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,EAAE,CAAA;CAAE,CAyDvC;AAojBD;;;GAGG;AACH,wBAAgB,uBAAuB,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAerE;AAyOD;;GAEG;AACH;;;;;;GAMG;AACH,wBAAgB,qBAAqB,CACnC,eAAe,EAAE,MAAM,EACvB,MAAM,EAAE,cAAc,GACrB,OAAO,CAOT;AAED,wBAAgB,kBAAkB,CAChC,UAAU,EAAE,aAAa,EAAE,EAC3B,GAAG,EAAE,MAAM,EACX,MAAM,EAAE,cAAc,EACtB,SAAS,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GAC7B,oBAAoB,CA+FtB;AA8JD;;;;GAIG;AACH,0CAA0C;AAC1C,wBAAgB,0BAA0B,CACxC,UAAU,EAAE,aAAa,EAAE,GAC1B,aAAa,EAAE,CAajB;AAED;;;;;;GAMG;AACH,wBAAsB,iBAAiB,CACrC,UAAU,EAAE,oBAAoB,EAChC,GAAG,EAAE,MAAM,EACX,OAAO,EAAE;IAAE,KAAK,CAAC,EAAE,OAAO,CAAC;IAAC,OAAO,CAAC,EAAE,OAAO,CAAA;CAAE,EAC/C,SAAS,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GAC7B,OAAO,CAAC,eAAe,CAAC,CAqL1B;AA4BD;;;;;;;;;GASG;AACH,wBAAgB,qBAAqB,CAAC,YAAY,EAAE,MAAM,GAAG;IAC3D,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB,CAsBA;AA+FD,wBAAsB,MAAM,CAAC,OAAO,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC,CAg0BlE"}
1
+ {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../src/commands/update.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EACV,kBAAkB,EAClB,aAAa,EACb,oBAAoB,EACpB,eAAe,EAEf,cAAc,EACf,MAAM,uBAAuB,CAAC;AAkD/B,OAAO,EAAmB,KAAK,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAuB7E,OAAO,EACL,gBAAgB,EAChB,aAAa,EACb,eAAe,GAChB,MAAM,2BAA2B,CAAC;AAEnC,MAAM,WAAW,aAAa;IAC5B,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAyDD,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAEjE;AAoFD;;;GAGG;AACH,wBAAgB,qBAAqB,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,WAAW,GAAG,MAAM,CAQ5E;AAmPD;;;;;;;;;;GAUG;AACH,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,EAAE,CA6DzD;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,oBAAoB,CAClC,QAAQ,EAAE,MAAM,EAChB,cAAc,EAAE,MAAM,GACrB,MAAM,GAAG,IAAI,CA2Bf;AAED;;;;;;;;;GASG;AACH,wBAAgB,wBAAwB,CACtC,OAAO,EAAE,kBAAkB,EAAE,EAC7B,GAAG,EAAE,MAAM,EACX,gBAAgB,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GACpC;IAAE,QAAQ,EAAE,MAAM,CAAA;CAAE,CA0CtB;AA6FD;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,wBAAgB,uBAAuB,CACrC,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,MAAM,GACf;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,EAAE,CAAA;CAAE,CAyDvC;AAqjBD;;;GAGG;AACH,wBAAgB,uBAAuB,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAerE;AAyOD;;GAEG;AACH;;;;;;GAMG;AACH,wBAAgB,qBAAqB,CACnC,eAAe,EAAE,MAAM,EACvB,MAAM,EAAE,cAAc,GACrB,OAAO,CAOT;AAED,wBAAgB,kBAAkB,CAChC,UAAU,EAAE,aAAa,EAAE,EAC3B,GAAG,EAAE,MAAM,EACX,MAAM,EAAE,cAAc,EACtB,SAAS,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GAC7B,oBAAoB,CA+FtB;AA8JD;;;;GAIG;AACH,0CAA0C;AAC1C,wBAAgB,0BAA0B,CACxC,UAAU,EAAE,aAAa,EAAE,GAC1B,aAAa,EAAE,CAajB;AAED;;;;;;GAMG;AACH,wBAAsB,iBAAiB,CACrC,UAAU,EAAE,oBAAoB,EAChC,GAAG,EAAE,MAAM,EACX,OAAO,EAAE;IAAE,KAAK,CAAC,EAAE,OAAO,CAAC;IAAC,OAAO,CAAC,EAAE,OAAO,CAAA;CAAE,EAC/C,SAAS,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GAC7B,OAAO,CAAC,eAAe,CAAC,CAqL1B;AA4BD;;;;;;;;;GASG;AACH,wBAAgB,qBAAqB,CAAC,YAAY,EAAE,MAAM,GAAG;IAC3D,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,EAAE,CAAC;CACnB,CAsBA;AA+FD,wBAAsB,MAAM,CAAC,OAAO,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC,CAo0BlE"}
@@ -20,14 +20,15 @@ const BATCH_FLAG_HINT = "Pass --force to overwrite, --skip-all to keep your vers
20
20
  // Import templates for comparison
21
21
  import { getAllScripts, getAllAgents,
22
22
  // Configuration
23
- configYamlTemplate, gitignoreTemplate, workflowMdTemplate, } from "../templates/atw/index.js";
24
- import { agentsMdContent } from "../templates/markdown/index.js";
23
+ configYamlTemplate, gitignoreTemplate, bundledWorkflowFor, } from "../templates/atw/index.js";
24
+ import { agentsMdFor } from "../templates/markdown/index.js";
25
25
  import { COPILOT_INSTRUCTIONS_BLOCK_END, COPILOT_INSTRUCTIONS_BLOCK_START, COPILOT_INSTRUCTIONS_PATH, getCopilotInstructions, } from "../templates/copilot/index.js";
26
26
  import { ALL_MANAGED_DIRS, getConfiguredPlatforms, collectPlatformTemplates, } from "../configurators/index.js";
27
27
  import { replacePythonCommandLiterals } from "../configurators/shared.js";
28
28
  import { preserveCodexAgentModelKeys } from "../configurators/codex.js";
29
29
  import { ensureGitattributes } from "../configurators/workflow.js";
30
30
  import { pruneOrphanManifestKeys } from "../utils/manifest-prune.js";
31
+ import { loadProjectMode } from "../utils/project-mode.js";
31
32
  import { fetchRegistrySpecTemplates, collectDirectoryFiles, removeDirectory, parseRegistrySource, probeRegistryIndex, downloadTemplateById, } from "../utils/template-fetcher.js";
32
33
  import { loadSpecRegistryConfig } from "../utils/registry-config.js";
33
34
  import { fetchOptionalSkills, getInstalledOptionalSkillDirs, installOptionalSkills, loadOptionalSkillRecord, } from "../utils/optional-skills.js";
@@ -61,7 +62,7 @@ function getManagedBlock(content, startMarker, endMarker) {
61
62
  }
62
63
  return content.slice(start, end + endMarker.length);
63
64
  }
64
- function getAtwManagedBlock(content) {
65
+ export function getAtwManagedBlock(content) {
65
66
  return getManagedBlock(content, ATW_BLOCK_START, ATW_BLOCK_END);
66
67
  }
67
68
  function replaceManagedBlock(existingContent, templateContent, startMarker, endMarker) {
@@ -101,8 +102,12 @@ function buildManagedBlockTemplate(cwd, relativePath, templateContent, startMark
101
102
  const existingContent = fs.readFileSync(fullPath, "utf-8");
102
103
  return mergeManagedBlockContent(existingContent, templateContent, startMarker, endMarker);
103
104
  }
104
- function buildAgentsMdTemplate(cwd) {
105
- return buildManagedBlockTemplate(cwd, FILE_NAMES.AGENTS, agentsMdContent, ATW_BLOCK_START, ATW_BLOCK_END);
105
+ /**
106
+ * 根 `AGENTS.md` 在 `mode` 下应有的内容:磁盘上的文件换上该模式的 ATW 托管块,
107
+ * 块外的内容原样保留。升级和模式切换都从这里取。
108
+ */
109
+ export function buildAgentsMdTemplate(cwd, mode) {
110
+ return buildManagedBlockTemplate(cwd, FILE_NAMES.AGENTS, agentsMdFor(mode), ATW_BLOCK_START, ATW_BLOCK_END);
106
111
  }
107
112
  function buildCopilotInstructionsTemplate(cwd) {
108
113
  return buildManagedBlockTemplate(cwd, COPILOT_INSTRUCTIONS_PATH, getCopilotInstructions(), COPILOT_INSTRUCTIONS_BLOCK_START, COPILOT_INSTRUCTIONS_BLOCK_END);
@@ -433,7 +438,7 @@ export function applyConfigSectionsAdded(entries, cwd, bundledTemplates) {
433
438
  * Returns true if upgrade is needed. Does NOT perform the upgrade —
434
439
  * caller should run configurePlatform("codex") after backup/confirm.
435
440
  */
436
- function needsCodexUpgrade(cwd) {
441
+ function needsCodexUpgrade(cwd, mode) {
437
442
  if (fs.existsSync(path.join(cwd, ".codex"))) {
438
443
  return false;
439
444
  }
@@ -455,7 +460,7 @@ function needsCodexUpgrade(cwd) {
455
460
  if (platformId === "codex") {
456
461
  continue;
457
462
  }
458
- const platformFiles = collectPlatformTemplates(platformId);
463
+ const platformFiles = collectPlatformTemplates(platformId, mode);
459
464
  if (platformFiles && legacyMarkers.some((key) => platformFiles.has(key))) {
460
465
  return false;
461
466
  }
@@ -646,7 +651,7 @@ async function collectRegistrySpecTemplates(cwd) {
646
651
  }
647
652
  return result.files;
648
653
  }
649
- async function collectTemplateFiles(cwd, extraPlatforms,
654
+ async function collectTemplateFiles(cwd, mode, extraPlatforms,
650
655
  /**
651
656
  * Bypass `update.skip` when collecting templates. Enable this for breaking
652
657
  * releases so newly added files (e.g. a new `continue.md`) and template
@@ -686,13 +691,13 @@ bypassUpdateSkip = false) {
686
691
  // --force behavior applies. Partial tag-block merging is unsafe because
687
692
  // platform routing markers outside [workflow-state:*] blocks are also
688
693
  // script-consumed.
689
- files.set(`${DIR_NAMES.WORKFLOW}/workflow.md`, workflowMdTemplate);
694
+ files.set(`${DIR_NAMES.WORKFLOW}/workflow.md`, bundledWorkflowFor(mode));
690
695
  // workspace/index.md stays excluded — it's runtime-appended by add_session.py
691
696
  // (journal index) and has no script-parsed structure.
692
- files.set(FILE_NAMES.AGENTS, buildAgentsMdTemplate(cwd));
697
+ files.set(FILE_NAMES.AGENTS, buildAgentsMdTemplate(cwd, mode));
693
698
  // Platform-specific templates (only for configured platforms)
694
699
  for (const platformId of platforms) {
695
- const platformFiles = collectPlatformTemplates(platformId);
700
+ const platformFiles = collectPlatformTemplates(platformId, mode);
696
701
  if (platformFiles) {
697
702
  for (const [filePath, content] of platformFiles) {
698
703
  files.set(filePath, content);
@@ -1772,6 +1777,8 @@ export async function update(options) {
1772
1777
  console.log(chalk.gray("Run 'atw init' first."));
1773
1778
  return;
1774
1779
  }
1780
+ // 升级只维护项目当前模式下的安装内容;非法的模式值在动任何文件之前就报错。
1781
+ const mode = loadProjectMode(cwd);
1775
1782
  console.log(chalk.cyan("\nATW Update"));
1776
1783
  console.log(chalk.cyan("══════════════\n"));
1777
1784
  // Set up proxy before any network calls (npm version check)
@@ -1828,7 +1835,7 @@ export async function update(options) {
1828
1835
  // detector reads the raw manifest looking for .agents/skills/ markers that
1829
1836
  // the prune step would otherwise consider orphans (codex hasn't been added
1830
1837
  // to configuredPlatforms yet at this point).
1831
- const codexUpgradeNeeded = needsCodexUpgrade(cwd);
1838
+ const codexUpgradeNeeded = needsCodexUpgrade(cwd, mode);
1832
1839
  if (codexUpgradeNeeded) {
1833
1840
  console.log(chalk.yellow(" Legacy Codex detected: .agents/skills/ tracked without .codex/ — will create .codex/ directory"));
1834
1841
  }
@@ -1863,7 +1870,7 @@ export async function update(options) {
1863
1870
  return md.breaking && md.recommendMigrate;
1864
1871
  })();
1865
1872
  // Collect templates (used for both migration classification and change analysis)
1866
- const templates = await collectTemplateFiles(cwd, codexUpgradeNeeded ? new Set(["codex"]) : undefined, breakingBypass);
1873
+ const templates = await collectTemplateFiles(cwd, mode, codexUpgradeNeeded ? new Set(["codex"]) : undefined, breakingBypass);
1867
1874
  // Load update.skip paths (used for both safe-file-delete and template collection)
1868
1875
  const skipPaths = loadUpdateSkipPaths(cwd);
1869
1876
  // Collect safe-file-delete items from ALL manifests (hash match is the safety net)