mancode 0.3.10 → 0.3.12
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.en.md +138 -165
- package/README.md +121 -141
- package/dist/chunk-CFC3HBNA.js +1290 -0
- package/dist/chunk-CFC3HBNA.js.map +1 -0
- package/dist/cli.js +224 -84
- package/dist/cli.js.map +1 -1
- package/dist/{v3-adapter-3GJT3AID.js → v3-adapter-DDZB3Y6S.js} +18 -4
- package/package.json +1 -1
- package/dist/chunk-KEIW7AEP.js +0 -597
- package/dist/chunk-KEIW7AEP.js.map +0 -1
- /package/dist/{v3-adapter-3GJT3AID.js.map → v3-adapter-DDZB3Y6S.js.map} +0 -0
|
@@ -1,27 +1,41 @@
|
|
|
1
1
|
import {
|
|
2
|
+
V3_ADAPTER_FILE_TARGETS,
|
|
2
3
|
V3_ADAPTER_MANAGED_MARKER,
|
|
3
4
|
V3_ADAPTER_VERSION,
|
|
5
|
+
V3_MODE_ENTRY_MANAGED_MARKER,
|
|
6
|
+
V3_MODE_NAMES,
|
|
4
7
|
applyV3AdapterFilePlan,
|
|
8
|
+
assertV3AdapterInstallable,
|
|
9
|
+
assertV3AdapterTargetSafe,
|
|
5
10
|
inspectV3Adapter,
|
|
6
11
|
inspectV3AdapterVersions,
|
|
7
12
|
installV3Adapter,
|
|
8
13
|
planV3AdapterFiles,
|
|
9
14
|
removeV3Adapter,
|
|
10
15
|
renderV3Bootstrap,
|
|
16
|
+
renderV3ModeEntry,
|
|
11
17
|
stageV3Adapter,
|
|
12
|
-
v3AdapterTargetPath
|
|
13
|
-
|
|
18
|
+
v3AdapterTargetPath,
|
|
19
|
+
v3ModeEntryPath
|
|
20
|
+
} from "./chunk-CFC3HBNA.js";
|
|
14
21
|
export {
|
|
22
|
+
V3_ADAPTER_FILE_TARGETS,
|
|
15
23
|
V3_ADAPTER_MANAGED_MARKER,
|
|
16
24
|
V3_ADAPTER_VERSION,
|
|
25
|
+
V3_MODE_ENTRY_MANAGED_MARKER,
|
|
26
|
+
V3_MODE_NAMES,
|
|
17
27
|
applyV3AdapterFilePlan,
|
|
28
|
+
assertV3AdapterInstallable,
|
|
29
|
+
assertV3AdapterTargetSafe,
|
|
18
30
|
inspectV3Adapter,
|
|
19
31
|
inspectV3AdapterVersions,
|
|
20
32
|
installV3Adapter,
|
|
21
33
|
planV3AdapterFiles,
|
|
22
34
|
removeV3Adapter,
|
|
23
35
|
renderV3Bootstrap,
|
|
36
|
+
renderV3ModeEntry,
|
|
24
37
|
stageV3Adapter,
|
|
25
|
-
v3AdapterTargetPath
|
|
38
|
+
v3AdapterTargetPath,
|
|
39
|
+
v3ModeEntryPath
|
|
26
40
|
};
|
|
27
|
-
//# sourceMappingURL=v3-adapter-
|
|
41
|
+
//# sourceMappingURL=v3-adapter-DDZB3Y6S.js.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "mancode",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.12",
|
|
4
4
|
"description": "AI coding agent workflow harness. Five modes from practice to playoffs: stop over-engineering, reuse project context, and add multi-agent code review.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "AGPL-3.0-only",
|
package/dist/chunk-KEIW7AEP.js
DELETED
|
@@ -1,597 +0,0 @@
|
|
|
1
|
-
// src/installers/v3-adapter.ts
|
|
2
|
-
import {
|
|
3
|
-
lstat,
|
|
4
|
-
mkdir,
|
|
5
|
-
readFile,
|
|
6
|
-
rename,
|
|
7
|
-
rm,
|
|
8
|
-
writeFile
|
|
9
|
-
} from "fs/promises";
|
|
10
|
-
import path from "path";
|
|
11
|
-
|
|
12
|
-
// src/installers/managed-block.ts
|
|
13
|
-
var DEFAULT_MANCODE_START_MARKER = "<!-- mancode:start -->";
|
|
14
|
-
var DEFAULT_MANCODE_END_MARKER = "<!-- mancode:end -->";
|
|
15
|
-
function removeManagedBlock(existing, startMarker = DEFAULT_MANCODE_START_MARKER, endMarker = DEFAULT_MANCODE_END_MARKER) {
|
|
16
|
-
const start = findMarkerLine(existing, startMarker);
|
|
17
|
-
const end = findMarkerLine(existing, endMarker);
|
|
18
|
-
if (start === null && end === null) return existing;
|
|
19
|
-
if (start === null || end === null) return existing;
|
|
20
|
-
if (end.start < start.start) return existing;
|
|
21
|
-
const before = existing.slice(0, start.start);
|
|
22
|
-
const after = existing.slice(end.end);
|
|
23
|
-
const merged = `${before}${after}`;
|
|
24
|
-
return cleanUpOrphanedNewlines(merged);
|
|
25
|
-
}
|
|
26
|
-
function hasManagedBlock(existing, startMarker = DEFAULT_MANCODE_START_MARKER, endMarker = DEFAULT_MANCODE_END_MARKER) {
|
|
27
|
-
const start = findMarkerLine(existing, startMarker);
|
|
28
|
-
const end = findMarkerLine(existing, endMarker);
|
|
29
|
-
return start !== null && end !== null && end.start > start.start;
|
|
30
|
-
}
|
|
31
|
-
function cleanUpOrphanedNewlines(content) {
|
|
32
|
-
const trimmed = content.replace(/\n{3,}/gu, "\n\n").replace(/\n+$/u, "\n");
|
|
33
|
-
return trimmed || "";
|
|
34
|
-
}
|
|
35
|
-
function replaceManagedBlock(existing, block, startMarker = DEFAULT_MANCODE_START_MARKER, endMarker = DEFAULT_MANCODE_END_MARKER) {
|
|
36
|
-
const normalizedBlock = normalizeManagedBlock(block, startMarker, endMarker);
|
|
37
|
-
const start = findMarkerLine(existing, startMarker);
|
|
38
|
-
const end = findMarkerLine(existing, endMarker);
|
|
39
|
-
if (start === null !== (end === null)) {
|
|
40
|
-
throw new Error("managed block is malformed: missing start or end marker");
|
|
41
|
-
}
|
|
42
|
-
if (start === null && end === null) {
|
|
43
|
-
const trimmedExisting = trimTrailingNewlines(existing);
|
|
44
|
-
if (!trimmedExisting) return `${normalizedBlock}
|
|
45
|
-
`;
|
|
46
|
-
return `${trimmedExisting}
|
|
47
|
-
|
|
48
|
-
${normalizedBlock}
|
|
49
|
-
`;
|
|
50
|
-
}
|
|
51
|
-
if (!start || !end) {
|
|
52
|
-
throw new Error("managed block is malformed: missing start or end marker");
|
|
53
|
-
}
|
|
54
|
-
if (end.start < start.start) {
|
|
55
|
-
throw new Error("managed block is malformed: end marker precedes start");
|
|
56
|
-
}
|
|
57
|
-
return `${existing.slice(0, start.start)}${normalizedBlock}${existing.slice(
|
|
58
|
-
end.end
|
|
59
|
-
)}`;
|
|
60
|
-
}
|
|
61
|
-
function normalizeManagedBlock(block, startMarker, endMarker) {
|
|
62
|
-
const trimmedBlock = block.trim();
|
|
63
|
-
const hasStart = trimmedBlock.startsWith(startMarker);
|
|
64
|
-
const hasEnd = trimmedBlock.endsWith(endMarker);
|
|
65
|
-
if (hasStart && hasEnd) return trimmedBlock;
|
|
66
|
-
if (hasStart || hasEnd) {
|
|
67
|
-
throw new Error("managed block content includes only one marker");
|
|
68
|
-
}
|
|
69
|
-
return `${startMarker}
|
|
70
|
-
${trimmedBlock}
|
|
71
|
-
${endMarker}`;
|
|
72
|
-
}
|
|
73
|
-
function trimTrailingNewlines(value) {
|
|
74
|
-
return value.replace(/\n+$/u, "");
|
|
75
|
-
}
|
|
76
|
-
function findMarkerLine(content, marker) {
|
|
77
|
-
let offset = 0;
|
|
78
|
-
let inFence = null;
|
|
79
|
-
for (const lineWithBreak of content.matchAll(/[^\n]*(?:\n|$)/gu)) {
|
|
80
|
-
const rawLine = lineWithBreak[0];
|
|
81
|
-
if (!rawLine) break;
|
|
82
|
-
const line = rawLine.replace(/\n$/u, "").replace(/\r$/u, "");
|
|
83
|
-
const fence = line.match(/^(`{3,}|~{3,})/u)?.[1];
|
|
84
|
-
if (fence) {
|
|
85
|
-
const char = fence[0];
|
|
86
|
-
if (!inFence) {
|
|
87
|
-
inFence = { char, length: fence.length };
|
|
88
|
-
} else if (inFence.char === char && fence.length >= inFence.length) {
|
|
89
|
-
inFence = null;
|
|
90
|
-
}
|
|
91
|
-
} else if (!inFence && line === marker) {
|
|
92
|
-
return {
|
|
93
|
-
start: offset,
|
|
94
|
-
end: offset + marker.length
|
|
95
|
-
};
|
|
96
|
-
}
|
|
97
|
-
offset += rawLine.length;
|
|
98
|
-
}
|
|
99
|
-
return null;
|
|
100
|
-
}
|
|
101
|
-
|
|
102
|
-
// src/installers/v3-adapter.ts
|
|
103
|
-
var V3_ADAPTER_VERSION = "3";
|
|
104
|
-
var V3_ADAPTER_MANAGED_MARKER = "<!-- Managed by mancode:v3-adapter. Do not edit this marker. -->";
|
|
105
|
-
var V3_CODEX_START_MARKER = "<!-- mancode:v3:codex:start -->";
|
|
106
|
-
var V3_CODEX_END_MARKER = "<!-- mancode:v3:codex:end -->";
|
|
107
|
-
var V3_ZCODE_START_MARKER = "<!-- mancode:v3:zcode:start -->";
|
|
108
|
-
var V3_ZCODE_END_MARKER = "<!-- mancode:v3:zcode:end -->";
|
|
109
|
-
var V3_COPILOT_START_MARKER = "<!-- mancode:v3:copilot:start -->";
|
|
110
|
-
var V3_COPILOT_END_MARKER = "<!-- mancode:v3:copilot:end -->";
|
|
111
|
-
var RETRIABLE_ADAPTER_READ_CODES = /* @__PURE__ */ new Set(["EACCES", "EBUSY", "EPERM"]);
|
|
112
|
-
var ADAPTER_READ_MAX_ATTEMPTS = 4;
|
|
113
|
-
var ADAPTER_READ_RETRY_DELAY_MS = 25;
|
|
114
|
-
var V3_ADAPTER_FILE_TARGETS = [
|
|
115
|
-
"claude-skill",
|
|
116
|
-
"cursor-rule",
|
|
117
|
-
"agents",
|
|
118
|
-
"copilot-instructions"
|
|
119
|
-
];
|
|
120
|
-
async function planV3AdapterFiles(projectRoot) {
|
|
121
|
-
const root = path.resolve(projectRoot);
|
|
122
|
-
const existing = /* @__PURE__ */ new Map();
|
|
123
|
-
for (const target of V3_ADAPTER_FILE_TARGETS) {
|
|
124
|
-
existing.set(target, await readAdapterTarget(root, target));
|
|
125
|
-
}
|
|
126
|
-
const agents = existing.get("agents") ?? "";
|
|
127
|
-
const nextAgents = replaceManagedV3BlockText(
|
|
128
|
-
replaceManagedV3BlockText(
|
|
129
|
-
agents,
|
|
130
|
-
V3_CODEX_START_MARKER,
|
|
131
|
-
V3_CODEX_END_MARKER,
|
|
132
|
-
renderV3Bootstrap("codex")
|
|
133
|
-
),
|
|
134
|
-
V3_ZCODE_START_MARKER,
|
|
135
|
-
V3_ZCODE_END_MARKER,
|
|
136
|
-
renderV3Bootstrap("zcode")
|
|
137
|
-
);
|
|
138
|
-
const plans = [
|
|
139
|
-
managedFilePlan(
|
|
140
|
-
"claude-skill",
|
|
141
|
-
existing.get("claude-skill") ?? null,
|
|
142
|
-
renderClaudeSkill(renderV3Bootstrap("claude-code"))
|
|
143
|
-
),
|
|
144
|
-
managedFilePlan(
|
|
145
|
-
"cursor-rule",
|
|
146
|
-
existing.get("cursor-rule") ?? null,
|
|
147
|
-
renderCursorRule(renderV3Bootstrap("cursor"))
|
|
148
|
-
),
|
|
149
|
-
{
|
|
150
|
-
target: "agents",
|
|
151
|
-
beforeContent: existing.get("agents") ?? null,
|
|
152
|
-
targetContent: nextAgents
|
|
153
|
-
},
|
|
154
|
-
{
|
|
155
|
-
target: "copilot-instructions",
|
|
156
|
-
beforeContent: existing.get("copilot-instructions") ?? null,
|
|
157
|
-
targetContent: replaceManagedV3BlockText(
|
|
158
|
-
existing.get("copilot-instructions") ?? "",
|
|
159
|
-
V3_COPILOT_START_MARKER,
|
|
160
|
-
V3_COPILOT_END_MARKER,
|
|
161
|
-
renderV3Bootstrap("copilot")
|
|
162
|
-
)
|
|
163
|
-
}
|
|
164
|
-
];
|
|
165
|
-
return plans;
|
|
166
|
-
}
|
|
167
|
-
async function applyV3AdapterFilePlan(projectRoot, plan) {
|
|
168
|
-
const root = path.resolve(projectRoot);
|
|
169
|
-
if (!V3_ADAPTER_FILE_TARGETS.includes(plan.target)) {
|
|
170
|
-
throw new Error("MANCODE_V3_ADAPTER_TARGET_INVALID");
|
|
171
|
-
}
|
|
172
|
-
if (typeof plan.targetContent !== "string" || !plan.targetContent.trim()) {
|
|
173
|
-
throw new Error("MANCODE_V3_ADAPTER_TARGET_INVALID");
|
|
174
|
-
}
|
|
175
|
-
const target = v3AdapterTargetPath(root, plan.target);
|
|
176
|
-
await mkdir(path.dirname(target), { recursive: true });
|
|
177
|
-
await atomicWrite(target, plan.targetContent);
|
|
178
|
-
}
|
|
179
|
-
async function stageV3Adapter(projectRoot, platform) {
|
|
180
|
-
const root = path.resolve(projectRoot);
|
|
181
|
-
const target = targetFor(platform);
|
|
182
|
-
const content = await renderV3AdapterCandidate(root, platform);
|
|
183
|
-
const stagingTarget = path.join(
|
|
184
|
-
".mancode",
|
|
185
|
-
"staging",
|
|
186
|
-
"adapters",
|
|
187
|
-
"v3",
|
|
188
|
-
platform,
|
|
189
|
-
target
|
|
190
|
-
);
|
|
191
|
-
const destination = path.join(root, stagingTarget);
|
|
192
|
-
await mkdir(path.dirname(destination), { recursive: true });
|
|
193
|
-
await atomicWrite(destination, content);
|
|
194
|
-
return { platform, target, stagingTarget };
|
|
195
|
-
}
|
|
196
|
-
function v3AdapterTargetPath(projectRoot, target) {
|
|
197
|
-
const root = path.resolve(projectRoot);
|
|
198
|
-
switch (target) {
|
|
199
|
-
case "claude-skill":
|
|
200
|
-
return path.join(root, ".claude", "skills", "mancode-v3", "SKILL.md");
|
|
201
|
-
case "cursor-rule":
|
|
202
|
-
return path.join(root, ".cursor", "rules", "mancode-v3.mdc");
|
|
203
|
-
case "agents":
|
|
204
|
-
return path.join(root, "AGENTS.md");
|
|
205
|
-
case "copilot-instructions":
|
|
206
|
-
return path.join(root, ".github", "copilot-instructions.md");
|
|
207
|
-
}
|
|
208
|
-
}
|
|
209
|
-
async function installV3Adapter(projectRoot, platform) {
|
|
210
|
-
const root = path.resolve(projectRoot);
|
|
211
|
-
const content = renderV3Bootstrap(platform);
|
|
212
|
-
switch (platform) {
|
|
213
|
-
case "claude-code":
|
|
214
|
-
await writeManagedFile(
|
|
215
|
-
path.join(root, ".claude", "skills", "mancode-v3", "SKILL.md"),
|
|
216
|
-
renderClaudeSkill(content)
|
|
217
|
-
);
|
|
218
|
-
break;
|
|
219
|
-
case "cursor":
|
|
220
|
-
await writeManagedFile(
|
|
221
|
-
path.join(root, ".cursor", "rules", "mancode-v3.mdc"),
|
|
222
|
-
renderCursorRule(content)
|
|
223
|
-
);
|
|
224
|
-
break;
|
|
225
|
-
case "codex":
|
|
226
|
-
await replaceManagedV3Block(
|
|
227
|
-
path.join(root, "AGENTS.md"),
|
|
228
|
-
V3_CODEX_START_MARKER,
|
|
229
|
-
V3_CODEX_END_MARKER,
|
|
230
|
-
content
|
|
231
|
-
);
|
|
232
|
-
break;
|
|
233
|
-
case "copilot":
|
|
234
|
-
await replaceManagedV3Block(
|
|
235
|
-
path.join(root, ".github", "copilot-instructions.md"),
|
|
236
|
-
V3_COPILOT_START_MARKER,
|
|
237
|
-
V3_COPILOT_END_MARKER,
|
|
238
|
-
content
|
|
239
|
-
);
|
|
240
|
-
break;
|
|
241
|
-
case "zcode":
|
|
242
|
-
await replaceManagedV3Block(
|
|
243
|
-
path.join(root, "AGENTS.md"),
|
|
244
|
-
V3_ZCODE_START_MARKER,
|
|
245
|
-
V3_ZCODE_END_MARKER,
|
|
246
|
-
content
|
|
247
|
-
);
|
|
248
|
-
break;
|
|
249
|
-
}
|
|
250
|
-
return inspectV3Adapter(root, platform);
|
|
251
|
-
}
|
|
252
|
-
async function inspectV3Adapter(projectRoot, platform) {
|
|
253
|
-
const root = path.resolve(projectRoot);
|
|
254
|
-
const target = targetFor(platform);
|
|
255
|
-
const installed = await adapterTargetPresent(root, platform);
|
|
256
|
-
return {
|
|
257
|
-
version: V3_ADAPTER_VERSION,
|
|
258
|
-
installed,
|
|
259
|
-
ready: installed,
|
|
260
|
-
target,
|
|
261
|
-
detail: installed ? "V3 bootstrap is present; session identity is explicit-required." : "V3 bootstrap is not installed.",
|
|
262
|
-
capabilities: capabilitiesFor(platform)
|
|
263
|
-
};
|
|
264
|
-
}
|
|
265
|
-
async function inspectV3AdapterVersions(projectRoot) {
|
|
266
|
-
const platforms = [
|
|
267
|
-
"claude-code",
|
|
268
|
-
"codex",
|
|
269
|
-
"cursor",
|
|
270
|
-
"copilot",
|
|
271
|
-
"zcode"
|
|
272
|
-
];
|
|
273
|
-
const entries = await Promise.all(
|
|
274
|
-
platforms.map(async (platform) => {
|
|
275
|
-
const status = await inspectV3Adapter(projectRoot, platform);
|
|
276
|
-
return [platform, status.ready ? status.version : "missing"];
|
|
277
|
-
})
|
|
278
|
-
);
|
|
279
|
-
return Object.fromEntries(entries);
|
|
280
|
-
}
|
|
281
|
-
async function removeV3Adapter(projectRoot, platform) {
|
|
282
|
-
const root = path.resolve(projectRoot);
|
|
283
|
-
switch (platform) {
|
|
284
|
-
case "claude-code":
|
|
285
|
-
await removeManagedFile(
|
|
286
|
-
path.join(root, ".claude", "skills", "mancode-v3", "SKILL.md")
|
|
287
|
-
);
|
|
288
|
-
return;
|
|
289
|
-
case "cursor":
|
|
290
|
-
await removeManagedFile(
|
|
291
|
-
path.join(root, ".cursor", "rules", "mancode-v3.mdc")
|
|
292
|
-
);
|
|
293
|
-
return;
|
|
294
|
-
case "codex":
|
|
295
|
-
await removeManagedV3Block(
|
|
296
|
-
path.join(root, "AGENTS.md"),
|
|
297
|
-
V3_CODEX_START_MARKER,
|
|
298
|
-
V3_CODEX_END_MARKER
|
|
299
|
-
);
|
|
300
|
-
return;
|
|
301
|
-
case "copilot":
|
|
302
|
-
await removeManagedV3Block(
|
|
303
|
-
path.join(root, ".github", "copilot-instructions.md"),
|
|
304
|
-
V3_COPILOT_START_MARKER,
|
|
305
|
-
V3_COPILOT_END_MARKER
|
|
306
|
-
);
|
|
307
|
-
return;
|
|
308
|
-
case "zcode":
|
|
309
|
-
await removeManagedV3Block(
|
|
310
|
-
path.join(root, "AGENTS.md"),
|
|
311
|
-
V3_ZCODE_START_MARKER,
|
|
312
|
-
V3_ZCODE_END_MARKER
|
|
313
|
-
);
|
|
314
|
-
}
|
|
315
|
-
}
|
|
316
|
-
function renderV3Bootstrap(platform) {
|
|
317
|
-
const platformLabel = platformLabelFor(platform);
|
|
318
|
-
const modeEntry = capabilitiesFor(platform).nativeModeEntry ? "Use the platform mode entry only as a shortcut; resolve a Context Pack first." : "This platform has no native V3 mode entry; use the CLI commands explicitly.";
|
|
319
|
-
return [
|
|
320
|
-
"# mancode V3 bootstrap",
|
|
321
|
-
"",
|
|
322
|
-
V3_ADAPTER_MANAGED_MARKER,
|
|
323
|
-
"",
|
|
324
|
-
`- Platform: ${platformLabel}. This file is a non-authoritative bootstrap.`,
|
|
325
|
-
"- Locate the project root before running mancode commands.",
|
|
326
|
-
`- Create or supply an explicit session: \`mancode context session new --client ${platform}\` or \`--session <id>\`.`,
|
|
327
|
-
"- Read current task context with `mancode context show --purpose orient --session <id>`; for anonymous diagnosis, include an explicit `--task <namespace:id>`.",
|
|
328
|
-
"- For a mode entry, request the matching Context Pack purpose: `plan`, `implement`, `review`, `verify`, or `handoff`.",
|
|
329
|
-
"- Perform mutations only through `mancode workflow`, `mancode team`, and `mancode context` commands with their required revision and session arguments.",
|
|
330
|
-
"- Do not persist task, mode, or session state in this adapter file or any legacy state file.",
|
|
331
|
-
`- ${modeEntry}`,
|
|
332
|
-
`- No approved session or prompt hook is assumed. After a real-host spike is recorded for ${platform}, a verified host may provide MANCODE_HOST_SESSION_KEY; otherwise mutations require an explicit \`--session\`.`
|
|
333
|
-
].join("\n");
|
|
334
|
-
}
|
|
335
|
-
async function renderV3AdapterCandidate(root, platform) {
|
|
336
|
-
switch (platform) {
|
|
337
|
-
case "claude-code": {
|
|
338
|
-
const existing = await readAdapterTarget(root, "claude-skill");
|
|
339
|
-
return managedFilePlan(
|
|
340
|
-
"claude-skill",
|
|
341
|
-
existing,
|
|
342
|
-
renderClaudeSkill(renderV3Bootstrap(platform))
|
|
343
|
-
).targetContent;
|
|
344
|
-
}
|
|
345
|
-
case "cursor": {
|
|
346
|
-
const existing = await readAdapterTarget(root, "cursor-rule");
|
|
347
|
-
return managedFilePlan(
|
|
348
|
-
"cursor-rule",
|
|
349
|
-
existing,
|
|
350
|
-
renderCursorRule(renderV3Bootstrap(platform))
|
|
351
|
-
).targetContent;
|
|
352
|
-
}
|
|
353
|
-
case "codex": {
|
|
354
|
-
const existing = await readAdapterTarget(root, "agents") ?? "";
|
|
355
|
-
return replaceManagedV3BlockText(
|
|
356
|
-
existing,
|
|
357
|
-
V3_CODEX_START_MARKER,
|
|
358
|
-
V3_CODEX_END_MARKER,
|
|
359
|
-
renderV3Bootstrap(platform)
|
|
360
|
-
);
|
|
361
|
-
}
|
|
362
|
-
case "copilot": {
|
|
363
|
-
const existing = await readAdapterTarget(root, "copilot-instructions") ?? "";
|
|
364
|
-
return replaceManagedV3BlockText(
|
|
365
|
-
existing,
|
|
366
|
-
V3_COPILOT_START_MARKER,
|
|
367
|
-
V3_COPILOT_END_MARKER,
|
|
368
|
-
renderV3Bootstrap(platform)
|
|
369
|
-
);
|
|
370
|
-
}
|
|
371
|
-
case "zcode": {
|
|
372
|
-
const existing = await readAdapterTarget(root, "agents") ?? "";
|
|
373
|
-
return replaceManagedV3BlockText(
|
|
374
|
-
existing,
|
|
375
|
-
V3_ZCODE_START_MARKER,
|
|
376
|
-
V3_ZCODE_END_MARKER,
|
|
377
|
-
renderV3Bootstrap(platform)
|
|
378
|
-
);
|
|
379
|
-
}
|
|
380
|
-
}
|
|
381
|
-
}
|
|
382
|
-
function renderClaudeSkill(content) {
|
|
383
|
-
return [
|
|
384
|
-
"---",
|
|
385
|
-
"name: mancode-v3",
|
|
386
|
-
'description: "Stable bootstrap for mancode V3 context and workflow commands."',
|
|
387
|
-
"---",
|
|
388
|
-
"",
|
|
389
|
-
content,
|
|
390
|
-
""
|
|
391
|
-
].join("\n");
|
|
392
|
-
}
|
|
393
|
-
function renderCursorRule(content) {
|
|
394
|
-
return [
|
|
395
|
-
"---",
|
|
396
|
-
'description: "Stable bootstrap for mancode V3 context and workflow commands."',
|
|
397
|
-
"alwaysApply: true",
|
|
398
|
-
'globs: "**/*"',
|
|
399
|
-
"---",
|
|
400
|
-
"",
|
|
401
|
-
content,
|
|
402
|
-
""
|
|
403
|
-
].join("\n");
|
|
404
|
-
}
|
|
405
|
-
async function adapterTargetPresent(root, platform) {
|
|
406
|
-
switch (platform) {
|
|
407
|
-
case "claude-code":
|
|
408
|
-
return managedFilePresent(
|
|
409
|
-
path.join(root, ".claude", "skills", "mancode-v3", "SKILL.md")
|
|
410
|
-
);
|
|
411
|
-
case "cursor":
|
|
412
|
-
return managedFilePresent(
|
|
413
|
-
path.join(root, ".cursor", "rules", "mancode-v3.mdc")
|
|
414
|
-
);
|
|
415
|
-
case "codex":
|
|
416
|
-
return managedBlockPresent(
|
|
417
|
-
path.join(root, "AGENTS.md"),
|
|
418
|
-
V3_CODEX_START_MARKER,
|
|
419
|
-
V3_CODEX_END_MARKER
|
|
420
|
-
);
|
|
421
|
-
case "copilot":
|
|
422
|
-
return managedBlockPresent(
|
|
423
|
-
path.join(root, ".github", "copilot-instructions.md"),
|
|
424
|
-
V3_COPILOT_START_MARKER,
|
|
425
|
-
V3_COPILOT_END_MARKER
|
|
426
|
-
);
|
|
427
|
-
case "zcode":
|
|
428
|
-
return managedBlockPresent(
|
|
429
|
-
path.join(root, "AGENTS.md"),
|
|
430
|
-
V3_ZCODE_START_MARKER,
|
|
431
|
-
V3_ZCODE_END_MARKER
|
|
432
|
-
);
|
|
433
|
-
}
|
|
434
|
-
}
|
|
435
|
-
async function writeManagedFile(filePath, content) {
|
|
436
|
-
const existing = await readTextIfExists(filePath);
|
|
437
|
-
if (existing !== null && !existing.includes(V3_ADAPTER_MANAGED_MARKER)) {
|
|
438
|
-
throw new Error("MANCODE_V3_ADAPTER_TARGET_USER_AUTHORED");
|
|
439
|
-
}
|
|
440
|
-
await mkdir(path.dirname(filePath), { recursive: true });
|
|
441
|
-
await atomicWrite(filePath, content);
|
|
442
|
-
}
|
|
443
|
-
async function removeManagedFile(filePath) {
|
|
444
|
-
const existing = await readTextIfExists(filePath);
|
|
445
|
-
if (existing?.includes(V3_ADAPTER_MANAGED_MARKER)) {
|
|
446
|
-
await rm(filePath, { force: true });
|
|
447
|
-
}
|
|
448
|
-
}
|
|
449
|
-
async function replaceManagedV3Block(filePath, startMarker, endMarker, content) {
|
|
450
|
-
const existing = await readTextIfExists(filePath) ?? "";
|
|
451
|
-
const block = [startMarker, content, endMarker].join("\n");
|
|
452
|
-
await mkdir(path.dirname(filePath), { recursive: true });
|
|
453
|
-
await atomicWrite(
|
|
454
|
-
filePath,
|
|
455
|
-
replaceManagedBlock(existing, block, startMarker, endMarker)
|
|
456
|
-
);
|
|
457
|
-
}
|
|
458
|
-
function replaceManagedV3BlockText(existing, startMarker, endMarker, content) {
|
|
459
|
-
return replaceManagedBlock(
|
|
460
|
-
existing,
|
|
461
|
-
[startMarker, content, endMarker].join("\n"),
|
|
462
|
-
startMarker,
|
|
463
|
-
endMarker
|
|
464
|
-
);
|
|
465
|
-
}
|
|
466
|
-
function managedFilePlan(target, beforeContent, targetContent) {
|
|
467
|
-
if (beforeContent !== null && !beforeContent.includes(V3_ADAPTER_MANAGED_MARKER)) {
|
|
468
|
-
throw new Error("MANCODE_V3_ADAPTER_TARGET_USER_AUTHORED");
|
|
469
|
-
}
|
|
470
|
-
return { target, beforeContent, targetContent };
|
|
471
|
-
}
|
|
472
|
-
async function readAdapterTarget(root, target) {
|
|
473
|
-
const filePath = v3AdapterTargetPath(root, target);
|
|
474
|
-
try {
|
|
475
|
-
const entry = await lstat(filePath);
|
|
476
|
-
if (!entry.isFile() || entry.isSymbolicLink()) {
|
|
477
|
-
throw new Error("MANCODE_ARTIFACT_PATH_UNSAFE");
|
|
478
|
-
}
|
|
479
|
-
} catch (error) {
|
|
480
|
-
if (isNodeError(error) && error.code === "ENOENT") return null;
|
|
481
|
-
throw error;
|
|
482
|
-
}
|
|
483
|
-
return readFile(filePath, "utf8");
|
|
484
|
-
}
|
|
485
|
-
async function removeManagedV3Block(filePath, startMarker, endMarker) {
|
|
486
|
-
const existing = await readTextIfExists(filePath);
|
|
487
|
-
if (existing === null || !hasManagedBlock(existing, startMarker, endMarker)) {
|
|
488
|
-
return;
|
|
489
|
-
}
|
|
490
|
-
const cleaned = removeManagedBlock(existing, startMarker, endMarker);
|
|
491
|
-
if (cleaned.trim()) {
|
|
492
|
-
await atomicWrite(filePath, `${cleaned.trimEnd()}
|
|
493
|
-
`);
|
|
494
|
-
} else {
|
|
495
|
-
await rm(filePath, { force: true });
|
|
496
|
-
}
|
|
497
|
-
}
|
|
498
|
-
async function managedFilePresent(filePath) {
|
|
499
|
-
const content = await readTextIfExists(filePath);
|
|
500
|
-
return content?.includes(V3_ADAPTER_MANAGED_MARKER) ?? false;
|
|
501
|
-
}
|
|
502
|
-
async function managedBlockPresent(filePath, startMarker, endMarker) {
|
|
503
|
-
const content = await readTextIfExists(filePath);
|
|
504
|
-
return content !== null && hasManagedBlock(content, startMarker, endMarker);
|
|
505
|
-
}
|
|
506
|
-
async function readTextIfExists(filePath) {
|
|
507
|
-
for (let attempt = 1; attempt <= ADAPTER_READ_MAX_ATTEMPTS; attempt += 1) {
|
|
508
|
-
try {
|
|
509
|
-
return await readFile(filePath, "utf8");
|
|
510
|
-
} catch (error) {
|
|
511
|
-
if (isNodeError(error) && error.code === "ENOENT") return null;
|
|
512
|
-
if (!isRetriableAdapterReadError(error) || attempt === ADAPTER_READ_MAX_ATTEMPTS) {
|
|
513
|
-
throw error;
|
|
514
|
-
}
|
|
515
|
-
await delay(ADAPTER_READ_RETRY_DELAY_MS * attempt);
|
|
516
|
-
}
|
|
517
|
-
}
|
|
518
|
-
throw new Error("MANCODE_V3_ADAPTER_READ_RETRY_EXHAUSTED");
|
|
519
|
-
}
|
|
520
|
-
async function atomicWrite(filePath, content) {
|
|
521
|
-
const temporary = path.join(
|
|
522
|
-
path.dirname(filePath),
|
|
523
|
-
`.${path.basename(filePath)}.${process.pid}.${Date.now()}.tmp`
|
|
524
|
-
);
|
|
525
|
-
try {
|
|
526
|
-
await writeFile(temporary, content, { encoding: "utf8", flag: "wx" });
|
|
527
|
-
await rename(temporary, filePath);
|
|
528
|
-
} finally {
|
|
529
|
-
await rm(temporary, { force: true }).catch(() => void 0);
|
|
530
|
-
}
|
|
531
|
-
}
|
|
532
|
-
function targetFor(platform) {
|
|
533
|
-
switch (platform) {
|
|
534
|
-
case "claude-code":
|
|
535
|
-
return ".claude/skills/mancode-v3/SKILL.md";
|
|
536
|
-
case "cursor":
|
|
537
|
-
return ".cursor/rules/mancode-v3.mdc";
|
|
538
|
-
case "codex":
|
|
539
|
-
case "zcode":
|
|
540
|
-
return "AGENTS.md";
|
|
541
|
-
case "copilot":
|
|
542
|
-
return ".github/copilot-instructions.md";
|
|
543
|
-
}
|
|
544
|
-
}
|
|
545
|
-
function platformLabelFor(platform) {
|
|
546
|
-
switch (platform) {
|
|
547
|
-
case "claude-code":
|
|
548
|
-
return "Claude Code";
|
|
549
|
-
case "cursor":
|
|
550
|
-
return "Cursor";
|
|
551
|
-
case "codex":
|
|
552
|
-
return "Codex";
|
|
553
|
-
case "copilot":
|
|
554
|
-
return "GitHub Copilot";
|
|
555
|
-
case "zcode":
|
|
556
|
-
return "ZCode";
|
|
557
|
-
}
|
|
558
|
-
}
|
|
559
|
-
function capabilitiesFor(platform) {
|
|
560
|
-
return {
|
|
561
|
-
nativeModeEntry: platform === "claude-code" || platform === "cursor",
|
|
562
|
-
sessionHook: false,
|
|
563
|
-
promptHook: false,
|
|
564
|
-
sessionIdentity: "explicit-required"
|
|
565
|
-
};
|
|
566
|
-
}
|
|
567
|
-
function isNodeError(error) {
|
|
568
|
-
return typeof error === "object" && error !== null && "code" in error;
|
|
569
|
-
}
|
|
570
|
-
function isRetriableAdapterReadError(error) {
|
|
571
|
-
return isNodeError(error) && RETRIABLE_ADAPTER_READ_CODES.has(error.code ?? "");
|
|
572
|
-
}
|
|
573
|
-
async function delay(milliseconds) {
|
|
574
|
-
await new Promise((resolve) => {
|
|
575
|
-
setTimeout(resolve, milliseconds);
|
|
576
|
-
});
|
|
577
|
-
}
|
|
578
|
-
|
|
579
|
-
export {
|
|
580
|
-
DEFAULT_MANCODE_START_MARKER,
|
|
581
|
-
DEFAULT_MANCODE_END_MARKER,
|
|
582
|
-
removeManagedBlock,
|
|
583
|
-
hasManagedBlock,
|
|
584
|
-
replaceManagedBlock,
|
|
585
|
-
V3_ADAPTER_VERSION,
|
|
586
|
-
V3_ADAPTER_MANAGED_MARKER,
|
|
587
|
-
planV3AdapterFiles,
|
|
588
|
-
applyV3AdapterFilePlan,
|
|
589
|
-
stageV3Adapter,
|
|
590
|
-
v3AdapterTargetPath,
|
|
591
|
-
installV3Adapter,
|
|
592
|
-
inspectV3Adapter,
|
|
593
|
-
inspectV3AdapterVersions,
|
|
594
|
-
removeV3Adapter,
|
|
595
|
-
renderV3Bootstrap
|
|
596
|
-
};
|
|
597
|
-
//# sourceMappingURL=chunk-KEIW7AEP.js.map
|