@deepstorm/cli 0.6.5 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli.js +588 -447
- package/package.json +2 -2
package/dist/cli.js
CHANGED
|
@@ -1187,13 +1187,13 @@ var require_ast = __commonJS({
|
|
|
1187
1187
|
helperExpression: function helperExpression(node) {
|
|
1188
1188
|
return node.type === "SubExpression" || (node.type === "MustacheStatement" || node.type === "BlockStatement") && !!(node.params && node.params.length || node.hash);
|
|
1189
1189
|
},
|
|
1190
|
-
scopedId: function scopedId(
|
|
1191
|
-
return /^\.|this\b/.test(
|
|
1190
|
+
scopedId: function scopedId(path23) {
|
|
1191
|
+
return /^\.|this\b/.test(path23.original);
|
|
1192
1192
|
},
|
|
1193
1193
|
// an ID is simple if it only has one part, and that part is not
|
|
1194
1194
|
// `..` or `this`.
|
|
1195
|
-
simpleId: function simpleId(
|
|
1196
|
-
return
|
|
1195
|
+
simpleId: function simpleId(path23) {
|
|
1196
|
+
return path23.parts.length === 1 && !AST.helpers.scopedId(path23) && !path23.depth;
|
|
1197
1197
|
}
|
|
1198
1198
|
}
|
|
1199
1199
|
};
|
|
@@ -2263,12 +2263,12 @@ var require_helpers2 = __commonJS({
|
|
|
2263
2263
|
loc
|
|
2264
2264
|
};
|
|
2265
2265
|
}
|
|
2266
|
-
function prepareMustache(
|
|
2266
|
+
function prepareMustache(path23, params, hash, open, strip, locInfo) {
|
|
2267
2267
|
var escapeFlag = open.charAt(3) || open.charAt(2), escaped = escapeFlag !== "{" && escapeFlag !== "&";
|
|
2268
2268
|
var decorator = /\*/.test(open);
|
|
2269
2269
|
return {
|
|
2270
2270
|
type: decorator ? "Decorator" : "MustacheStatement",
|
|
2271
|
-
path:
|
|
2271
|
+
path: path23,
|
|
2272
2272
|
params,
|
|
2273
2273
|
hash,
|
|
2274
2274
|
escaped,
|
|
@@ -2586,9 +2586,9 @@ var require_compiler = __commonJS({
|
|
|
2586
2586
|
},
|
|
2587
2587
|
DecoratorBlock: function DecoratorBlock(decorator) {
|
|
2588
2588
|
var program2 = decorator.program && this.compileProgram(decorator.program);
|
|
2589
|
-
var params = this.setupFullMustacheParams(decorator, program2, void 0),
|
|
2589
|
+
var params = this.setupFullMustacheParams(decorator, program2, void 0), path23 = decorator.path;
|
|
2590
2590
|
this.useDecorators = true;
|
|
2591
|
-
this.opcode("registerDecorator", params.length,
|
|
2591
|
+
this.opcode("registerDecorator", params.length, path23.original);
|
|
2592
2592
|
},
|
|
2593
2593
|
PartialStatement: function PartialStatement(partial) {
|
|
2594
2594
|
this.usePartial = true;
|
|
@@ -2652,46 +2652,46 @@ var require_compiler = __commonJS({
|
|
|
2652
2652
|
}
|
|
2653
2653
|
},
|
|
2654
2654
|
ambiguousSexpr: function ambiguousSexpr(sexpr, program2, inverse) {
|
|
2655
|
-
var
|
|
2656
|
-
this.opcode("getContext",
|
|
2655
|
+
var path23 = sexpr.path, name = path23.parts[0], isBlock = program2 != null || inverse != null;
|
|
2656
|
+
this.opcode("getContext", path23.depth);
|
|
2657
2657
|
this.opcode("pushProgram", program2);
|
|
2658
2658
|
this.opcode("pushProgram", inverse);
|
|
2659
|
-
|
|
2660
|
-
this.accept(
|
|
2659
|
+
path23.strict = true;
|
|
2660
|
+
this.accept(path23);
|
|
2661
2661
|
this.opcode("invokeAmbiguous", name, isBlock);
|
|
2662
2662
|
},
|
|
2663
2663
|
simpleSexpr: function simpleSexpr(sexpr) {
|
|
2664
|
-
var
|
|
2665
|
-
|
|
2666
|
-
this.accept(
|
|
2664
|
+
var path23 = sexpr.path;
|
|
2665
|
+
path23.strict = true;
|
|
2666
|
+
this.accept(path23);
|
|
2667
2667
|
this.opcode("resolvePossibleLambda");
|
|
2668
2668
|
},
|
|
2669
2669
|
helperSexpr: function helperSexpr(sexpr, program2, inverse) {
|
|
2670
|
-
var params = this.setupFullMustacheParams(sexpr, program2, inverse),
|
|
2670
|
+
var params = this.setupFullMustacheParams(sexpr, program2, inverse), path23 = sexpr.path, name = path23.parts[0];
|
|
2671
2671
|
if (this.options.knownHelpers[name]) {
|
|
2672
2672
|
this.opcode("invokeKnownHelper", params.length, name);
|
|
2673
2673
|
} else if (this.options.knownHelpersOnly) {
|
|
2674
2674
|
throw new _exception2["default"]("You specified knownHelpersOnly, but used the unknown helper " + name, sexpr);
|
|
2675
2675
|
} else {
|
|
2676
|
-
|
|
2677
|
-
|
|
2678
|
-
this.accept(
|
|
2679
|
-
this.opcode("invokeHelper", params.length,
|
|
2676
|
+
path23.strict = true;
|
|
2677
|
+
path23.falsy = true;
|
|
2678
|
+
this.accept(path23);
|
|
2679
|
+
this.opcode("invokeHelper", params.length, path23.original, _ast2["default"].helpers.simpleId(path23));
|
|
2680
2680
|
}
|
|
2681
2681
|
},
|
|
2682
|
-
PathExpression: function PathExpression(
|
|
2683
|
-
this.addDepth(
|
|
2684
|
-
this.opcode("getContext",
|
|
2685
|
-
var name =
|
|
2682
|
+
PathExpression: function PathExpression(path23) {
|
|
2683
|
+
this.addDepth(path23.depth);
|
|
2684
|
+
this.opcode("getContext", path23.depth);
|
|
2685
|
+
var name = path23.parts[0], scoped = _ast2["default"].helpers.scopedId(path23), blockParamId = !path23.depth && !scoped && this.blockParamIndex(name);
|
|
2686
2686
|
if (blockParamId) {
|
|
2687
|
-
this.opcode("lookupBlockParam", blockParamId,
|
|
2687
|
+
this.opcode("lookupBlockParam", blockParamId, path23.parts);
|
|
2688
2688
|
} else if (!name) {
|
|
2689
2689
|
this.opcode("pushContext");
|
|
2690
|
-
} else if (
|
|
2690
|
+
} else if (path23.data) {
|
|
2691
2691
|
this.options.data = true;
|
|
2692
|
-
this.opcode("lookupData",
|
|
2692
|
+
this.opcode("lookupData", path23.depth, path23.parts, path23.strict);
|
|
2693
2693
|
} else {
|
|
2694
|
-
this.opcode("lookupOnContext",
|
|
2694
|
+
this.opcode("lookupOnContext", path23.parts, path23.falsy, path23.strict, scoped);
|
|
2695
2695
|
}
|
|
2696
2696
|
},
|
|
2697
2697
|
StringLiteral: function StringLiteral(string) {
|
|
@@ -3041,16 +3041,16 @@ var require_util = __commonJS({
|
|
|
3041
3041
|
}
|
|
3042
3042
|
exports2.urlGenerate = urlGenerate;
|
|
3043
3043
|
function normalize(aPath) {
|
|
3044
|
-
var
|
|
3044
|
+
var path23 = aPath;
|
|
3045
3045
|
var url = urlParse(aPath);
|
|
3046
3046
|
if (url) {
|
|
3047
3047
|
if (!url.path) {
|
|
3048
3048
|
return aPath;
|
|
3049
3049
|
}
|
|
3050
|
-
|
|
3050
|
+
path23 = url.path;
|
|
3051
3051
|
}
|
|
3052
|
-
var isAbsolute = exports2.isAbsolute(
|
|
3053
|
-
var parts =
|
|
3052
|
+
var isAbsolute = exports2.isAbsolute(path23);
|
|
3053
|
+
var parts = path23.split(/\/+/);
|
|
3054
3054
|
for (var part, up = 0, i = parts.length - 1; i >= 0; i--) {
|
|
3055
3055
|
part = parts[i];
|
|
3056
3056
|
if (part === ".") {
|
|
@@ -3067,18 +3067,18 @@ var require_util = __commonJS({
|
|
|
3067
3067
|
}
|
|
3068
3068
|
}
|
|
3069
3069
|
}
|
|
3070
|
-
|
|
3071
|
-
if (
|
|
3072
|
-
|
|
3070
|
+
path23 = parts.join("/");
|
|
3071
|
+
if (path23 === "") {
|
|
3072
|
+
path23 = isAbsolute ? "/" : ".";
|
|
3073
3073
|
}
|
|
3074
3074
|
if (url) {
|
|
3075
|
-
url.path =
|
|
3075
|
+
url.path = path23;
|
|
3076
3076
|
return urlGenerate(url);
|
|
3077
3077
|
}
|
|
3078
|
-
return
|
|
3078
|
+
return path23;
|
|
3079
3079
|
}
|
|
3080
3080
|
exports2.normalize = normalize;
|
|
3081
|
-
function
|
|
3081
|
+
function join21(aRoot, aPath) {
|
|
3082
3082
|
if (aRoot === "") {
|
|
3083
3083
|
aRoot = ".";
|
|
3084
3084
|
}
|
|
@@ -3110,7 +3110,7 @@ var require_util = __commonJS({
|
|
|
3110
3110
|
}
|
|
3111
3111
|
return joined;
|
|
3112
3112
|
}
|
|
3113
|
-
exports2.join =
|
|
3113
|
+
exports2.join = join21;
|
|
3114
3114
|
exports2.isAbsolute = function(aPath) {
|
|
3115
3115
|
return aPath.charAt(0) === "/" || urlRegexp.test(aPath);
|
|
3116
3116
|
};
|
|
@@ -3283,7 +3283,7 @@ var require_util = __commonJS({
|
|
|
3283
3283
|
parsed.path = parsed.path.substring(0, index + 1);
|
|
3284
3284
|
}
|
|
3285
3285
|
}
|
|
3286
|
-
sourceURL =
|
|
3286
|
+
sourceURL = join21(urlGenerate(parsed), sourceURL);
|
|
3287
3287
|
}
|
|
3288
3288
|
return normalize(sourceURL);
|
|
3289
3289
|
}
|
|
@@ -5858,8 +5858,8 @@ var require_printer = __commonJS({
|
|
|
5858
5858
|
return this.accept(sexpr.path) + " " + params + hash;
|
|
5859
5859
|
};
|
|
5860
5860
|
PrintVisitor.prototype.PathExpression = function(id) {
|
|
5861
|
-
var
|
|
5862
|
-
return (id.data ? "@" : "") + "PATH:" +
|
|
5861
|
+
var path23 = id.parts.join("/");
|
|
5862
|
+
return (id.data ? "@" : "") + "PATH:" + path23;
|
|
5863
5863
|
};
|
|
5864
5864
|
PrintVisitor.prototype.StringLiteral = function(string) {
|
|
5865
5865
|
return '"' + string.value + '"';
|
|
@@ -5898,8 +5898,8 @@ var require_lib = __commonJS({
|
|
|
5898
5898
|
handlebars.print = printer.print;
|
|
5899
5899
|
module2.exports = handlebars;
|
|
5900
5900
|
function extension(module3, filename) {
|
|
5901
|
-
var
|
|
5902
|
-
var templateString =
|
|
5901
|
+
var fs28 = require("fs");
|
|
5902
|
+
var templateString = fs28.readFileSync(filename, "utf8");
|
|
5903
5903
|
module3.exports = handlebars.compile(templateString);
|
|
5904
5904
|
}
|
|
5905
5905
|
if (typeof require !== "undefined" && require.extensions) {
|
|
@@ -5911,12 +5911,12 @@ var require_lib = __commonJS({
|
|
|
5911
5911
|
|
|
5912
5912
|
// src/index.ts
|
|
5913
5913
|
var import_commander = require("commander");
|
|
5914
|
-
var
|
|
5915
|
-
var
|
|
5914
|
+
var fs27 = __toESM(require("node:fs"));
|
|
5915
|
+
var path22 = __toESM(require("node:path"));
|
|
5916
5916
|
|
|
5917
5917
|
// src/commands/setup.ts
|
|
5918
|
-
var
|
|
5919
|
-
var
|
|
5918
|
+
var path9 = __toESM(require("node:path"));
|
|
5919
|
+
var fs13 = __toESM(require("node:fs"));
|
|
5920
5920
|
|
|
5921
5921
|
// src/engine/registry.ts
|
|
5922
5922
|
var RegistryReader = class {
|
|
@@ -6247,19 +6247,38 @@ function initContextMap(targetDir, opts) {
|
|
|
6247
6247
|
const content = CONTEXT_MD_TEMPLATE.replace("{backend.language}", backendLang).replace("{frontend.framework}", frontendFramework);
|
|
6248
6248
|
fs2.writeFileSync(contextPath, content, "utf-8");
|
|
6249
6249
|
console.log("\u2714 \u5DF2\u521B\u5EFA .deepstorm/context.md \u9879\u76EE\u4E0A\u4E0B\u6587\u5730\u56FE");
|
|
6250
|
-
appendClaudeMdRef(targetDir);
|
|
6251
6250
|
}
|
|
6252
|
-
function
|
|
6253
|
-
const
|
|
6254
|
-
const
|
|
6255
|
-
if (
|
|
6256
|
-
|
|
6257
|
-
|
|
6251
|
+
function initClaudeMd(targetDir, opts) {
|
|
6252
|
+
const claudeDir = path2.join(targetDir, ".claude");
|
|
6253
|
+
const claudeMdPath = path2.join(claudeDir, "CLAUDE.md");
|
|
6254
|
+
if (fs2.existsSync(claudeMdPath)) return;
|
|
6255
|
+
ensureDir2(claudeDir);
|
|
6256
|
+
const projectName = opts.projectName || "unknown";
|
|
6257
|
+
const lines = [
|
|
6258
|
+
`# ${projectName}`,
|
|
6259
|
+
""
|
|
6260
|
+
];
|
|
6261
|
+
const techLines = [];
|
|
6262
|
+
if (opts.frontend) {
|
|
6263
|
+
techLines.push(`- **\u524D\u7AEF**\uFF1A${opts.frontend}`);
|
|
6264
|
+
if (opts.uiLib) techLines.push(`- **UI \u5E93**\uFF1A${opts.uiLib}`);
|
|
6265
|
+
if (opts.cssFramework) techLines.push(`- **CSS \u65B9\u6848**\uFF1A${opts.cssFramework}`);
|
|
6266
|
+
}
|
|
6267
|
+
if (opts.backend) {
|
|
6268
|
+
techLines.push(`- **\u540E\u7AEF**\uFF1A${opts.backend}`);
|
|
6269
|
+
if (opts.orm) techLines.push(`- **ORM**\uFF1A${opts.orm}`);
|
|
6270
|
+
if (opts.migration) techLines.push(`- **\u6570\u636E\u5E93\u8FC1\u79FB**\uFF1A${opts.migration}`);
|
|
6271
|
+
if (opts.ai) techLines.push(`- **AI \u6846\u67B6**\uFF1A${opts.ai}`);
|
|
6258
6272
|
}
|
|
6259
|
-
|
|
6260
|
-
|
|
6261
|
-
|
|
6262
|
-
|
|
6273
|
+
if (techLines.length > 0) {
|
|
6274
|
+
lines.push("## \u6280\u672F\u6808", "");
|
|
6275
|
+
lines.push(...techLines);
|
|
6276
|
+
lines.push("");
|
|
6277
|
+
}
|
|
6278
|
+
lines.push("> \u9879\u76EE\u4E8B\u5B9E\u89C1 .deepstorm/context.md");
|
|
6279
|
+
lines.push("");
|
|
6280
|
+
fs2.writeFileSync(claudeMdPath, lines.join("\n"), "utf-8");
|
|
6281
|
+
console.log("\u2714 \u5DF2\u521B\u5EFA .claude/claude.md \u9879\u76EE\u4FE1\u606F");
|
|
6263
6282
|
}
|
|
6264
6283
|
function writeInitTechStack(baseDir, opts) {
|
|
6265
6284
|
const config = {};
|
|
@@ -6280,6 +6299,7 @@ function writeInitTechStack(baseDir, opts) {
|
|
|
6280
6299
|
const nested = buildInitNestedConfig(config);
|
|
6281
6300
|
writeDeepStormConfig(baseDir, nested);
|
|
6282
6301
|
initContextMap(baseDir, opts);
|
|
6302
|
+
initClaudeMd(baseDir, opts);
|
|
6283
6303
|
}
|
|
6284
6304
|
function buildInitNestedConfig(flat) {
|
|
6285
6305
|
const result = { reef: {} };
|
|
@@ -6346,9 +6366,10 @@ async function promptContinueSetup(targetDir, projectName, registry2) {
|
|
|
6346
6366
|
}
|
|
6347
6367
|
}
|
|
6348
6368
|
function buildContext(opts) {
|
|
6369
|
+
const projectName = opts.projectName || "project";
|
|
6349
6370
|
return {
|
|
6350
|
-
projectName
|
|
6351
|
-
packageName:
|
|
6371
|
+
projectName,
|
|
6372
|
+
packageName: projectName.replace(/[_-]/g, "").toLowerCase(),
|
|
6352
6373
|
groupId: "com.example",
|
|
6353
6374
|
frontend: opts.frontend || false,
|
|
6354
6375
|
backend: opts.backend || false,
|
|
@@ -6362,19 +6383,34 @@ function buildContext(opts) {
|
|
|
6362
6383
|
async function runInteractiveMode(targetDir) {
|
|
6363
6384
|
const { intro: intro2, outro: outro2, text: text2, select: select2, isCancel: isCancel8, confirm: confirm6 } = await import("@clack/prompts");
|
|
6364
6385
|
intro2("\u{1F680} DeepStorm Init \u2014 \u9879\u76EE\u811A\u624B\u67B6\u521D\u59CB\u5316");
|
|
6365
|
-
const
|
|
6366
|
-
message: "\u9879\u76EE\
|
|
6367
|
-
|
|
6368
|
-
validate: (value) => {
|
|
6369
|
-
if (!value) return "\u8BF7\u8F93\u5165\u9879\u76EE\u540D\u79F0";
|
|
6370
|
-
if (!VALID_PROJECT_NAME.test(value)) return "\u9879\u76EE\u540D\u4EC5\u652F\u6301\u5B57\u6BCD\u3001\u6570\u5B57\u3001\u4E0B\u5212\u7EBF\u548C\u77ED\u6A2A\u7EBF";
|
|
6371
|
-
return void 0;
|
|
6372
|
-
}
|
|
6386
|
+
const isProjectDir = await confirm6({
|
|
6387
|
+
message: "\u5F53\u524D\u8DEF\u5F84\u662F\u5426\u4E3A\u9879\u76EE\u76EE\u5F55\uFF1F",
|
|
6388
|
+
initialValue: false
|
|
6373
6389
|
});
|
|
6374
|
-
if (isCancel8(
|
|
6390
|
+
if (isCancel8(isProjectDir)) {
|
|
6375
6391
|
outro2("\u5DF2\u53D6\u6D88");
|
|
6376
6392
|
return;
|
|
6377
6393
|
}
|
|
6394
|
+
let projectName;
|
|
6395
|
+
if (isProjectDir) {
|
|
6396
|
+
console.log("\u2713 \u5C06\u5728\u5F53\u524D\u76EE\u5F55\u76F4\u63A5\u751F\u6210\u811A\u624B\u67B6");
|
|
6397
|
+
projectName = void 0;
|
|
6398
|
+
} else {
|
|
6399
|
+
const name = await text2({
|
|
6400
|
+
message: "\u9879\u76EE\u540D\u79F0\uFF1A",
|
|
6401
|
+
placeholder: "my-project",
|
|
6402
|
+
validate: (value) => {
|
|
6403
|
+
if (!value) return "\u8BF7\u8F93\u5165\u9879\u76EE\u540D\u79F0";
|
|
6404
|
+
if (!VALID_PROJECT_NAME.test(value)) return "\u9879\u76EE\u540D\u4EC5\u652F\u6301\u5B57\u6BCD\u3001\u6570\u5B57\u3001\u4E0B\u5212\u7EBF\u548C\u77ED\u6A2A\u7EBF";
|
|
6405
|
+
return void 0;
|
|
6406
|
+
}
|
|
6407
|
+
});
|
|
6408
|
+
if (isCancel8(name) || typeof name !== "string") {
|
|
6409
|
+
outro2("\u5DF2\u53D6\u6D88");
|
|
6410
|
+
return;
|
|
6411
|
+
}
|
|
6412
|
+
projectName = name;
|
|
6413
|
+
}
|
|
6378
6414
|
const frontendChoice = await select2({
|
|
6379
6415
|
message: "\u9009\u62E9\u524D\u7AEF\u6846\u67B6\uFF1A",
|
|
6380
6416
|
options: [
|
|
@@ -6389,28 +6425,30 @@ async function runInteractiveMode(targetDir) {
|
|
|
6389
6425
|
let uiLib;
|
|
6390
6426
|
let cssFramework;
|
|
6391
6427
|
if (frontendChoice === "angular") {
|
|
6392
|
-
|
|
6428
|
+
const uiLibResult = await select2({
|
|
6393
6429
|
message: "\u9009\u62E9 UI \u5E93\uFF1A",
|
|
6394
6430
|
options: [
|
|
6395
6431
|
{ value: "primeng", label: "PrimeNG" },
|
|
6396
6432
|
{ value: "none", label: "\u65E0\uFF08\u4EC5 Angular \u6838\u5FC3\uFF09" }
|
|
6397
6433
|
]
|
|
6398
6434
|
});
|
|
6399
|
-
if (isCancel8(
|
|
6435
|
+
if (isCancel8(uiLibResult)) {
|
|
6400
6436
|
outro2("\u5DF2\u53D6\u6D88");
|
|
6401
6437
|
return;
|
|
6402
6438
|
}
|
|
6403
|
-
|
|
6439
|
+
uiLib = uiLibResult;
|
|
6440
|
+
const cssResult = await select2({
|
|
6404
6441
|
message: "\u9009\u62E9 CSS \u65B9\u6848\uFF1A",
|
|
6405
6442
|
options: [
|
|
6406
6443
|
{ value: "tailwind", label: "Tailwind CSS" },
|
|
6407
6444
|
{ value: "none", label: "\u6807\u51C6 CSS" }
|
|
6408
6445
|
]
|
|
6409
6446
|
});
|
|
6410
|
-
if (isCancel8(
|
|
6447
|
+
if (isCancel8(cssResult)) {
|
|
6411
6448
|
outro2("\u5DF2\u53D6\u6D88");
|
|
6412
6449
|
return;
|
|
6413
6450
|
}
|
|
6451
|
+
cssFramework = cssResult;
|
|
6414
6452
|
}
|
|
6415
6453
|
const backendChoice = await select2({
|
|
6416
6454
|
message: "\u9009\u62E9\u540E\u7AEF\u6846\u67B6\uFF1A",
|
|
@@ -6427,39 +6465,42 @@ async function runInteractiveMode(targetDir) {
|
|
|
6427
6465
|
let migration;
|
|
6428
6466
|
let aiChoice;
|
|
6429
6467
|
if (backendChoice === "java") {
|
|
6430
|
-
|
|
6468
|
+
const ormResult = await select2({
|
|
6431
6469
|
message: "\u9009\u62E9 ORM \u6846\u67B6\uFF1A",
|
|
6432
6470
|
options: [
|
|
6433
6471
|
{ value: "hibernate", label: "Hibernate" },
|
|
6434
6472
|
{ value: "none", label: "\u65E0" }
|
|
6435
6473
|
]
|
|
6436
6474
|
});
|
|
6437
|
-
if (isCancel8(
|
|
6475
|
+
if (isCancel8(ormResult)) {
|
|
6438
6476
|
outro2("\u5DF2\u53D6\u6D88");
|
|
6439
6477
|
return;
|
|
6440
6478
|
}
|
|
6441
|
-
|
|
6479
|
+
orm = ormResult;
|
|
6480
|
+
const migrationResult = await select2({
|
|
6442
6481
|
message: "\u9009\u62E9\u6570\u636E\u5E93\u8FC1\u79FB\u5DE5\u5177\uFF1A",
|
|
6443
6482
|
options: [
|
|
6444
6483
|
{ value: "liquibase", label: "Liquibase" },
|
|
6445
6484
|
{ value: "none", label: "\u65E0" }
|
|
6446
6485
|
]
|
|
6447
6486
|
});
|
|
6448
|
-
if (isCancel8(
|
|
6487
|
+
if (isCancel8(migrationResult)) {
|
|
6449
6488
|
outro2("\u5DF2\u53D6\u6D88");
|
|
6450
6489
|
return;
|
|
6451
6490
|
}
|
|
6452
|
-
|
|
6491
|
+
migration = migrationResult;
|
|
6492
|
+
const aiResult = await select2({
|
|
6453
6493
|
message: "\u9009\u62E9 AI \u6846\u67B6\uFF1A",
|
|
6454
6494
|
options: [
|
|
6455
6495
|
{ value: "spring-ai", label: "Spring AI" },
|
|
6456
6496
|
{ value: "none", label: "\u65E0" }
|
|
6457
6497
|
]
|
|
6458
6498
|
});
|
|
6459
|
-
if (isCancel8(
|
|
6499
|
+
if (isCancel8(aiResult)) {
|
|
6460
6500
|
outro2("\u5DF2\u53D6\u6D88");
|
|
6461
6501
|
return;
|
|
6462
6502
|
}
|
|
6503
|
+
aiChoice = aiResult;
|
|
6463
6504
|
}
|
|
6464
6505
|
if ((!frontendChoice || frontendChoice === "none") && (!backendChoice || backendChoice === "none")) {
|
|
6465
6506
|
console.error("\u274C \u81F3\u5C11\u9700\u8981\u9009\u62E9\u524D\u7AEF\u6216\u540E\u7AEF\u4E4B\u4E00");
|
|
@@ -6481,18 +6522,19 @@ async function runInteractiveMode(targetDir) {
|
|
|
6481
6522
|
return opts;
|
|
6482
6523
|
}
|
|
6483
6524
|
async function runInit(baseDir, opts) {
|
|
6484
|
-
|
|
6485
|
-
|
|
6486
|
-
|
|
6487
|
-
|
|
6488
|
-
throw new Error(`\u9879\u76EE\u540D "${opts.projectName}" \u5305\u542B\u975E\u6CD5\u5B57\u7B26\u3002\u4EC5\u652F\u6301\u5B57\u6BCD\u3001\u6570\u5B57\u3001\u4E0B\u5212\u7EBF\u548C\u77ED\u6A2A\u7EBF\u3002`);
|
|
6525
|
+
const inPlace = !opts.projectName;
|
|
6526
|
+
const projectName = inPlace ? "project" : opts.projectName;
|
|
6527
|
+
if (!inPlace && !VALID_PROJECT_NAME.test(projectName)) {
|
|
6528
|
+
throw new Error(`\u9879\u76EE\u540D "${projectName}" \u5305\u542B\u975E\u6CD5\u5B57\u7B26\u3002\u4EC5\u652F\u6301\u5B57\u6BCD\u3001\u6570\u5B57\u3001\u4E0B\u5212\u7EBF\u548C\u77ED\u6A2A\u7EBF\u3002`);
|
|
6489
6529
|
}
|
|
6490
|
-
const projectDir = path2.join(baseDir,
|
|
6491
|
-
if (fs2.existsSync(projectDir)) {
|
|
6530
|
+
const projectDir = inPlace ? baseDir : path2.join(baseDir, projectName);
|
|
6531
|
+
if (!inPlace && fs2.existsSync(projectDir)) {
|
|
6492
6532
|
throw new Error(`\u76EE\u6807\u76EE\u5F55 ${projectDir} \u5DF2\u5B58\u5728\u3002\u8BF7\u5220\u9664\u540E\u91CD\u8BD5\u6216\u4F7F\u7528\u5176\u4ED6\u9879\u76EE\u540D\u3002`);
|
|
6493
6533
|
}
|
|
6534
|
+
if (!inPlace) {
|
|
6535
|
+
fs2.mkdirSync(projectDir, { recursive: true });
|
|
6536
|
+
}
|
|
6494
6537
|
const ctx = buildContext(opts);
|
|
6495
|
-
fs2.mkdirSync(projectDir, { recursive: true });
|
|
6496
6538
|
const hasFrontend = opts.frontend === "angular";
|
|
6497
6539
|
const hasBackend = opts.backend === "java";
|
|
6498
6540
|
try {
|
|
@@ -6506,13 +6548,18 @@ async function runInit(baseDir, opts) {
|
|
|
6506
6548
|
console.log(`
|
|
6507
6549
|
\u2714 \u9879\u76EE\u5DF2\u521B\u5EFA: ${projectDir}`);
|
|
6508
6550
|
console.log("\n\u4E0B\u4E00\u6B65:");
|
|
6509
|
-
|
|
6551
|
+
if (!inPlace) {
|
|
6552
|
+
console.log(` cd ${opts.projectName}`);
|
|
6553
|
+
}
|
|
6510
6554
|
if (opts.frontend) console.log(` pnpm install # \u5B89\u88C5\u524D\u7AEF\u4F9D\u8D56`);
|
|
6511
6555
|
if (opts.backend) console.log(` ./gradlew build # \u6784\u5EFA\u540E\u7AEF`);
|
|
6512
6556
|
console.log();
|
|
6513
6557
|
printProjectTree(projectDir, hasFrontend, hasBackend);
|
|
6558
|
+
if (inPlace) {
|
|
6559
|
+
initClaudeMd(baseDir, opts);
|
|
6560
|
+
}
|
|
6514
6561
|
} catch (err) {
|
|
6515
|
-
if (fs2.existsSync(projectDir)) {
|
|
6562
|
+
if (!inPlace && fs2.existsSync(projectDir)) {
|
|
6516
6563
|
fs2.rmSync(projectDir, { recursive: true, force: true });
|
|
6517
6564
|
}
|
|
6518
6565
|
throw err;
|
|
@@ -7018,7 +7065,7 @@ __pycache__/
|
|
|
7018
7065
|
.vscode/
|
|
7019
7066
|
*.iml
|
|
7020
7067
|
`);
|
|
7021
|
-
|
|
7068
|
+
writeEnvFile(projectDir, `# \u6570\u636E\u5E93\u914D\u7F6E
|
|
7022
7069
|
DB_URL=jdbc:postgresql://localhost:5432/${ctx.packageName}
|
|
7023
7070
|
DB_USERNAME=postgres
|
|
7024
7071
|
DB_PASSWORD=change-me
|
|
@@ -7076,9 +7123,23 @@ function ensureDir2(dir) {
|
|
|
7076
7123
|
}
|
|
7077
7124
|
function writeTemplate(baseDir, relativePath, content) {
|
|
7078
7125
|
const fullPath = path2.join(baseDir, relativePath);
|
|
7126
|
+
if (fs2.existsSync(fullPath)) {
|
|
7127
|
+
console.log(` \u2139 \u8DF3\u8FC7\u5DF2\u6709\u6587\u4EF6: ${relativePath}`);
|
|
7128
|
+
return;
|
|
7129
|
+
}
|
|
7079
7130
|
ensureDir2(path2.dirname(fullPath));
|
|
7080
7131
|
fs2.writeFileSync(fullPath, content, "utf-8");
|
|
7081
7132
|
}
|
|
7133
|
+
function writeEnvFile(baseDir, content) {
|
|
7134
|
+
const envPath = path2.join(baseDir, ".env");
|
|
7135
|
+
ensureDir2(path2.dirname(envPath));
|
|
7136
|
+
if (fs2.existsSync(envPath)) {
|
|
7137
|
+
const existing = fs2.readFileSync(envPath, "utf-8").trimEnd();
|
|
7138
|
+
fs2.writeFileSync(envPath, existing + "\n\n" + content, "utf-8");
|
|
7139
|
+
} else {
|
|
7140
|
+
fs2.writeFileSync(envPath, content, "utf-8");
|
|
7141
|
+
}
|
|
7142
|
+
}
|
|
7082
7143
|
function printProjectTree(projectDir, hasFrontend, hasBackend) {
|
|
7083
7144
|
console.log("\u76EE\u5F55\u7ED3\u6784:");
|
|
7084
7145
|
console.log(` ${path2.basename(projectDir)}/`);
|
|
@@ -7109,13 +7170,90 @@ function printProjectTree(projectDir, hasFrontend, hasBackend) {
|
|
|
7109
7170
|
}
|
|
7110
7171
|
}
|
|
7111
7172
|
|
|
7112
|
-
// src/
|
|
7173
|
+
// src/utils/auto-install.ts
|
|
7113
7174
|
var fs3 = __toESM(require("node:fs"));
|
|
7175
|
+
var path3 = __toESM(require("node:path"));
|
|
7176
|
+
var import_node_child_process = require("node:child_process");
|
|
7177
|
+
var EXEC_OPTIONS = { encoding: "utf-8", timeout: 12e4, stdio: "pipe" };
|
|
7178
|
+
function execSafe(command) {
|
|
7179
|
+
try {
|
|
7180
|
+
const output = (0, import_node_child_process.execSync)(command, EXEC_OPTIONS);
|
|
7181
|
+
return { success: true, output: output.toString() };
|
|
7182
|
+
} catch (error) {
|
|
7183
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
7184
|
+
return { success: false, output: message };
|
|
7185
|
+
}
|
|
7186
|
+
}
|
|
7187
|
+
function isBmadInstalled() {
|
|
7188
|
+
const result = execSafe("npx bmad-method status");
|
|
7189
|
+
return result.success && result.output.includes("Version:");
|
|
7190
|
+
}
|
|
7191
|
+
function isGrillMeInstalled(targetDir) {
|
|
7192
|
+
return fs3.existsSync(path3.join(targetDir, ".claude", "skills", "grill-me", "SKILL.md"));
|
|
7193
|
+
}
|
|
7194
|
+
function installBmadMethod() {
|
|
7195
|
+
if (isBmadInstalled()) {
|
|
7196
|
+
console.log("\u2139 BMAD Method \u5DF2\u5B58\u5728\uFF0C\u8DF3\u8FC7\u5B89\u88C5");
|
|
7197
|
+
return;
|
|
7198
|
+
}
|
|
7199
|
+
const result = execSafe("npx bmad-method install");
|
|
7200
|
+
if (result.success) {
|
|
7201
|
+
console.log("\u2714 BMAD Method \u5DF2\u5B89\u88C5");
|
|
7202
|
+
} else {
|
|
7203
|
+
console.log("\u26A0 BMAD Method \u5B89\u88C5\u5931\u8D25\uFF0C\u8BF7\u624B\u52A8\u6267\u884C npx bmad-method install");
|
|
7204
|
+
}
|
|
7205
|
+
}
|
|
7206
|
+
function installGrillMe(targetDir) {
|
|
7207
|
+
if (isGrillMeInstalled(targetDir)) {
|
|
7208
|
+
console.log("\u2139 grill-me \u5DF2\u5B58\u5728\uFF0C\u8DF3\u8FC7\u5B89\u88C5");
|
|
7209
|
+
return;
|
|
7210
|
+
}
|
|
7211
|
+
const skillDir = path3.join(targetDir, ".claude", "skills", "grill-me");
|
|
7212
|
+
fs3.mkdirSync(skillDir, { recursive: true });
|
|
7213
|
+
try {
|
|
7214
|
+
(0, import_node_child_process.execSync)(
|
|
7215
|
+
"curl -fsSL https://raw.githubusercontent.com/mattpocock/skills/main/grill-me/SKILL.md -o SKILL.md",
|
|
7216
|
+
{ ...EXEC_OPTIONS, cwd: skillDir }
|
|
7217
|
+
);
|
|
7218
|
+
console.log("\u2714 grill-me skill \u5DF2\u5B89\u88C5");
|
|
7219
|
+
} catch {
|
|
7220
|
+
console.log("\u26A0 grill-me \u5B89\u88C5\u5931\u8D25\uFF0C\u8BF7\u624B\u52A8\u5B89\u88C5 https://github.com/mattpocock/skills");
|
|
7221
|
+
}
|
|
7222
|
+
}
|
|
7223
|
+
function isPlaywrightInstalled(targetDir) {
|
|
7224
|
+
const result = execSafe("npx playwright install --dry-run");
|
|
7225
|
+
return result.success && !result.output.toLowerCase().includes("to install");
|
|
7226
|
+
}
|
|
7227
|
+
function installPlaywright(config, targetDir) {
|
|
7228
|
+
if (config["sweep.e2eFramework"] !== "playwright") return;
|
|
7229
|
+
if (isPlaywrightInstalled(targetDir)) {
|
|
7230
|
+
console.log("\u2139 Playwright \u6D4F\u89C8\u5668\u5DF2\u5B58\u5728\uFF0C\u8DF3\u8FC7\u5B89\u88C5");
|
|
7231
|
+
return;
|
|
7232
|
+
}
|
|
7233
|
+
const result = execSafe("npx playwright install");
|
|
7234
|
+
if (result.success) {
|
|
7235
|
+
console.log("\u2714 Playwright \u6D4F\u89C8\u5668\u5DF2\u5B89\u88C5");
|
|
7236
|
+
} else {
|
|
7237
|
+
console.log("\u26A0 Playwright \u6D4F\u89C8\u5668\u5B89\u88C5\u5931\u8D25\uFF0C\u8BF7\u624B\u52A8\u6267\u884C npx playwright install");
|
|
7238
|
+
}
|
|
7239
|
+
}
|
|
7240
|
+
function step9AutoInstallDeps(tools, config, targetDir) {
|
|
7241
|
+
if (tools.includes("tide")) {
|
|
7242
|
+
installBmadMethod();
|
|
7243
|
+
installGrillMe(targetDir);
|
|
7244
|
+
}
|
|
7245
|
+
if (tools.includes("sweep")) {
|
|
7246
|
+
installPlaywright(config, targetDir);
|
|
7247
|
+
}
|
|
7248
|
+
}
|
|
7249
|
+
|
|
7250
|
+
// src/merger/mcp.ts
|
|
7251
|
+
var fs4 = __toESM(require("node:fs"));
|
|
7114
7252
|
function mergeMcpServers(mcpPath, servers) {
|
|
7115
7253
|
let mcp = {};
|
|
7116
7254
|
try {
|
|
7117
|
-
if (
|
|
7118
|
-
const raw =
|
|
7255
|
+
if (fs4.existsSync(mcpPath)) {
|
|
7256
|
+
const raw = fs4.readFileSync(mcpPath, "utf-8");
|
|
7119
7257
|
mcp = JSON.parse(raw);
|
|
7120
7258
|
}
|
|
7121
7259
|
} catch {
|
|
@@ -7123,31 +7261,31 @@ function mergeMcpServers(mcpPath, servers) {
|
|
|
7123
7261
|
}
|
|
7124
7262
|
const existingServers = mcp.mcpServers || {};
|
|
7125
7263
|
mcp.mcpServers = deepMerge(existingServers, servers);
|
|
7126
|
-
|
|
7264
|
+
fs4.writeFileSync(mcpPath, JSON.stringify(mcp, null, 2) + "\n", "utf-8");
|
|
7127
7265
|
}
|
|
7128
7266
|
|
|
7129
7267
|
// src/merger/hooks.ts
|
|
7130
|
-
var
|
|
7268
|
+
var fs5 = __toESM(require("node:fs"));
|
|
7131
7269
|
function mergeHooks(hooksPath, hooks) {
|
|
7132
7270
|
let existing = {};
|
|
7133
7271
|
try {
|
|
7134
|
-
if (
|
|
7135
|
-
const raw =
|
|
7272
|
+
if (fs5.existsSync(hooksPath)) {
|
|
7273
|
+
const raw = fs5.readFileSync(hooksPath, "utf-8");
|
|
7136
7274
|
existing = JSON.parse(raw);
|
|
7137
7275
|
}
|
|
7138
7276
|
} catch {
|
|
7139
7277
|
existing = {};
|
|
7140
7278
|
}
|
|
7141
7279
|
const merged = deepMerge(existing, hooks);
|
|
7142
|
-
|
|
7280
|
+
fs5.writeFileSync(hooksPath, JSON.stringify(merged, null, 2) + "\n", "utf-8");
|
|
7143
7281
|
}
|
|
7144
7282
|
|
|
7145
7283
|
// src/wizard/mcp-env.ts
|
|
7146
|
-
var
|
|
7147
|
-
var
|
|
7284
|
+
var fs6 = __toESM(require("node:fs"));
|
|
7285
|
+
var path4 = __toESM(require("node:path"));
|
|
7148
7286
|
function parseEnvExampleFile(filePath) {
|
|
7149
|
-
if (!
|
|
7150
|
-
const content =
|
|
7287
|
+
if (!fs6.existsSync(filePath)) return [];
|
|
7288
|
+
const content = fs6.readFileSync(filePath, "utf-8");
|
|
7151
7289
|
const lines = content.split("\n");
|
|
7152
7290
|
const entries = [];
|
|
7153
7291
|
let lastComment = "";
|
|
@@ -7173,7 +7311,7 @@ function getMcpEnvStubs(selectedTools, examplesDir) {
|
|
|
7173
7311
|
if (!examplesDir) return [];
|
|
7174
7312
|
const result = [];
|
|
7175
7313
|
for (const tool of selectedTools) {
|
|
7176
|
-
const filePath =
|
|
7314
|
+
const filePath = path4.join(examplesDir, `${tool}.env-example`);
|
|
7177
7315
|
const entries = parseEnvExampleFile(filePath);
|
|
7178
7316
|
result.push(...entries);
|
|
7179
7317
|
}
|
|
@@ -7182,9 +7320,9 @@ function getMcpEnvStubs(selectedTools, examplesDir) {
|
|
|
7182
7320
|
function collectEnvSections(selectedTools, examplesDir, existingKeys) {
|
|
7183
7321
|
const sections = [];
|
|
7184
7322
|
for (const tool of selectedTools) {
|
|
7185
|
-
const filePath =
|
|
7186
|
-
if (!
|
|
7187
|
-
const content =
|
|
7323
|
+
const filePath = path4.join(examplesDir, `${tool}.env-example`);
|
|
7324
|
+
if (!fs6.existsSync(filePath)) continue;
|
|
7325
|
+
const content = fs6.readFileSync(filePath, "utf-8").trimEnd();
|
|
7188
7326
|
const entries = parseEnvExampleFile(filePath);
|
|
7189
7327
|
const allExist = entries.every((e) => existingKeys.has(e.key));
|
|
7190
7328
|
if (allExist) continue;
|
|
@@ -7220,7 +7358,7 @@ function filterExistingKeys(content, existingKeys) {
|
|
|
7220
7358
|
|
|
7221
7359
|
// src/wizard/wizard-flow.ts
|
|
7222
7360
|
var p4 = __toESM(require("@clack/prompts"));
|
|
7223
|
-
var
|
|
7361
|
+
var fs8 = __toESM(require("node:fs"));
|
|
7224
7362
|
|
|
7225
7363
|
// src/wizard/tool-select.ts
|
|
7226
7364
|
var p = __toESM(require("@clack/prompts"));
|
|
@@ -7612,7 +7750,7 @@ function parseFrontmatter(content) {
|
|
|
7612
7750
|
}
|
|
7613
7751
|
|
|
7614
7752
|
// src/template/registry.ts
|
|
7615
|
-
var
|
|
7753
|
+
var fs7 = __toESM(require("node:fs"));
|
|
7616
7754
|
function buildMcpCapabilities(mcpCapabilities, installedMcpServers, mcpTools) {
|
|
7617
7755
|
const installedSet = new Set(installedMcpServers);
|
|
7618
7756
|
const result = {};
|
|
@@ -7637,8 +7775,8 @@ function deriveVariableName(frontmatter) {
|
|
|
7637
7775
|
return "tide_capabilities";
|
|
7638
7776
|
}
|
|
7639
7777
|
function injectSkillCapabilities(tmplFilePath, baseVariables, installedMcpServers, mcpTools, variableName) {
|
|
7640
|
-
if (!
|
|
7641
|
-
const content =
|
|
7778
|
+
if (!fs7.existsSync(tmplFilePath)) return baseVariables;
|
|
7779
|
+
const content = fs7.readFileSync(tmplFilePath, "utf-8");
|
|
7642
7780
|
const fm = parseFrontmatter(content);
|
|
7643
7781
|
if (!fm) return baseVariables;
|
|
7644
7782
|
const mcpCapabilities = fm.mcpCapabilities;
|
|
@@ -7732,9 +7870,9 @@ function buildTemplateVariables(registry2, config, installedMcpTools = []) {
|
|
|
7732
7870
|
// src/wizard/wizard-flow.ts
|
|
7733
7871
|
function loadExistingConfigKeys(targetDir) {
|
|
7734
7872
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
7735
|
-
if (!
|
|
7873
|
+
if (!fs8.existsSync(settingsPath)) return /* @__PURE__ */ new Set();
|
|
7736
7874
|
try {
|
|
7737
|
-
const raw =
|
|
7875
|
+
const raw = fs8.readFileSync(settingsPath, "utf-8");
|
|
7738
7876
|
const config = JSON.parse(raw);
|
|
7739
7877
|
if (!config || Object.keys(config).length === 0) return /* @__PURE__ */ new Set();
|
|
7740
7878
|
const keys = /* @__PURE__ */ new Set();
|
|
@@ -7793,16 +7931,16 @@ async function runWizardFlow(reader, registry2, initialMcpValues, targetDir) {
|
|
|
7793
7931
|
}
|
|
7794
7932
|
|
|
7795
7933
|
// src/wizard/reconfigure.ts
|
|
7796
|
-
var
|
|
7797
|
-
var
|
|
7934
|
+
var fs9 = __toESM(require("node:fs"));
|
|
7935
|
+
var path5 = __toESM(require("node:path"));
|
|
7798
7936
|
function cleanInstalled(targetDir) {
|
|
7799
7937
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
7800
|
-
if (!
|
|
7938
|
+
if (!fs9.existsSync(settingsPath)) {
|
|
7801
7939
|
return;
|
|
7802
7940
|
}
|
|
7803
7941
|
let config;
|
|
7804
7942
|
try {
|
|
7805
|
-
config = JSON.parse(
|
|
7943
|
+
config = JSON.parse(fs9.readFileSync(settingsPath, "utf-8"));
|
|
7806
7944
|
} catch {
|
|
7807
7945
|
return;
|
|
7808
7946
|
}
|
|
@@ -7810,41 +7948,41 @@ function cleanInstalled(targetDir) {
|
|
|
7810
7948
|
const installedSkills = config.installedSkills;
|
|
7811
7949
|
if (installedSkills) {
|
|
7812
7950
|
for (const skillId of installedSkills) {
|
|
7813
|
-
const skillDir =
|
|
7814
|
-
if (
|
|
7815
|
-
|
|
7951
|
+
const skillDir = path5.join(targetDir, ".claude", "skills", skillId);
|
|
7952
|
+
if (fs9.existsSync(skillDir)) {
|
|
7953
|
+
fs9.rmSync(skillDir, { recursive: true, force: true });
|
|
7816
7954
|
}
|
|
7817
7955
|
}
|
|
7818
7956
|
}
|
|
7819
7957
|
const installedAgents = config.installedAgents;
|
|
7820
7958
|
if (installedAgents) {
|
|
7821
7959
|
for (const agent of installedAgents) {
|
|
7822
|
-
const agentDir =
|
|
7823
|
-
if (
|
|
7824
|
-
|
|
7960
|
+
const agentDir = path5.join(targetDir, ".claude", "agents", agent);
|
|
7961
|
+
if (fs9.existsSync(agentDir)) {
|
|
7962
|
+
fs9.rmSync(agentDir, { recursive: true, force: true });
|
|
7825
7963
|
}
|
|
7826
7964
|
}
|
|
7827
7965
|
}
|
|
7828
|
-
const hooksJson =
|
|
7829
|
-
if (
|
|
7830
|
-
|
|
7966
|
+
const hooksJson = path5.join(targetDir, ".claude", "hooks.json");
|
|
7967
|
+
if (fs9.existsSync(hooksJson)) {
|
|
7968
|
+
fs9.rmSync(hooksJson, { force: true });
|
|
7831
7969
|
}
|
|
7832
|
-
const hooksDir =
|
|
7833
|
-
if (
|
|
7834
|
-
|
|
7970
|
+
const hooksDir = path5.join(targetDir, ".claude", "hooks");
|
|
7971
|
+
if (fs9.existsSync(hooksDir)) {
|
|
7972
|
+
fs9.rmSync(hooksDir, { recursive: true, force: true });
|
|
7835
7973
|
}
|
|
7836
7974
|
const installedMcp = config.installedMcpServers;
|
|
7837
7975
|
if (installedMcp) {
|
|
7838
|
-
const mcpPath =
|
|
7839
|
-
if (
|
|
7976
|
+
const mcpPath = path5.join(targetDir, ".mcp.json");
|
|
7977
|
+
if (fs9.existsSync(mcpPath)) {
|
|
7840
7978
|
try {
|
|
7841
|
-
const mcp = JSON.parse(
|
|
7979
|
+
const mcp = JSON.parse(fs9.readFileSync(mcpPath, "utf-8"));
|
|
7842
7980
|
if (mcp.mcpServers) {
|
|
7843
7981
|
for (const serverName of installedMcp) {
|
|
7844
7982
|
delete mcp.mcpServers[`deepstorm-${serverName}`];
|
|
7845
7983
|
}
|
|
7846
7984
|
}
|
|
7847
|
-
|
|
7985
|
+
fs9.writeFileSync(mcpPath, JSON.stringify(mcp, null, 2) + "\n", "utf-8");
|
|
7848
7986
|
} catch {
|
|
7849
7987
|
}
|
|
7850
7988
|
}
|
|
@@ -7871,8 +8009,8 @@ function parseNonInteractiveArgs(toolsStr, setValues) {
|
|
|
7871
8009
|
}
|
|
7872
8010
|
|
|
7873
8011
|
// src/wizard/guide.ts
|
|
7874
|
-
var
|
|
7875
|
-
var
|
|
8012
|
+
var fs10 = __toESM(require("node:fs"));
|
|
8013
|
+
var path6 = __toESM(require("node:path"));
|
|
7876
8014
|
var import_prompts = require("@clack/prompts");
|
|
7877
8015
|
function printMcpEnvStatus(mcpTools, installedMcpServices, examplesDir, targetDir) {
|
|
7878
8016
|
const allMcp = [.../* @__PURE__ */ new Set([...mcpTools, ...installedMcpServices])];
|
|
@@ -7880,8 +8018,8 @@ function printMcpEnvStatus(mcpTools, installedMcpServices, examplesDir, targetDi
|
|
|
7880
8018
|
console.log("");
|
|
7881
8019
|
console.log(" \u73AF\u5883\u53D8\u91CF\u914D\u7F6E\u72B6\u6001\uFF1A");
|
|
7882
8020
|
for (const mcp of allMcp) {
|
|
7883
|
-
const filePath =
|
|
7884
|
-
if (!
|
|
8021
|
+
const filePath = path6.join(examplesDir, `${mcp}.env-example`);
|
|
8022
|
+
if (!fs10.existsSync(filePath)) {
|
|
7885
8023
|
console.log(` \u2139 ${mcp}: \u65E0\u9700\u73AF\u5883\u53D8\u91CF\u914D\u7F6E`);
|
|
7886
8024
|
continue;
|
|
7887
8025
|
}
|
|
@@ -7890,10 +8028,10 @@ function printMcpEnvStatus(mcpTools, installedMcpServices, examplesDir, targetDi
|
|
|
7890
8028
|
console.log(` \u2139 ${mcp}: \u65E0\u9700\u73AF\u5883\u53D8\u91CF\u914D\u7F6E`);
|
|
7891
8029
|
continue;
|
|
7892
8030
|
}
|
|
7893
|
-
const dotEnvPath =
|
|
8031
|
+
const dotEnvPath = path6.join(targetDir, ".env");
|
|
7894
8032
|
const dotEnvMap = /* @__PURE__ */ new Map();
|
|
7895
|
-
if (
|
|
7896
|
-
const content =
|
|
8033
|
+
if (fs10.existsSync(dotEnvPath)) {
|
|
8034
|
+
const content = fs10.readFileSync(dotEnvPath, "utf-8");
|
|
7897
8035
|
for (const line of content.split("\n")) {
|
|
7898
8036
|
const trimmed = line.trim();
|
|
7899
8037
|
if (trimmed.includes("=") && !trimmed.startsWith("#")) {
|
|
@@ -7906,7 +8044,7 @@ function printMcpEnvStatus(mcpTools, installedMcpServices, examplesDir, targetDi
|
|
|
7906
8044
|
}
|
|
7907
8045
|
}
|
|
7908
8046
|
}
|
|
7909
|
-
const envDefaultContent =
|
|
8047
|
+
const envDefaultContent = fs10.readFileSync(filePath, "utf-8");
|
|
7910
8048
|
const defaults = /* @__PURE__ */ new Map();
|
|
7911
8049
|
for (const line of envDefaultContent.split("\n")) {
|
|
7912
8050
|
const trimmed = line.trim();
|
|
@@ -7966,17 +8104,17 @@ async function printGuide(options) {
|
|
|
7966
8104
|
console.log(" \u4E0B\u4E00\u6B65\uFF1A");
|
|
7967
8105
|
console.log(" \u8FD0\u884C Claude Code\uFF0C\u8F93\u5165 /help \u67E5\u770B\u6240\u6709\u53EF\u7528\u7684 DeepStorm \u547D\u4EE4");
|
|
7968
8106
|
console.log("");
|
|
7969
|
-
const gitDir =
|
|
7970
|
-
if (
|
|
8107
|
+
const gitDir = path6.join(options.targetDir, ".git");
|
|
8108
|
+
if (fs10.existsSync(gitDir)) {
|
|
7971
8109
|
const shouldAdd = await (0, import_prompts.confirm)({
|
|
7972
8110
|
message: "\u662F\u5426\u5C06 .claude/ \u914D\u7F6E\u63D0\u4EA4\u5230 Git\uFF1F(.gitignore \u9700\u8981\u5FFD\u7565 .claude/)",
|
|
7973
8111
|
initialValue: false
|
|
7974
8112
|
});
|
|
7975
8113
|
if (!(0, import_prompts.isCancel)(shouldAdd) && shouldAdd) {
|
|
7976
|
-
const gitignorePath =
|
|
8114
|
+
const gitignorePath = path6.join(options.targetDir, ".gitignore");
|
|
7977
8115
|
let isIgnored = false;
|
|
7978
|
-
if (
|
|
7979
|
-
const gitignore =
|
|
8116
|
+
if (fs10.existsSync(gitignorePath)) {
|
|
8117
|
+
const gitignore = fs10.readFileSync(gitignorePath, "utf-8");
|
|
7980
8118
|
isIgnored = gitignore.split("\n").some((line) => {
|
|
7981
8119
|
const trimmed = line.trim();
|
|
7982
8120
|
return trimmed === ".claude" || trimmed === ".claude/" || trimmed === ".claude/**";
|
|
@@ -7995,25 +8133,25 @@ async function printGuide(options) {
|
|
|
7995
8133
|
}
|
|
7996
8134
|
|
|
7997
8135
|
// src/template/renderer.ts
|
|
7998
|
-
var
|
|
7999
|
-
var
|
|
8136
|
+
var fs12 = __toESM(require("node:fs"));
|
|
8137
|
+
var path8 = __toESM(require("node:path"));
|
|
8000
8138
|
var import_handlebars = __toESM(require_lib());
|
|
8001
8139
|
|
|
8002
8140
|
// src/utils/fs.ts
|
|
8003
|
-
var
|
|
8004
|
-
var
|
|
8141
|
+
var fs11 = __toESM(require("node:fs"));
|
|
8142
|
+
var path7 = __toESM(require("node:path"));
|
|
8005
8143
|
function ensureDir3(dir) {
|
|
8006
|
-
|
|
8144
|
+
fs11.mkdirSync(dir, { recursive: true });
|
|
8007
8145
|
}
|
|
8008
8146
|
function copyDir(src, dest) {
|
|
8009
|
-
|
|
8147
|
+
fs11.cpSync(src, dest, { recursive: true, force: true });
|
|
8010
8148
|
}
|
|
8011
8149
|
function removeDirContents(dir) {
|
|
8012
|
-
const entries =
|
|
8150
|
+
const entries = fs11.readdirSync(dir);
|
|
8013
8151
|
for (const entry of entries) {
|
|
8014
8152
|
if (entry === ".DS_Store") continue;
|
|
8015
|
-
const fullPath =
|
|
8016
|
-
|
|
8153
|
+
const fullPath = path7.join(dir, entry);
|
|
8154
|
+
fs11.rmSync(fullPath, { recursive: true, force: true });
|
|
8017
8155
|
}
|
|
8018
8156
|
}
|
|
8019
8157
|
|
|
@@ -8034,38 +8172,38 @@ function toNested(vars) {
|
|
|
8034
8172
|
}
|
|
8035
8173
|
var compiledCache = /* @__PURE__ */ new Map();
|
|
8036
8174
|
function renderTemplate(tmplPath, variables, outputPath) {
|
|
8037
|
-
if (!
|
|
8175
|
+
if (!fs12.existsSync(tmplPath)) {
|
|
8038
8176
|
throw new Error(`\u6A21\u677F\u6587\u4EF6\u4E0D\u5B58\u5728: ${tmplPath}`);
|
|
8039
8177
|
}
|
|
8040
8178
|
let templateFn = compiledCache.get(tmplPath);
|
|
8041
8179
|
if (!templateFn) {
|
|
8042
|
-
const source =
|
|
8180
|
+
const source = fs12.readFileSync(tmplPath, "utf-8");
|
|
8043
8181
|
templateFn = import_handlebars.default.compile(source, { noEscape: true });
|
|
8044
8182
|
compiledCache.set(tmplPath, templateFn);
|
|
8045
8183
|
}
|
|
8046
8184
|
const nestedVars = toNested(variables);
|
|
8047
8185
|
const content = templateFn(nestedVars);
|
|
8048
|
-
ensureDir3(
|
|
8049
|
-
|
|
8186
|
+
ensureDir3(path8.dirname(outputPath));
|
|
8187
|
+
fs12.writeFileSync(outputPath, content, "utf-8");
|
|
8050
8188
|
}
|
|
8051
8189
|
function copyVariants(sourceVariantsDir, selectedValue, targetDir, clean = false) {
|
|
8052
|
-
const variantDir =
|
|
8053
|
-
if (!
|
|
8190
|
+
const variantDir = path8.join(sourceVariantsDir, selectedValue);
|
|
8191
|
+
if (!fs12.existsSync(variantDir)) {
|
|
8054
8192
|
console.warn(
|
|
8055
8193
|
`[template] \u26A0 \u53D8\u4F53\u76EE\u5F55\u4E0D\u5B58\u5728: ${variantDir}\uFF08\u76F8\u5BF9\u4E8E ${sourceVariantsDir}\uFF09\uFF0C\u8DF3\u8FC7`
|
|
8056
8194
|
);
|
|
8057
8195
|
return;
|
|
8058
8196
|
}
|
|
8059
|
-
if (clean &&
|
|
8197
|
+
if (clean && fs12.existsSync(targetDir)) {
|
|
8060
8198
|
removeDirContents(targetDir);
|
|
8061
8199
|
}
|
|
8062
8200
|
ensureDir3(targetDir);
|
|
8063
|
-
const entries =
|
|
8201
|
+
const entries = fs12.readdirSync(variantDir);
|
|
8064
8202
|
for (const entry of entries) {
|
|
8065
8203
|
if (entry === ".DS_Store") continue;
|
|
8066
|
-
const src =
|
|
8067
|
-
const dest =
|
|
8068
|
-
|
|
8204
|
+
const src = path8.join(variantDir, entry);
|
|
8205
|
+
const dest = path8.join(targetDir, entry);
|
|
8206
|
+
fs12.cpSync(src, dest, { recursive: true, force: true });
|
|
8069
8207
|
}
|
|
8070
8208
|
}
|
|
8071
8209
|
|
|
@@ -8093,7 +8231,7 @@ async function runSetup(reader, targetDir, cliDir2, options, registry2) {
|
|
|
8093
8231
|
let selectedMcpTools = [];
|
|
8094
8232
|
let templateVariables = {};
|
|
8095
8233
|
let enabledMcpJsonServers = [];
|
|
8096
|
-
const examplesDir =
|
|
8234
|
+
const examplesDir = path9.join(cliDir2, "env-examples");
|
|
8097
8235
|
const installedSkillIds = [];
|
|
8098
8236
|
if (options.nonInteractive) {
|
|
8099
8237
|
const parsed = parseNonInteractiveArgs(options.tools, options.set);
|
|
@@ -8121,7 +8259,7 @@ async function runSetup(reader, targetDir, cliDir2, options, registry2) {
|
|
|
8121
8259
|
templateVariables = wizardResult.templateVariables;
|
|
8122
8260
|
}
|
|
8123
8261
|
if (selectedMcpTools.length > 0) {
|
|
8124
|
-
const mcpPath =
|
|
8262
|
+
const mcpPath = path9.join(targetDir, ".mcp.json");
|
|
8125
8263
|
const servers = loadMcpServerConfigs(cliDir2, selectedMcpTools);
|
|
8126
8264
|
mergeMcpServers(mcpPath, servers);
|
|
8127
8265
|
enabledMcpJsonServers = Object.keys(servers);
|
|
@@ -8133,13 +8271,13 @@ async function runSetup(reader, targetDir, cliDir2, options, registry2) {
|
|
|
8133
8271
|
installedSkillIds.push(...ids);
|
|
8134
8272
|
}
|
|
8135
8273
|
if (shouldInstallGlobalHooks(tools, reader)) {
|
|
8136
|
-
const hooksSrcDir =
|
|
8137
|
-
const destHooksJson =
|
|
8274
|
+
const hooksSrcDir = path9.join(cliDir2, "hooks");
|
|
8275
|
+
const destHooksJson = path9.join(targetDir, ".claude", "hooks.json");
|
|
8138
8276
|
for (const tool of tools) {
|
|
8139
|
-
const toolHooksJsonPath =
|
|
8140
|
-
if (
|
|
8141
|
-
ensureDir3(
|
|
8142
|
-
const incoming = JSON.parse(
|
|
8277
|
+
const toolHooksJsonPath = path9.join(hooksSrcDir, `${tool}-hooks.json`);
|
|
8278
|
+
if (fs13.existsSync(toolHooksJsonPath)) {
|
|
8279
|
+
ensureDir3(path9.join(targetDir, ".claude"));
|
|
8280
|
+
const incoming = JSON.parse(fs13.readFileSync(toolHooksJsonPath, "utf-8"));
|
|
8143
8281
|
mergeHooks(destHooksJson, incoming);
|
|
8144
8282
|
}
|
|
8145
8283
|
}
|
|
@@ -8165,7 +8303,7 @@ async function runSetup(reader, targetDir, cliDir2, options, registry2) {
|
|
|
8165
8303
|
const frontend = nestedConfig.reef?.frontend?.framework ?? void 0;
|
|
8166
8304
|
const backend = nestedConfig.reef?.backend?.language ?? void 0;
|
|
8167
8305
|
initContextMap(targetDir, { frontend, backend, projectName: "" });
|
|
8168
|
-
const claudeSettingsPath =
|
|
8306
|
+
const claudeSettingsPath = path9.join(targetDir, ".claude", "settings.json");
|
|
8169
8307
|
if (enabledMcpJsonServers.length > 0) {
|
|
8170
8308
|
writeEnabledMcpJsonServers(claudeSettingsPath, enabledMcpJsonServers);
|
|
8171
8309
|
const servers = loadMcpServerConfigs(cliDir2, selectedMcpTools);
|
|
@@ -8173,13 +8311,13 @@ async function runSetup(reader, targetDir, cliDir2, options, registry2) {
|
|
|
8173
8311
|
}
|
|
8174
8312
|
mergeSandboxDisabled(claudeSettingsPath);
|
|
8175
8313
|
if (selectedMcpTools.length > 0) {
|
|
8176
|
-
const envPath =
|
|
8314
|
+
const envPath = path9.join(targetDir, ".env");
|
|
8177
8315
|
const existingKeys = readExistingEnvKeys(envPath);
|
|
8178
8316
|
const sections = collectEnvSections(selectedMcpTools, examplesDir, existingKeys);
|
|
8179
8317
|
if (sections.length > 0) {
|
|
8180
8318
|
let existing = "";
|
|
8181
|
-
if (
|
|
8182
|
-
existing =
|
|
8319
|
+
if (fs13.existsSync(envPath)) {
|
|
8320
|
+
existing = fs13.readFileSync(envPath, "utf-8").trimEnd();
|
|
8183
8321
|
}
|
|
8184
8322
|
const deepstormHeader = [
|
|
8185
8323
|
"# \u2500\u2500 DeepStorm \u2500\u2500",
|
|
@@ -8194,7 +8332,7 @@ async function runSetup(reader, targetDir, cliDir2, options, registry2) {
|
|
|
8194
8332
|
""
|
|
8195
8333
|
].join("\n");
|
|
8196
8334
|
const content = existing ? existing + "\n\n" + deepstormHeader + sections.join("\n\n") + "\n" : deepstormHeader + sections.join("\n\n") + "\n";
|
|
8197
|
-
|
|
8335
|
+
fs13.writeFileSync(envPath, content, "utf-8");
|
|
8198
8336
|
console.log(`\u2714 \u5DF2\u751F\u6210 .env \u73AF\u5883\u53D8\u91CF\u6A21\u677F`);
|
|
8199
8337
|
}
|
|
8200
8338
|
}
|
|
@@ -8210,6 +8348,7 @@ async function runSetup(reader, targetDir, cliDir2, options, registry2) {
|
|
|
8210
8348
|
mcpTools: selectedMcpTools.length > 0 ? selectedMcpTools : void 0,
|
|
8211
8349
|
mcpEnvStubs: mcpEnvStubs.length > 0 ? mcpEnvStubs : void 0
|
|
8212
8350
|
});
|
|
8351
|
+
step9AutoInstallDeps(tools, config, targetDir);
|
|
8213
8352
|
}
|
|
8214
8353
|
function shouldSkipSkill(skill, config) {
|
|
8215
8354
|
if (!skill.configKey) return false;
|
|
@@ -8229,9 +8368,9 @@ function shouldSkipAgent(agentFile, config) {
|
|
|
8229
8368
|
}
|
|
8230
8369
|
function renderToolAssets(tool, reader, cliDir2, targetDir, templateVariables, config, registry2, installedMcpTools = [], targetSubDir = ".claude", skillIdFilter) {
|
|
8231
8370
|
const installedSkillIds = [];
|
|
8232
|
-
const targetSkillsDir = targetSubDir ?
|
|
8371
|
+
const targetSkillsDir = targetSubDir ? path9.join(targetDir, targetSubDir, "skills") : path9.join(targetDir, "skills");
|
|
8233
8372
|
const toolSkills = reader.getToolSkills(tool);
|
|
8234
|
-
const skillsDir =
|
|
8373
|
+
const skillsDir = path9.join(cliDir2, "skills");
|
|
8235
8374
|
for (const skill of toolSkills) {
|
|
8236
8375
|
const skillId = getSkillId(skill, registry2);
|
|
8237
8376
|
if (!skillId) continue;
|
|
@@ -8240,12 +8379,12 @@ function renderToolAssets(tool, reader, cliDir2, targetDir, templateVariables, c
|
|
|
8240
8379
|
console.log(` \u23ED ${skillId}\uFF1A\u4F9D\u8D56 ${skill.configKey} \u672A\u914D\u7F6E\uFF0C\u8DF3\u8FC7`);
|
|
8241
8380
|
continue;
|
|
8242
8381
|
}
|
|
8243
|
-
const srcDir =
|
|
8244
|
-
const targetDirPath =
|
|
8245
|
-
if (!
|
|
8246
|
-
const tmplPath =
|
|
8247
|
-
const variantsDir =
|
|
8248
|
-
if (
|
|
8382
|
+
const srcDir = path9.join(skillsDir, skillId);
|
|
8383
|
+
const targetDirPath = path9.join(targetSkillsDir, skillId);
|
|
8384
|
+
if (!fs13.existsSync(srcDir)) continue;
|
|
8385
|
+
const tmplPath = path9.join(srcDir, "SKILL.md.tmpl");
|
|
8386
|
+
const variantsDir = path9.join(srcDir, "variants");
|
|
8387
|
+
if (fs13.existsSync(tmplPath)) {
|
|
8249
8388
|
const enrichedVars = injectSkillCapabilities(
|
|
8250
8389
|
tmplPath,
|
|
8251
8390
|
templateVariables,
|
|
@@ -8256,7 +8395,7 @@ function renderToolAssets(tool, reader, cliDir2, targetDir, templateVariables, c
|
|
|
8256
8395
|
renderTemplate(
|
|
8257
8396
|
tmplPath,
|
|
8258
8397
|
enrichedVars,
|
|
8259
|
-
|
|
8398
|
+
path9.join(targetDirPath, "SKILL.md")
|
|
8260
8399
|
);
|
|
8261
8400
|
copyVariantsForConfig(variantsDir, config, targetDirPath, skill.configKey);
|
|
8262
8401
|
copyFragmentsForSkill(skillId, srcDir, config, registry2, targetDirPath);
|
|
@@ -8267,9 +8406,9 @@ function renderToolAssets(tool, reader, cliDir2, targetDir, templateVariables, c
|
|
|
8267
8406
|
installedSkillIds.push(skillId);
|
|
8268
8407
|
}
|
|
8269
8408
|
const toolAgents = reader.getToolAgents(tool);
|
|
8270
|
-
const agentsSrcDir =
|
|
8271
|
-
const targetAgentsDir = targetSubDir ?
|
|
8272
|
-
if (
|
|
8409
|
+
const agentsSrcDir = path9.join(cliDir2, "agents");
|
|
8410
|
+
const targetAgentsDir = targetSubDir ? path9.join(targetDir, targetSubDir, "agents") : path9.join(targetDir, "agents");
|
|
8411
|
+
if (fs13.existsSync(agentsSrcDir)) {
|
|
8273
8412
|
ensureDir3(targetAgentsDir);
|
|
8274
8413
|
for (const agentFile of toolAgents) {
|
|
8275
8414
|
if (shouldSkipAgent(agentFile, config)) {
|
|
@@ -8277,38 +8416,38 @@ function renderToolAssets(tool, reader, cliDir2, targetDir, templateVariables, c
|
|
|
8277
8416
|
console.log(` \u23ED ${base}\uFF1A\u4F9D\u8D56\u672A\u914D\u7F6E\uFF0C\u8DF3\u8FC7`);
|
|
8278
8417
|
continue;
|
|
8279
8418
|
}
|
|
8280
|
-
const srcPath =
|
|
8281
|
-
if (!
|
|
8282
|
-
const tmplSrcPath =
|
|
8283
|
-
if (
|
|
8419
|
+
const srcPath = path9.join(agentsSrcDir, agentFile);
|
|
8420
|
+
if (!fs13.existsSync(srcPath)) {
|
|
8421
|
+
const tmplSrcPath = path9.join(agentsSrcDir, agentFile.replace(/\.md$/, ".md.tmpl"));
|
|
8422
|
+
if (fs13.existsSync(tmplSrcPath)) {
|
|
8284
8423
|
const outputName = agentFile.replace(/\.tmpl$/, "");
|
|
8285
8424
|
renderTemplate(
|
|
8286
8425
|
tmplSrcPath,
|
|
8287
8426
|
templateVariables,
|
|
8288
|
-
|
|
8427
|
+
path9.join(targetAgentsDir, outputName)
|
|
8289
8428
|
);
|
|
8290
8429
|
}
|
|
8291
8430
|
continue;
|
|
8292
8431
|
}
|
|
8293
|
-
copyDir(srcPath,
|
|
8432
|
+
copyDir(srcPath, path9.join(targetAgentsDir, agentFile));
|
|
8294
8433
|
}
|
|
8295
8434
|
}
|
|
8296
8435
|
const toolHooks = reader.getToolHooks(tool);
|
|
8297
|
-
const hooksSrcDir =
|
|
8298
|
-
const targetHooksDir = targetSubDir ?
|
|
8299
|
-
if (
|
|
8436
|
+
const hooksSrcDir = path9.join(cliDir2, "hooks");
|
|
8437
|
+
const targetHooksDir = targetSubDir ? path9.join(targetDir, targetSubDir, "hooks") : path9.join(targetDir, "hooks");
|
|
8438
|
+
if (fs13.existsSync(hooksSrcDir)) {
|
|
8300
8439
|
ensureDir3(targetHooksDir);
|
|
8301
8440
|
for (const hookFile of toolHooks) {
|
|
8302
|
-
const srcPath =
|
|
8303
|
-
if (
|
|
8304
|
-
copyDir(srcPath,
|
|
8441
|
+
const srcPath = path9.join(hooksSrcDir, hookFile);
|
|
8442
|
+
if (fs13.existsSync(srcPath)) {
|
|
8443
|
+
copyDir(srcPath, path9.join(targetHooksDir, hookFile));
|
|
8305
8444
|
} else {
|
|
8306
8445
|
const tmplPath = srcPath + ".tmpl";
|
|
8307
|
-
if (
|
|
8446
|
+
if (fs13.existsSync(tmplPath)) {
|
|
8308
8447
|
renderTemplate(
|
|
8309
8448
|
tmplPath,
|
|
8310
8449
|
templateVariables,
|
|
8311
|
-
|
|
8450
|
+
path9.join(targetHooksDir, hookFile)
|
|
8312
8451
|
);
|
|
8313
8452
|
}
|
|
8314
8453
|
}
|
|
@@ -8317,9 +8456,9 @@ function renderToolAssets(tool, reader, cliDir2, targetDir, templateVariables, c
|
|
|
8317
8456
|
return installedSkillIds;
|
|
8318
8457
|
}
|
|
8319
8458
|
function installMcpSkills(tools, reader, cliDir2, targetDir, installedSkillIds, selectedMcpTools = []) {
|
|
8320
|
-
const mcpSkillsDir =
|
|
8321
|
-
const targetSkillsDir =
|
|
8322
|
-
if (!
|
|
8459
|
+
const mcpSkillsDir = path9.join(cliDir2, "mcp-skills");
|
|
8460
|
+
const targetSkillsDir = path9.join(targetDir, ".claude", "skills");
|
|
8461
|
+
if (!fs13.existsSync(mcpSkillsDir)) return;
|
|
8323
8462
|
if (selectedMcpTools.length === 0) {
|
|
8324
8463
|
console.log("\u23ED \u672A\u9009\u62E9 MCP \u670D\u52A1\uFF0C\u8DF3\u8FC7 MCP \u6280\u80FD\u5B89\u88C5");
|
|
8325
8464
|
return;
|
|
@@ -8336,9 +8475,9 @@ function installMcpSkills(tools, reader, cliDir2, targetDir, installedSkillIds,
|
|
|
8336
8475
|
}
|
|
8337
8476
|
let installed = 0;
|
|
8338
8477
|
for (const skillId of neededSkills) {
|
|
8339
|
-
const srcDir =
|
|
8340
|
-
if (
|
|
8341
|
-
const targetDirPath =
|
|
8478
|
+
const srcDir = path9.join(mcpSkillsDir, skillId);
|
|
8479
|
+
if (fs13.existsSync(srcDir)) {
|
|
8480
|
+
const targetDirPath = path9.join(targetSkillsDir, skillId);
|
|
8342
8481
|
copyDir(srcDir, targetDirPath);
|
|
8343
8482
|
installedSkillIds.push(skillId);
|
|
8344
8483
|
installed++;
|
|
@@ -8353,14 +8492,14 @@ function shouldInstallGlobalHooks(tools, reader) {
|
|
|
8353
8492
|
}
|
|
8354
8493
|
function buildUnifiedMcpCapabilities(cliDir2, installedMcpTools, mcpTools) {
|
|
8355
8494
|
const allDeclarations = {};
|
|
8356
|
-
const skillsDir =
|
|
8357
|
-
if (!
|
|
8358
|
-
const skillDirs =
|
|
8495
|
+
const skillsDir = path9.join(cliDir2, "skills");
|
|
8496
|
+
if (!fs13.existsSync(skillsDir)) return {};
|
|
8497
|
+
const skillDirs = fs13.readdirSync(skillsDir, { withFileTypes: true });
|
|
8359
8498
|
for (const entry of skillDirs) {
|
|
8360
8499
|
if (!entry.isDirectory()) continue;
|
|
8361
|
-
const tmplPath =
|
|
8362
|
-
if (!
|
|
8363
|
-
const content =
|
|
8500
|
+
const tmplPath = path9.join(skillsDir, entry.name, "SKILL.md.tmpl");
|
|
8501
|
+
if (!fs13.existsSync(tmplPath)) continue;
|
|
8502
|
+
const content = fs13.readFileSync(tmplPath, "utf-8");
|
|
8364
8503
|
const fm = parseFrontmatter(content);
|
|
8365
8504
|
if (!fm) continue;
|
|
8366
8505
|
const mcpCap = fm.mcpCapabilities;
|
|
@@ -8379,7 +8518,7 @@ function getSkillId(skill, registry2) {
|
|
|
8379
8518
|
return void 0;
|
|
8380
8519
|
}
|
|
8381
8520
|
function copyVariantsForConfig(variantsDir, config, targetDir, configKey) {
|
|
8382
|
-
if (!
|
|
8521
|
+
if (!fs13.existsSync(variantsDir)) return;
|
|
8383
8522
|
for (const [key, value] of Object.entries(config)) {
|
|
8384
8523
|
if (configKey && key !== configKey) continue;
|
|
8385
8524
|
if (value.includes(",")) continue;
|
|
@@ -8387,8 +8526,8 @@ function copyVariantsForConfig(variantsDir, config, targetDir, configKey) {
|
|
|
8387
8526
|
}
|
|
8388
8527
|
}
|
|
8389
8528
|
function copyFragmentsForSkill(skillId, srcDir, config, registry2, targetDir) {
|
|
8390
|
-
const fragmentsDir =
|
|
8391
|
-
if (!
|
|
8529
|
+
const fragmentsDir = path9.join(srcDir, "fragments");
|
|
8530
|
+
if (!fs13.existsSync(fragmentsDir)) return;
|
|
8392
8531
|
const selectedFragments = [];
|
|
8393
8532
|
for (const wizard of Object.values(registry2.wizards)) {
|
|
8394
8533
|
for (const question of wizard.questions) {
|
|
@@ -8396,43 +8535,43 @@ function copyFragmentsForSkill(skillId, srcDir, config, registry2, targetDir) {
|
|
|
8396
8535
|
}
|
|
8397
8536
|
}
|
|
8398
8537
|
if (selectedFragments.length === 0) return;
|
|
8399
|
-
const targetExamplesDir =
|
|
8538
|
+
const targetExamplesDir = path9.join(targetDir, "examples");
|
|
8400
8539
|
for (const { category, value } of selectedFragments) {
|
|
8401
|
-
const srcPath =
|
|
8402
|
-
if (!
|
|
8403
|
-
const srcQr =
|
|
8404
|
-
if (
|
|
8405
|
-
|
|
8406
|
-
}
|
|
8407
|
-
const srcExamples =
|
|
8408
|
-
if (
|
|
8409
|
-
const exampleFiles =
|
|
8540
|
+
const srcPath = path9.join(fragmentsDir, category, value);
|
|
8541
|
+
if (!fs13.existsSync(srcPath)) continue;
|
|
8542
|
+
const srcQr = path9.join(srcPath, "quick-reference.md");
|
|
8543
|
+
if (fs13.existsSync(srcQr)) {
|
|
8544
|
+
fs13.cpSync(srcQr, path9.join(targetDir, `${value}.md`), { force: true });
|
|
8545
|
+
}
|
|
8546
|
+
const srcExamples = path9.join(srcPath, "examples");
|
|
8547
|
+
if (fs13.existsSync(srcExamples)) {
|
|
8548
|
+
const exampleFiles = fs13.readdirSync(srcExamples);
|
|
8410
8549
|
for (const file of exampleFiles) {
|
|
8411
8550
|
if (file === ".DS_Store") continue;
|
|
8412
8551
|
ensureDir3(targetExamplesDir);
|
|
8413
|
-
|
|
8414
|
-
|
|
8415
|
-
|
|
8552
|
+
fs13.cpSync(
|
|
8553
|
+
path9.join(srcExamples, file),
|
|
8554
|
+
path9.join(targetExamplesDir, `${value}-${file}`),
|
|
8416
8555
|
{ force: true }
|
|
8417
8556
|
);
|
|
8418
8557
|
}
|
|
8419
8558
|
}
|
|
8420
|
-
const allFiles =
|
|
8559
|
+
const allFiles = fs13.readdirSync(srcPath);
|
|
8421
8560
|
for (const file of allFiles) {
|
|
8422
8561
|
if (file === ".DS_Store") continue;
|
|
8423
8562
|
if (file === "quick-reference.md") continue;
|
|
8424
8563
|
if (file === "examples") continue;
|
|
8425
8564
|
if (!file.endsWith(".md")) continue;
|
|
8426
|
-
|
|
8565
|
+
fs13.cpSync(path9.join(srcPath, file), path9.join(targetDir, file), { force: true });
|
|
8427
8566
|
}
|
|
8428
8567
|
}
|
|
8429
8568
|
}
|
|
8430
8569
|
function copyReferencesForSkill(srcDir, targetDir) {
|
|
8431
|
-
const referencesDir =
|
|
8432
|
-
if (
|
|
8433
|
-
const targetReferencesDir =
|
|
8570
|
+
const referencesDir = path9.join(srcDir, "references");
|
|
8571
|
+
if (fs13.existsSync(referencesDir)) {
|
|
8572
|
+
const targetReferencesDir = path9.join(targetDir, "references");
|
|
8434
8573
|
ensureDir3(targetReferencesDir);
|
|
8435
|
-
|
|
8574
|
+
fs13.cpSync(referencesDir, targetReferencesDir, { recursive: true, force: true });
|
|
8436
8575
|
}
|
|
8437
8576
|
}
|
|
8438
8577
|
function collectFragmentsFromQuestion(question, config, selectedFragments) {
|
|
@@ -8458,15 +8597,15 @@ function collectFragmentsFromQuestion(question, config, selectedFragments) {
|
|
|
8458
8597
|
}
|
|
8459
8598
|
}
|
|
8460
8599
|
function loadMcpServerConfigs(cliDir2, selectedTools) {
|
|
8461
|
-
const mcpDir =
|
|
8462
|
-
if (!
|
|
8600
|
+
const mcpDir = path9.join(cliDir2, "mcp");
|
|
8601
|
+
if (!fs13.existsSync(mcpDir)) return {};
|
|
8463
8602
|
const servers = {};
|
|
8464
8603
|
function collectJsonFiles(dir) {
|
|
8465
8604
|
const results = [];
|
|
8466
|
-
for (const entry of
|
|
8467
|
-
const fullPath =
|
|
8605
|
+
for (const entry of fs13.readdirSync(dir)) {
|
|
8606
|
+
const fullPath = path9.join(dir, entry);
|
|
8468
8607
|
if (entry === ".DS_Store") continue;
|
|
8469
|
-
if (
|
|
8608
|
+
if (fs13.statSync(fullPath).isDirectory()) {
|
|
8470
8609
|
results.push(...collectJsonFiles(fullPath));
|
|
8471
8610
|
} else if (entry.endsWith(".json")) {
|
|
8472
8611
|
results.push(fullPath);
|
|
@@ -8477,7 +8616,7 @@ function loadMcpServerConfigs(cliDir2, selectedTools) {
|
|
|
8477
8616
|
const jsonFiles = collectJsonFiles(mcpDir);
|
|
8478
8617
|
for (const jsonPath of jsonFiles) {
|
|
8479
8618
|
try {
|
|
8480
|
-
const data = JSON.parse(
|
|
8619
|
+
const data = JSON.parse(fs13.readFileSync(jsonPath, "utf-8"));
|
|
8481
8620
|
if (!data.name || !selectedTools.includes(data.name)) continue;
|
|
8482
8621
|
if (!data.mcpServers || typeof data.mcpServers !== "object") continue;
|
|
8483
8622
|
for (const [serverName, serverConfig] of Object.entries(data.mcpServers)) {
|
|
@@ -8523,37 +8662,37 @@ function writeEnabledMcpJsonServers(settingsPath, serverNames) {
|
|
|
8523
8662
|
if (serverNames.length === 0) return;
|
|
8524
8663
|
let settings = {};
|
|
8525
8664
|
try {
|
|
8526
|
-
if (
|
|
8527
|
-
const raw =
|
|
8665
|
+
if (fs13.existsSync(settingsPath)) {
|
|
8666
|
+
const raw = fs13.readFileSync(settingsPath, "utf-8");
|
|
8528
8667
|
settings = JSON.parse(raw);
|
|
8529
8668
|
}
|
|
8530
8669
|
} catch {
|
|
8531
8670
|
settings = {};
|
|
8532
8671
|
}
|
|
8533
8672
|
settings.enabledMcpjsonServers = serverNames;
|
|
8534
|
-
ensureDir3(
|
|
8535
|
-
|
|
8673
|
+
ensureDir3(path9.dirname(settingsPath));
|
|
8674
|
+
fs13.writeFileSync(settingsPath, JSON.stringify(settings, null, 2) + "\n", "utf-8");
|
|
8536
8675
|
}
|
|
8537
8676
|
function mergeSandboxDisabled(settingsPath) {
|
|
8538
8677
|
let settings = {};
|
|
8539
8678
|
try {
|
|
8540
|
-
if (
|
|
8541
|
-
const raw =
|
|
8679
|
+
if (fs13.existsSync(settingsPath)) {
|
|
8680
|
+
const raw = fs13.readFileSync(settingsPath, "utf-8");
|
|
8542
8681
|
settings = JSON.parse(raw);
|
|
8543
8682
|
}
|
|
8544
8683
|
} catch {
|
|
8545
8684
|
settings = {};
|
|
8546
8685
|
}
|
|
8547
8686
|
settings.sandbox = { enabled: false };
|
|
8548
|
-
ensureDir3(
|
|
8549
|
-
|
|
8687
|
+
ensureDir3(path9.dirname(settingsPath));
|
|
8688
|
+
fs13.writeFileSync(settingsPath, JSON.stringify(settings, null, 2) + "\n", "utf-8");
|
|
8550
8689
|
}
|
|
8551
8690
|
function mergeSettingsMcpServers(settingsPath, servers) {
|
|
8552
8691
|
if (!servers || Object.keys(servers).length === 0) return;
|
|
8553
8692
|
let settings = {};
|
|
8554
8693
|
try {
|
|
8555
|
-
if (
|
|
8556
|
-
const raw =
|
|
8694
|
+
if (fs13.existsSync(settingsPath)) {
|
|
8695
|
+
const raw = fs13.readFileSync(settingsPath, "utf-8");
|
|
8557
8696
|
settings = JSON.parse(raw);
|
|
8558
8697
|
}
|
|
8559
8698
|
} catch {
|
|
@@ -8561,13 +8700,13 @@ function mergeSettingsMcpServers(settingsPath, servers) {
|
|
|
8561
8700
|
}
|
|
8562
8701
|
const existingServers = settings.mcpServers || {};
|
|
8563
8702
|
settings.mcpServers = deepMerge(existingServers, servers);
|
|
8564
|
-
ensureDir3(
|
|
8565
|
-
|
|
8703
|
+
ensureDir3(path9.dirname(settingsPath));
|
|
8704
|
+
fs13.writeFileSync(settingsPath, JSON.stringify(settings, null, 2) + "\n", "utf-8");
|
|
8566
8705
|
}
|
|
8567
8706
|
function readExistingEnvKeys(envPath) {
|
|
8568
8707
|
const keys = /* @__PURE__ */ new Set();
|
|
8569
|
-
if (!
|
|
8570
|
-
for (const line of
|
|
8708
|
+
if (!fs13.existsSync(envPath)) return keys;
|
|
8709
|
+
for (const line of fs13.readFileSync(envPath, "utf-8").split("\n")) {
|
|
8571
8710
|
const trimmed = line.trim();
|
|
8572
8711
|
if (!trimmed || trimmed.startsWith("#")) continue;
|
|
8573
8712
|
const eqIdx = trimmed.indexOf("=");
|
|
@@ -8582,22 +8721,22 @@ function readExistingEnvKeys(envPath) {
|
|
|
8582
8721
|
}
|
|
8583
8722
|
|
|
8584
8723
|
// src/commands/plugin-build.ts
|
|
8585
|
-
var
|
|
8586
|
-
var
|
|
8724
|
+
var fs15 = __toESM(require("node:fs"));
|
|
8725
|
+
var path11 = __toESM(require("node:path"));
|
|
8587
8726
|
|
|
8588
8727
|
// src/engine/plugin-builder.ts
|
|
8589
|
-
var
|
|
8590
|
-
var
|
|
8728
|
+
var fs14 = __toESM(require("node:fs"));
|
|
8729
|
+
var path10 = __toESM(require("node:path"));
|
|
8591
8730
|
async function buildPlugin(config) {
|
|
8592
8731
|
const { marketplaceName, tools, selectedMcpTools, cliDir: cliDir2, targetDir } = config;
|
|
8593
|
-
const outputDir =
|
|
8594
|
-
if (
|
|
8595
|
-
|
|
8732
|
+
const outputDir = path10.join(targetDir, ".deepstorm");
|
|
8733
|
+
if (fs14.existsSync(outputDir)) {
|
|
8734
|
+
fs14.rmSync(outputDir, { recursive: true, force: true });
|
|
8596
8735
|
}
|
|
8597
|
-
|
|
8736
|
+
fs14.mkdirSync(outputDir, { recursive: true });
|
|
8598
8737
|
const rootPkgMeta = readRootPackageJson(targetDir);
|
|
8599
|
-
const claudePluginDir =
|
|
8600
|
-
|
|
8738
|
+
const claudePluginDir = path10.join(outputDir, ".claude-plugin");
|
|
8739
|
+
fs14.mkdirSync(claudePluginDir, { recursive: true });
|
|
8601
8740
|
const pluginJson = {
|
|
8602
8741
|
name: "deepstorm",
|
|
8603
8742
|
description: rootPkgMeta.description,
|
|
@@ -8606,7 +8745,7 @@ async function buildPlugin(config) {
|
|
|
8606
8745
|
license: "MIT",
|
|
8607
8746
|
keywords: ["deepstorm", "ai", "software-engineering", ...tools]
|
|
8608
8747
|
};
|
|
8609
|
-
|
|
8748
|
+
fs14.writeFileSync(path10.join(claudePluginDir, "plugin.json"), JSON.stringify(pluginJson, null, 2), "utf-8");
|
|
8610
8749
|
const marketplaceJson = {
|
|
8611
8750
|
name: marketplaceName,
|
|
8612
8751
|
description: "DeepStorm Claude Code \u63D2\u4EF6",
|
|
@@ -8620,11 +8759,11 @@ async function buildPlugin(config) {
|
|
|
8620
8759
|
}
|
|
8621
8760
|
]
|
|
8622
8761
|
};
|
|
8623
|
-
|
|
8762
|
+
fs14.writeFileSync(path10.join(claudePluginDir, "marketplace.json"), JSON.stringify(marketplaceJson, null, 2), "utf-8");
|
|
8624
8763
|
const settingsJson = {
|
|
8625
8764
|
enabledMcpjsonServers: selectedMcpTools
|
|
8626
8765
|
};
|
|
8627
|
-
|
|
8766
|
+
fs14.writeFileSync(path10.join(outputDir, "settings.json"), JSON.stringify(settingsJson, null, 2), "utf-8");
|
|
8628
8767
|
if (selectedMcpTools.length > 0) {
|
|
8629
8768
|
const mcpServers = {};
|
|
8630
8769
|
for (const mcpName of selectedMcpTools) {
|
|
@@ -8634,46 +8773,48 @@ async function buildPlugin(config) {
|
|
|
8634
8773
|
}
|
|
8635
8774
|
}
|
|
8636
8775
|
if (Object.keys(mcpServers).length > 0) {
|
|
8637
|
-
|
|
8638
|
-
|
|
8776
|
+
fs14.writeFileSync(
|
|
8777
|
+
path10.join(outputDir, ".mcp.json"),
|
|
8639
8778
|
JSON.stringify({ mcpServers }, null, 2) + "\n",
|
|
8640
8779
|
"utf-8"
|
|
8641
8780
|
);
|
|
8642
8781
|
}
|
|
8643
8782
|
}
|
|
8644
8783
|
if (selectedMcpTools.length > 0) {
|
|
8645
|
-
const envPath =
|
|
8646
|
-
const
|
|
8647
|
-
|
|
8648
|
-
"# \u590D\u5236\u6B64\u6587\u4EF6\u4E3A .env \u5E76\u586B\u5199\u5B9E\u9645\u503C",
|
|
8649
|
-
""
|
|
8650
|
-
];
|
|
8784
|
+
const envPath = path10.join(targetDir, ".env");
|
|
8785
|
+
const header = "# \u2500\u2500 DeepStorm Plugin MCP \u73AF\u5883\u53D8\u91CF \u2500\u2500\n\n";
|
|
8786
|
+
const sections = [];
|
|
8651
8787
|
for (const mcpName of selectedMcpTools) {
|
|
8652
|
-
const envExampleFile =
|
|
8653
|
-
if (
|
|
8654
|
-
const content =
|
|
8655
|
-
|
|
8656
|
-
|
|
8657
|
-
envLines.push("");
|
|
8788
|
+
const envExampleFile = path10.join(cliDir2, "env-examples", `${mcpName}.env-example`);
|
|
8789
|
+
if (fs14.existsSync(envExampleFile)) {
|
|
8790
|
+
const content = fs14.readFileSync(envExampleFile, "utf-8");
|
|
8791
|
+
sections.push(`# ${mcpName}`);
|
|
8792
|
+
sections.push(content);
|
|
8658
8793
|
}
|
|
8659
8794
|
}
|
|
8660
|
-
|
|
8795
|
+
const newContent = header + sections.join("\n") + "\n";
|
|
8796
|
+
if (fs14.existsSync(envPath)) {
|
|
8797
|
+
const existing = fs14.readFileSync(envPath, "utf-8").trimEnd();
|
|
8798
|
+
fs14.writeFileSync(envPath, existing + "\n\n" + newContent, "utf-8");
|
|
8799
|
+
} else {
|
|
8800
|
+
fs14.writeFileSync(envPath, newContent, "utf-8");
|
|
8801
|
+
}
|
|
8661
8802
|
}
|
|
8662
8803
|
const readmeContent = generateReadme2(marketplaceName, tools, selectedMcpTools, rootPkgMeta.version);
|
|
8663
|
-
|
|
8804
|
+
fs14.writeFileSync(path10.join(outputDir, "README.md"), readmeContent, "utf-8");
|
|
8664
8805
|
const changelogContent = `# Changelog
|
|
8665
8806
|
|
|
8666
8807
|
## v${rootPkgMeta.version}
|
|
8667
8808
|
|
|
8668
8809
|
- \u9996\u6B21\u6784\u5EFA DeepStorm Plugin
|
|
8669
8810
|
`;
|
|
8670
|
-
|
|
8811
|
+
fs14.writeFileSync(path10.join(outputDir, "CHANGELOG.md"), changelogContent, "utf-8");
|
|
8671
8812
|
return outputDir;
|
|
8672
8813
|
}
|
|
8673
8814
|
function readRootPackageJson(targetDir) {
|
|
8674
|
-
const pkgPath =
|
|
8815
|
+
const pkgPath = path10.join(targetDir, "package.json");
|
|
8675
8816
|
try {
|
|
8676
|
-
const pkg = JSON.parse(
|
|
8817
|
+
const pkg = JSON.parse(fs14.readFileSync(pkgPath, "utf-8"));
|
|
8677
8818
|
return {
|
|
8678
8819
|
version: pkg.version || "0.1.0",
|
|
8679
8820
|
description: pkg.description || "DeepStorm \u2014 Spec \u9A71\u52A8\u7684 AI \u534F\u540C\u8F6F\u4EF6\u5DE5\u7A0B\u5B9E\u8DF5\u5DE5\u5177\u96C6"
|
|
@@ -8713,7 +8854,7 @@ function generateReadme2(marketplaceName, tools, selectedMcpTools, version) {
|
|
|
8713
8854
|
"",
|
|
8714
8855
|
"## \u73AF\u5883\u53D8\u91CF",
|
|
8715
8856
|
"",
|
|
8716
|
-
"\
|
|
8857
|
+
"\u7F16\u8F91 .env \u6587\u4EF6\uFF0C\u586B\u5199\u5BF9\u5E94\u7684 API Token \u540E\u91CD\u542F Claude Code \u4F1A\u8BDD\u3002",
|
|
8717
8858
|
"",
|
|
8718
8859
|
"## \u5F00\u53D1",
|
|
8719
8860
|
"",
|
|
@@ -8725,16 +8866,16 @@ function generateReadme2(marketplaceName, tools, selectedMcpTools, version) {
|
|
|
8725
8866
|
return lines.join("\n");
|
|
8726
8867
|
}
|
|
8727
8868
|
function readMcpServerConfig(cliDir2, mcpName) {
|
|
8728
|
-
const mcpDir =
|
|
8729
|
-
if (!
|
|
8730
|
-
const entries =
|
|
8869
|
+
const mcpDir = path10.join(cliDir2, "mcp");
|
|
8870
|
+
if (!fs14.existsSync(mcpDir)) return null;
|
|
8871
|
+
const entries = fs14.readdirSync(mcpDir, { withFileTypes: true });
|
|
8731
8872
|
for (const entry of entries) {
|
|
8732
8873
|
if (!entry.isDirectory()) continue;
|
|
8733
|
-
const domainDir =
|
|
8734
|
-
const files =
|
|
8874
|
+
const domainDir = path10.join(mcpDir, entry.name);
|
|
8875
|
+
const files = fs14.readdirSync(domainDir).filter((f) => f.endsWith(".json"));
|
|
8735
8876
|
for (const file of files) {
|
|
8736
8877
|
try {
|
|
8737
|
-
const content = JSON.parse(
|
|
8878
|
+
const content = JSON.parse(fs14.readFileSync(path10.join(domainDir, file), "utf-8"));
|
|
8738
8879
|
if (content.name === mcpName && content.mcpServers) {
|
|
8739
8880
|
const servers = content.mcpServers;
|
|
8740
8881
|
const keys = Object.keys(servers);
|
|
@@ -8830,27 +8971,27 @@ function registerPluginBuildCommand(program2, registry2) {
|
|
|
8830
8971
|
});
|
|
8831
8972
|
}
|
|
8832
8973
|
function updatePluginJsonHooks(pluginDir) {
|
|
8833
|
-
const hooksDir =
|
|
8834
|
-
const pluginJsonPath =
|
|
8835
|
-
if (!
|
|
8974
|
+
const hooksDir = path11.join(pluginDir, "hooks");
|
|
8975
|
+
const pluginJsonPath = path11.join(pluginDir, ".claude-plugin", "plugin.json");
|
|
8976
|
+
if (!fs15.existsSync(hooksDir) || !fs15.existsSync(pluginJsonPath)) return;
|
|
8836
8977
|
try {
|
|
8837
|
-
const pluginJson = JSON.parse(
|
|
8978
|
+
const pluginJson = JSON.parse(fs15.readFileSync(pluginJsonPath, "utf-8"));
|
|
8838
8979
|
pluginJson.hooks = "./hooks/deepstorm-hooks.json";
|
|
8839
|
-
|
|
8980
|
+
fs15.writeFileSync(pluginJsonPath, JSON.stringify(pluginJson, null, 2) + "\n", "utf-8");
|
|
8840
8981
|
console.log("\u2714 plugin.json \u5DF2\u6DFB\u52A0 hooks \u58F0\u660E");
|
|
8841
8982
|
} catch {
|
|
8842
8983
|
}
|
|
8843
8984
|
}
|
|
8844
8985
|
function ensureGitIgnore(targetDir) {
|
|
8845
|
-
const gitIgnorePath =
|
|
8986
|
+
const gitIgnorePath = path11.join(targetDir, ".gitignore");
|
|
8846
8987
|
const line = ".deepstorm/";
|
|
8847
8988
|
try {
|
|
8848
|
-
if (
|
|
8849
|
-
const content =
|
|
8989
|
+
if (fs15.existsSync(gitIgnorePath)) {
|
|
8990
|
+
const content = fs15.readFileSync(gitIgnorePath, "utf-8");
|
|
8850
8991
|
if (content.includes(line)) return;
|
|
8851
|
-
|
|
8992
|
+
fs15.writeFileSync(gitIgnorePath, content.trimEnd() + "\n" + line + "\n", "utf-8");
|
|
8852
8993
|
} else {
|
|
8853
|
-
|
|
8994
|
+
fs15.writeFileSync(gitIgnorePath, line + "\n", "utf-8");
|
|
8854
8995
|
}
|
|
8855
8996
|
console.log("\u2714 .gitignore \u5DF2\u6DFB\u52A0 .deepstorm/ \u5FFD\u7565\u89C4\u5219");
|
|
8856
8997
|
} catch {
|
|
@@ -8858,14 +8999,14 @@ function ensureGitIgnore(targetDir) {
|
|
|
8858
8999
|
}
|
|
8859
9000
|
function mergePluginHooks(tools, reader, pluginDir, packagesDir) {
|
|
8860
9001
|
if (!tools.some((tool) => reader.getToolHooks(tool).length > 0)) return;
|
|
8861
|
-
const pkgsDir = packagesDir ??
|
|
8862
|
-
const pluginHooksDir =
|
|
8863
|
-
const destHooksJson =
|
|
9002
|
+
const pkgsDir = packagesDir ?? path11.resolve(process.cwd(), "packages");
|
|
9003
|
+
const pluginHooksDir = path11.join(pluginDir, "hooks");
|
|
9004
|
+
const destHooksJson = path11.join(pluginHooksDir, "deepstorm-hooks.json");
|
|
8864
9005
|
for (const tool of tools) {
|
|
8865
|
-
const srcPath =
|
|
8866
|
-
if (
|
|
8867
|
-
|
|
8868
|
-
const incoming = JSON.parse(
|
|
9006
|
+
const srcPath = path11.join(pkgsDir, tool, "hooks", "hooks.json");
|
|
9007
|
+
if (fs15.existsSync(srcPath)) {
|
|
9008
|
+
fs15.mkdirSync(pluginHooksDir, { recursive: true });
|
|
9009
|
+
const incoming = JSON.parse(fs15.readFileSync(srcPath, "utf-8"));
|
|
8869
9010
|
mergeHooks(destHooksJson, incoming);
|
|
8870
9011
|
}
|
|
8871
9012
|
}
|
|
@@ -8886,24 +9027,24 @@ function viewConfig(targetDir) {
|
|
|
8886
9027
|
}
|
|
8887
9028
|
|
|
8888
9029
|
// src/commands/config-set.ts
|
|
8889
|
-
var
|
|
8890
|
-
var
|
|
9030
|
+
var fs17 = __toESM(require("node:fs"));
|
|
9031
|
+
var path13 = __toESM(require("node:path"));
|
|
8891
9032
|
var p6 = __toESM(require("@clack/prompts"));
|
|
8892
9033
|
|
|
8893
9034
|
// src/utils/config-schema.ts
|
|
8894
|
-
var
|
|
8895
|
-
var
|
|
9035
|
+
var fs16 = __toESM(require("node:fs"));
|
|
9036
|
+
var path12 = __toESM(require("node:path"));
|
|
8896
9037
|
function loadValidConfigKeys() {
|
|
8897
9038
|
const candidates = [
|
|
8898
|
-
|
|
8899
|
-
|
|
8900
|
-
|
|
8901
|
-
|
|
9039
|
+
path12.resolve(__dirname, "config-schema.json"),
|
|
9040
|
+
path12.resolve(__dirname, "..", "config-schema.json"),
|
|
9041
|
+
path12.resolve(process.cwd(), "config-schema.json"),
|
|
9042
|
+
path12.resolve(process.cwd(), "packages", "cli", "config-schema.json")
|
|
8902
9043
|
];
|
|
8903
9044
|
for (const schemaPath of candidates) {
|
|
8904
9045
|
try {
|
|
8905
|
-
if (!
|
|
8906
|
-
const schema = JSON.parse(
|
|
9046
|
+
if (!fs16.existsSync(schemaPath)) continue;
|
|
9047
|
+
const schema = JSON.parse(fs16.readFileSync(schemaPath, "utf-8"));
|
|
8907
9048
|
const keys = /* @__PURE__ */ new Set();
|
|
8908
9049
|
collectLeafPaths(schema.properties, "", keys);
|
|
8909
9050
|
return keys;
|
|
@@ -8941,9 +9082,9 @@ async function setConfigValue(targetDir, key, value, registry2) {
|
|
|
8941
9082
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
8942
9083
|
readDeepStormConfig(targetDir);
|
|
8943
9084
|
let config = {};
|
|
8944
|
-
if (
|
|
9085
|
+
if (fs17.existsSync(settingsPath)) {
|
|
8945
9086
|
try {
|
|
8946
|
-
config = JSON.parse(
|
|
9087
|
+
config = JSON.parse(fs17.readFileSync(settingsPath, "utf-8"));
|
|
8947
9088
|
} catch {
|
|
8948
9089
|
config = {};
|
|
8949
9090
|
}
|
|
@@ -8977,7 +9118,7 @@ async function setConfigValue(targetDir, key, value, registry2) {
|
|
|
8977
9118
|
writePointer = writePointer[parts[i]];
|
|
8978
9119
|
}
|
|
8979
9120
|
writePointer[parts[parts.length - 1]] = value;
|
|
8980
|
-
|
|
9121
|
+
fs17.writeFileSync(settingsPath, JSON.stringify(config, null, 2) + "\n", "utf-8");
|
|
8981
9122
|
console.log(`\u2714 ${key} \u5DF2\u66F4\u65B0\u4E3A ${value}`);
|
|
8982
9123
|
const affected = findAffectedTemplates(registry2, key);
|
|
8983
9124
|
if (affected.length === 0) {
|
|
@@ -9015,8 +9156,8 @@ async function setConfigValue(targetDir, key, value, registry2) {
|
|
|
9015
9156
|
const templateVariables = buildTemplateVariables(registry2, fullConfig, installedMcpServers);
|
|
9016
9157
|
let renderCount = 0;
|
|
9017
9158
|
for (const tmplRelPath of affected) {
|
|
9018
|
-
const tmplPath =
|
|
9019
|
-
if (!
|
|
9159
|
+
const tmplPath = path13.join(cliDir, tmplRelPath);
|
|
9160
|
+
if (!fs17.existsSync(tmplPath)) {
|
|
9020
9161
|
console.warn(` \u26A0 \u6A21\u677F\u6587\u4EF6\u4E0D\u5B58\u5728: ${tmplRelPath}\uFF0C\u8DF3\u8FC7`);
|
|
9021
9162
|
continue;
|
|
9022
9163
|
}
|
|
@@ -9024,12 +9165,12 @@ async function setConfigValue(targetDir, key, value, registry2) {
|
|
|
9024
9165
|
const assetType = pathParts[0];
|
|
9025
9166
|
const assetName = pathParts[1];
|
|
9026
9167
|
const outputFile = pathParts[pathParts.length - 1].replace(/\.tmpl$/, "");
|
|
9027
|
-
const targetDirPath =
|
|
9168
|
+
const targetDirPath = path13.join(targetDir, ".claude", assetType, assetName);
|
|
9028
9169
|
ensureDir3(targetDirPath);
|
|
9029
|
-
const outputPath =
|
|
9170
|
+
const outputPath = path13.join(targetDirPath, outputFile);
|
|
9030
9171
|
renderTemplate(tmplPath, templateVariables, outputPath);
|
|
9031
|
-
const variantsDir =
|
|
9032
|
-
if (
|
|
9172
|
+
const variantsDir = path13.join(cliDir, assetType, assetName, "variants");
|
|
9173
|
+
if (fs17.existsSync(variantsDir)) {
|
|
9033
9174
|
copyVariants(variantsDir, value, targetDirPath, true);
|
|
9034
9175
|
}
|
|
9035
9176
|
renderCount++;
|
|
@@ -9039,43 +9180,43 @@ async function setConfigValue(targetDir, key, value, registry2) {
|
|
|
9039
9180
|
}
|
|
9040
9181
|
|
|
9041
9182
|
// src/commands/config-reset.ts
|
|
9042
|
-
var
|
|
9043
|
-
var
|
|
9183
|
+
var fs18 = __toESM(require("node:fs"));
|
|
9184
|
+
var path14 = __toESM(require("node:path"));
|
|
9044
9185
|
function resetConfig(targetDir) {
|
|
9045
|
-
const settingsPath =
|
|
9046
|
-
if (!
|
|
9186
|
+
const settingsPath = path14.join(targetDir, ".deepstorm", "settings.json");
|
|
9187
|
+
if (!fs18.existsSync(settingsPath)) return;
|
|
9047
9188
|
try {
|
|
9048
|
-
|
|
9189
|
+
fs18.unlinkSync(settingsPath);
|
|
9049
9190
|
console.log("\u2714 \u5DF2\u6E05\u9664 DeepStorm \u914D\u7F6E");
|
|
9050
9191
|
} catch {
|
|
9051
9192
|
}
|
|
9052
9193
|
}
|
|
9053
9194
|
|
|
9054
9195
|
// src/commands/config-refresh.ts
|
|
9055
|
-
var
|
|
9056
|
-
var
|
|
9196
|
+
var fs19 = __toESM(require("node:fs"));
|
|
9197
|
+
var path15 = __toESM(require("node:path"));
|
|
9057
9198
|
function refreshConfig(cliDir2, targetDir, registry2) {
|
|
9058
9199
|
const result = { refreshed: [], errors: [] };
|
|
9059
9200
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
9060
|
-
if (!
|
|
9201
|
+
if (!fs19.existsSync(settingsPath)) {
|
|
9061
9202
|
return result;
|
|
9062
9203
|
}
|
|
9063
9204
|
readDeepStormConfig(targetDir);
|
|
9064
9205
|
let config;
|
|
9065
9206
|
try {
|
|
9066
|
-
config = JSON.parse(
|
|
9207
|
+
config = JSON.parse(fs19.readFileSync(settingsPath, "utf-8"));
|
|
9067
9208
|
} catch {
|
|
9068
9209
|
return result;
|
|
9069
9210
|
}
|
|
9070
9211
|
const installedSkills = config.installedSkills ?? [];
|
|
9071
9212
|
const installedMcpServers = config.installedMcpServers ?? [];
|
|
9072
|
-
const targetDotClaudeDir =
|
|
9213
|
+
const targetDotClaudeDir = path15.join(targetDir, ".claude");
|
|
9073
9214
|
if (installedSkills.length === 0) return result;
|
|
9074
9215
|
for (const skillId of installedSkills) {
|
|
9075
|
-
const tmplPath =
|
|
9076
|
-
if (!
|
|
9077
|
-
const targetSkillDir =
|
|
9078
|
-
const outputPath =
|
|
9216
|
+
const tmplPath = path15.join(cliDir2, "skills", skillId, "SKILL.md.tmpl");
|
|
9217
|
+
if (!fs19.existsSync(tmplPath)) continue;
|
|
9218
|
+
const targetSkillDir = path15.join(targetDotClaudeDir, "skills", skillId);
|
|
9219
|
+
const outputPath = path15.join(targetSkillDir, "SKILL.md");
|
|
9079
9220
|
try {
|
|
9080
9221
|
const enrichedVars = injectSkillCapabilities(
|
|
9081
9222
|
tmplPath,
|
|
@@ -9083,7 +9224,7 @@ function refreshConfig(cliDir2, targetDir, registry2) {
|
|
|
9083
9224
|
installedMcpServers,
|
|
9084
9225
|
registry2.mcpTools ?? {}
|
|
9085
9226
|
);
|
|
9086
|
-
|
|
9227
|
+
fs19.mkdirSync(targetSkillDir, { recursive: true });
|
|
9087
9228
|
renderTemplate(tmplPath, enrichedVars, outputPath);
|
|
9088
9229
|
result.refreshed.push(skillId);
|
|
9089
9230
|
} catch (err) {
|
|
@@ -9100,14 +9241,14 @@ function refreshConfig(cliDir2, targetDir, registry2) {
|
|
|
9100
9241
|
}
|
|
9101
9242
|
function buildUnifiedMcpCapabilities2(cliDir2, installedMcpTools, mcpTools) {
|
|
9102
9243
|
const allDeclarations = {};
|
|
9103
|
-
const skillsDir =
|
|
9104
|
-
if (!
|
|
9105
|
-
const skillDirs =
|
|
9244
|
+
const skillsDir = path15.join(cliDir2, "skills");
|
|
9245
|
+
if (!fs19.existsSync(skillsDir)) return {};
|
|
9246
|
+
const skillDirs = fs19.readdirSync(skillsDir, { withFileTypes: true });
|
|
9106
9247
|
for (const entry of skillDirs) {
|
|
9107
9248
|
if (!entry.isDirectory()) continue;
|
|
9108
|
-
const tmplPath =
|
|
9109
|
-
if (!
|
|
9110
|
-
const content =
|
|
9249
|
+
const tmplPath = path15.join(skillsDir, entry.name, "SKILL.md.tmpl");
|
|
9250
|
+
if (!fs19.existsSync(tmplPath)) continue;
|
|
9251
|
+
const content = fs19.readFileSync(tmplPath, "utf-8");
|
|
9111
9252
|
const fm = parseFrontmatter(content);
|
|
9112
9253
|
if (!fm) continue;
|
|
9113
9254
|
const mcpCap = fm.mcpCapabilities;
|
|
@@ -9190,17 +9331,17 @@ function listTemplates(registry2, tool) {
|
|
|
9190
9331
|
}
|
|
9191
9332
|
|
|
9192
9333
|
// src/commands/template-init.ts
|
|
9193
|
-
var
|
|
9194
|
-
var
|
|
9334
|
+
var fs20 = __toESM(require("node:fs"));
|
|
9335
|
+
var path16 = __toESM(require("node:path"));
|
|
9195
9336
|
var import_prompts3 = require("@clack/prompts");
|
|
9196
9337
|
async function initTemplate(cliDir2, targetDir, skillId) {
|
|
9197
|
-
const srcDir =
|
|
9198
|
-
const destDir =
|
|
9199
|
-
if (!
|
|
9338
|
+
const srcDir = path16.join(cliDir2, "skills", skillId);
|
|
9339
|
+
const destDir = path16.join(targetDir, ".deepstorm", "templates", skillId);
|
|
9340
|
+
if (!fs20.existsSync(srcDir)) {
|
|
9200
9341
|
console.log(`\u6A21\u677F\u4E0D\u5B58\u5728\uFF1A${skillId}`);
|
|
9201
9342
|
return;
|
|
9202
9343
|
}
|
|
9203
|
-
if (
|
|
9344
|
+
if (fs20.existsSync(destDir)) {
|
|
9204
9345
|
const shouldOverwrite = await (0, import_prompts3.confirm)({
|
|
9205
9346
|
message: `\u6A21\u677F ${skillId} \u5DF2\u5B58\u5728\uFF0C\u662F\u5426\u8986\u76D6\uFF1F`,
|
|
9206
9347
|
initialValue: false
|
|
@@ -9209,21 +9350,21 @@ async function initTemplate(cliDir2, targetDir, skillId) {
|
|
|
9209
9350
|
console.log("\u5DF2\u53D6\u6D88");
|
|
9210
9351
|
return;
|
|
9211
9352
|
}
|
|
9212
|
-
|
|
9353
|
+
fs20.rmSync(destDir, { recursive: true, force: true });
|
|
9213
9354
|
}
|
|
9214
|
-
ensureDir3(
|
|
9355
|
+
ensureDir3(path16.dirname(destDir));
|
|
9215
9356
|
copyDir(srcDir, destDir);
|
|
9216
9357
|
console.log(`\u2714 \u6A21\u677F\u5DF2\u5BFC\u51FA\u5230 .deepstorm/templates/${skillId}/`);
|
|
9217
9358
|
console.log(` \u4FEE\u6539\u5B8C\u6210\u540E\u8FD0\u884C deepstorm template apply ${skillId} \u5E94\u7528\u66F4\u6539`);
|
|
9218
9359
|
}
|
|
9219
9360
|
|
|
9220
9361
|
// src/commands/template-apply.ts
|
|
9221
|
-
var
|
|
9222
|
-
var
|
|
9362
|
+
var fs21 = __toESM(require("node:fs"));
|
|
9363
|
+
var path17 = __toESM(require("node:path"));
|
|
9223
9364
|
function applyTemplate(targetDir, skillId) {
|
|
9224
|
-
const srcDir =
|
|
9225
|
-
const destDir =
|
|
9226
|
-
if (!
|
|
9365
|
+
const srcDir = path17.join(targetDir, ".deepstorm", "templates", skillId);
|
|
9366
|
+
const destDir = path17.join(targetDir, ".claude", "skills", skillId);
|
|
9367
|
+
if (!fs21.existsSync(srcDir)) {
|
|
9227
9368
|
console.log(`\u6A21\u677F\u4E0D\u5B58\u5728\uFF0C\u8BF7\u5148\u8FD0\u884C deepstorm template init ${skillId}`);
|
|
9228
9369
|
return;
|
|
9229
9370
|
}
|
|
@@ -9257,21 +9398,21 @@ function registerTemplateCommand(program2, registry2) {
|
|
|
9257
9398
|
}
|
|
9258
9399
|
|
|
9259
9400
|
// src/commands/update.ts
|
|
9260
|
-
var
|
|
9261
|
-
var
|
|
9401
|
+
var fs24 = __toESM(require("node:fs"));
|
|
9402
|
+
var import_node_child_process2 = require("node:child_process");
|
|
9262
9403
|
|
|
9263
9404
|
// src/utils/version.ts
|
|
9264
|
-
var
|
|
9265
|
-
var
|
|
9405
|
+
var fs22 = __toESM(require("node:fs"));
|
|
9406
|
+
var path18 = __toESM(require("node:path"));
|
|
9266
9407
|
function getCliVersion() {
|
|
9267
9408
|
try {
|
|
9268
9409
|
const paths = [
|
|
9269
|
-
|
|
9270
|
-
|
|
9410
|
+
path18.resolve(__dirname, "package.json"),
|
|
9411
|
+
path18.resolve(__dirname, "..", "package.json")
|
|
9271
9412
|
];
|
|
9272
9413
|
for (const pkgPath of paths) {
|
|
9273
|
-
if (
|
|
9274
|
-
const pkg = JSON.parse(
|
|
9414
|
+
if (fs22.existsSync(pkgPath)) {
|
|
9415
|
+
const pkg = JSON.parse(fs22.readFileSync(pkgPath, "utf-8"));
|
|
9275
9416
|
return pkg.version || "0.0.0";
|
|
9276
9417
|
}
|
|
9277
9418
|
}
|
|
@@ -9282,14 +9423,14 @@ function getCliVersion() {
|
|
|
9282
9423
|
}
|
|
9283
9424
|
|
|
9284
9425
|
// src/commands/template-upgrade.ts
|
|
9285
|
-
var
|
|
9286
|
-
var
|
|
9426
|
+
var fs23 = __toESM(require("node:fs"));
|
|
9427
|
+
var path19 = __toESM(require("node:path"));
|
|
9287
9428
|
var crypto = __toESM(require("node:crypto"));
|
|
9288
9429
|
var CHECKSUM_FILE = "deepstorm-checksums.json";
|
|
9289
9430
|
function computeFileChecksum(filePath) {
|
|
9290
9431
|
try {
|
|
9291
|
-
if (!
|
|
9292
|
-
const content =
|
|
9432
|
+
if (!fs23.existsSync(filePath)) return null;
|
|
9433
|
+
const content = fs23.readFileSync(filePath);
|
|
9293
9434
|
return crypto.createHash("sha256").update(content).digest("hex");
|
|
9294
9435
|
} catch {
|
|
9295
9436
|
return null;
|
|
@@ -9297,15 +9438,15 @@ function computeFileChecksum(filePath) {
|
|
|
9297
9438
|
}
|
|
9298
9439
|
function computeDirChecksums(dirPath, relativeTo = dirPath) {
|
|
9299
9440
|
const result = {};
|
|
9300
|
-
if (!
|
|
9441
|
+
if (!fs23.existsSync(dirPath)) return result;
|
|
9301
9442
|
function walk(current) {
|
|
9302
|
-
for (const entry of
|
|
9303
|
-
const fullPath =
|
|
9443
|
+
for (const entry of fs23.readdirSync(current, { withFileTypes: true })) {
|
|
9444
|
+
const fullPath = path19.join(current, entry.name);
|
|
9304
9445
|
if (entry.name === ".DS_Store") continue;
|
|
9305
9446
|
if (entry.isDirectory()) {
|
|
9306
9447
|
walk(fullPath);
|
|
9307
9448
|
} else if (entry.isFile()) {
|
|
9308
|
-
const relPath =
|
|
9449
|
+
const relPath = path19.relative(relativeTo, fullPath);
|
|
9309
9450
|
const checksum = computeFileChecksum(fullPath);
|
|
9310
9451
|
if (checksum) result[relPath] = checksum;
|
|
9311
9452
|
}
|
|
@@ -9315,32 +9456,32 @@ function computeDirChecksums(dirPath, relativeTo = dirPath) {
|
|
|
9315
9456
|
return result;
|
|
9316
9457
|
}
|
|
9317
9458
|
function loadChecksums(targetDir) {
|
|
9318
|
-
const filePath =
|
|
9459
|
+
const filePath = path19.join(targetDir, ".claude", CHECKSUM_FILE);
|
|
9319
9460
|
try {
|
|
9320
|
-
return JSON.parse(
|
|
9461
|
+
return JSON.parse(fs23.readFileSync(filePath, "utf-8"));
|
|
9321
9462
|
} catch {
|
|
9322
9463
|
return {};
|
|
9323
9464
|
}
|
|
9324
9465
|
}
|
|
9325
9466
|
function saveChecksums(targetDir, checksums) {
|
|
9326
|
-
const dir =
|
|
9467
|
+
const dir = path19.join(targetDir, ".claude");
|
|
9327
9468
|
ensureDir3(dir);
|
|
9328
|
-
|
|
9329
|
-
|
|
9469
|
+
fs23.writeFileSync(
|
|
9470
|
+
path19.join(dir, CHECKSUM_FILE),
|
|
9330
9471
|
JSON.stringify(checksums, null, 2) + "\n",
|
|
9331
9472
|
"utf-8"
|
|
9332
9473
|
);
|
|
9333
9474
|
}
|
|
9334
9475
|
function backupFile(filePath) {
|
|
9335
9476
|
try {
|
|
9336
|
-
if (!
|
|
9337
|
-
const dir =
|
|
9338
|
-
const ext =
|
|
9339
|
-
const base =
|
|
9477
|
+
if (!fs23.existsSync(filePath)) return null;
|
|
9478
|
+
const dir = path19.dirname(filePath);
|
|
9479
|
+
const ext = path19.extname(filePath);
|
|
9480
|
+
const base = path19.basename(filePath, ext);
|
|
9340
9481
|
const timestamp = Date.now();
|
|
9341
9482
|
const bakName = `${base}.${timestamp}.bak`;
|
|
9342
|
-
const bakPath =
|
|
9343
|
-
|
|
9483
|
+
const bakPath = path19.join(dir, bakName);
|
|
9484
|
+
fs23.cpSync(filePath, bakPath, { force: true });
|
|
9344
9485
|
return bakName;
|
|
9345
9486
|
} catch {
|
|
9346
9487
|
return null;
|
|
@@ -9361,19 +9502,19 @@ function backupModifiedAssets(targetDir, skillIds, toolNames, registry2) {
|
|
|
9361
9502
|
const stored = loadChecksums(targetDir);
|
|
9362
9503
|
const backedUp = [];
|
|
9363
9504
|
for (const skillId of skillIds) {
|
|
9364
|
-
const skillDir =
|
|
9365
|
-
if (!
|
|
9505
|
+
const skillDir = path19.join(targetDir, ".claude", "skills", skillId);
|
|
9506
|
+
if (!fs23.existsSync(skillDir)) continue;
|
|
9366
9507
|
const checksums = computeDirChecksums(skillDir);
|
|
9367
9508
|
for (const [relPath] of Object.entries(checksums)) {
|
|
9368
9509
|
const key = `skills/${skillId}/${relPath}`;
|
|
9369
|
-
checkAndBackup(key,
|
|
9510
|
+
checkAndBackup(key, path19.join(skillDir, relPath), stored, backedUp);
|
|
9370
9511
|
}
|
|
9371
9512
|
}
|
|
9372
9513
|
const reader = new RegistryReader(registry2);
|
|
9373
9514
|
for (const tool of toolNames) {
|
|
9374
9515
|
const agents = reader.getToolAgents(tool);
|
|
9375
9516
|
for (const agentFile of agents) {
|
|
9376
|
-
const filePath =
|
|
9517
|
+
const filePath = path19.join(targetDir, ".claude", "agents", agentFile.replace(/\.tmpl$/, ""));
|
|
9377
9518
|
const key = `agents/${agentFile.replace(/\.tmpl$/, "")}`;
|
|
9378
9519
|
checkAndBackup(key, filePath, stored, backedUp);
|
|
9379
9520
|
}
|
|
@@ -9381,7 +9522,7 @@ function backupModifiedAssets(targetDir, skillIds, toolNames, registry2) {
|
|
|
9381
9522
|
for (const tool of toolNames) {
|
|
9382
9523
|
const hooks = reader.getToolHooks(tool);
|
|
9383
9524
|
for (const hookFile of hooks) {
|
|
9384
|
-
const filePath =
|
|
9525
|
+
const filePath = path19.join(targetDir, ".claude", "hooks", hookFile);
|
|
9385
9526
|
const key = `hooks/${hookFile}`;
|
|
9386
9527
|
checkAndBackup(key, filePath, stored, backedUp);
|
|
9387
9528
|
}
|
|
@@ -9392,7 +9533,7 @@ function storeNewChecksums(targetDir, skillIds, toolNames, registry2) {
|
|
|
9392
9533
|
const newChecksums = {};
|
|
9393
9534
|
const reader = new RegistryReader(registry2);
|
|
9394
9535
|
for (const skillId of skillIds) {
|
|
9395
|
-
const skillDir =
|
|
9536
|
+
const skillDir = path19.join(targetDir, ".claude", "skills", skillId);
|
|
9396
9537
|
const checksums = computeDirChecksums(skillDir);
|
|
9397
9538
|
for (const [relPath, checksum] of Object.entries(checksums)) {
|
|
9398
9539
|
newChecksums[`skills/${skillId}/${relPath}`] = checksum;
|
|
@@ -9402,7 +9543,7 @@ function storeNewChecksums(targetDir, skillIds, toolNames, registry2) {
|
|
|
9402
9543
|
const agents = reader.getToolAgents(tool);
|
|
9403
9544
|
for (const agentFile of agents) {
|
|
9404
9545
|
const installedName = agentFile.replace(/\.tmpl$/, "");
|
|
9405
|
-
const filePath =
|
|
9546
|
+
const filePath = path19.join(targetDir, ".claude", "agents", installedName);
|
|
9406
9547
|
const chk = computeFileChecksum(filePath);
|
|
9407
9548
|
if (chk) newChecksums[`agents/${installedName}`] = chk;
|
|
9408
9549
|
}
|
|
@@ -9410,7 +9551,7 @@ function storeNewChecksums(targetDir, skillIds, toolNames, registry2) {
|
|
|
9410
9551
|
for (const tool of toolNames) {
|
|
9411
9552
|
const hooks = reader.getToolHooks(tool);
|
|
9412
9553
|
for (const hookFile of hooks) {
|
|
9413
|
-
const filePath =
|
|
9554
|
+
const filePath = path19.join(targetDir, ".claude", "hooks", hookFile);
|
|
9414
9555
|
const chk = computeFileChecksum(filePath);
|
|
9415
9556
|
if (chk) newChecksums[`hooks/${hookFile}`] = chk;
|
|
9416
9557
|
}
|
|
@@ -9443,7 +9584,7 @@ function detectToolsFromConfig(config, registry2) {
|
|
|
9443
9584
|
function readSettingsConfig(targetDir) {
|
|
9444
9585
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
9445
9586
|
try {
|
|
9446
|
-
const raw =
|
|
9587
|
+
const raw = fs23.readFileSync(settingsPath, "utf-8");
|
|
9447
9588
|
const config = JSON.parse(raw);
|
|
9448
9589
|
const metaKeys = /* @__PURE__ */ new Set([
|
|
9449
9590
|
"installedSkills",
|
|
@@ -9473,22 +9614,22 @@ function flattenNestedConfig(obj, prefix, result, skipKeys) {
|
|
|
9473
9614
|
}
|
|
9474
9615
|
}
|
|
9475
9616
|
function loadRegistryFromCliDir(cliDir2) {
|
|
9476
|
-
const registryPath =
|
|
9617
|
+
const registryPath = path19.join(cliDir2, "registry.json");
|
|
9477
9618
|
try {
|
|
9478
|
-
const raw =
|
|
9619
|
+
const raw = fs23.readFileSync(registryPath, "utf-8");
|
|
9479
9620
|
return JSON.parse(raw);
|
|
9480
9621
|
} catch {
|
|
9481
9622
|
return null;
|
|
9482
9623
|
}
|
|
9483
9624
|
}
|
|
9484
9625
|
function mergeToolHooksJson(toolNames, cliDir2, targetDir) {
|
|
9485
|
-
const hooksSrcDir =
|
|
9486
|
-
const destHooksJson =
|
|
9626
|
+
const hooksSrcDir = path19.join(cliDir2, "hooks");
|
|
9627
|
+
const destHooksJson = path19.join(targetDir, ".claude", "hooks.json");
|
|
9487
9628
|
for (const tool of toolNames) {
|
|
9488
|
-
const toolHooksJsonPath =
|
|
9489
|
-
if (
|
|
9490
|
-
ensureDir3(
|
|
9491
|
-
const incoming = JSON.parse(
|
|
9629
|
+
const toolHooksJsonPath = path19.join(hooksSrcDir, `${tool}-hooks.json`);
|
|
9630
|
+
if (fs23.existsSync(toolHooksJsonPath)) {
|
|
9631
|
+
ensureDir3(path19.join(targetDir, ".claude"));
|
|
9632
|
+
const incoming = JSON.parse(fs23.readFileSync(toolHooksJsonPath, "utf-8"));
|
|
9492
9633
|
mergeHooks(destHooksJson, incoming);
|
|
9493
9634
|
}
|
|
9494
9635
|
}
|
|
@@ -9606,8 +9747,8 @@ function readLocalRegistryFile(url) {
|
|
|
9606
9747
|
filePath = filePath.slice(7);
|
|
9607
9748
|
}
|
|
9608
9749
|
try {
|
|
9609
|
-
if (
|
|
9610
|
-
return JSON.parse(
|
|
9750
|
+
if (fs24.existsSync(filePath)) {
|
|
9751
|
+
return JSON.parse(fs24.readFileSync(filePath, "utf-8"));
|
|
9611
9752
|
}
|
|
9612
9753
|
} catch {
|
|
9613
9754
|
}
|
|
@@ -9676,7 +9817,7 @@ async function updateCLI(fetchFn) {
|
|
|
9676
9817
|
console.log("\u2192 \u6B63\u5728\u81EA\u52A8\u66F4\u65B0...");
|
|
9677
9818
|
const updateCmd = process.env.DEEPSTORM_UPDATE_CMD || "npm install -g @deepstorm/cli@latest";
|
|
9678
9819
|
try {
|
|
9679
|
-
(0,
|
|
9820
|
+
(0, import_node_child_process2.execSync)(updateCmd, { stdio: "inherit" });
|
|
9680
9821
|
console.log(`
|
|
9681
9822
|
\u2714 \u5DF2\u66F4\u65B0\u81F3 v${result.latest}`);
|
|
9682
9823
|
} catch {
|
|
@@ -9691,7 +9832,7 @@ async function updateCLI(fetchFn) {
|
|
|
9691
9832
|
function getInstalledSkillIds(targetDir) {
|
|
9692
9833
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
9693
9834
|
try {
|
|
9694
|
-
const raw =
|
|
9835
|
+
const raw = fs24.readFileSync(settingsPath, "utf-8");
|
|
9695
9836
|
const config = JSON.parse(raw);
|
|
9696
9837
|
return config.installedSkills ?? [];
|
|
9697
9838
|
} catch {
|
|
@@ -9718,12 +9859,12 @@ function registerPilotCommands(program2) {
|
|
|
9718
9859
|
}
|
|
9719
9860
|
|
|
9720
9861
|
// src/commands/doctor.ts
|
|
9721
|
-
var
|
|
9722
|
-
var
|
|
9862
|
+
var fs25 = __toESM(require("node:fs"));
|
|
9863
|
+
var path20 = __toESM(require("node:path"));
|
|
9723
9864
|
function getInstalledSkills(targetDir) {
|
|
9724
9865
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
9725
9866
|
try {
|
|
9726
|
-
const settings = JSON.parse(
|
|
9867
|
+
const settings = JSON.parse(fs25.readFileSync(settingsPath, "utf-8"));
|
|
9727
9868
|
return settings.installedSkills || [];
|
|
9728
9869
|
} catch {
|
|
9729
9870
|
return [];
|
|
@@ -9740,7 +9881,7 @@ function runDoctor(targetDir) {
|
|
|
9740
9881
|
message: `v${version}\uFF08\u8FD0\u884C deepstorm update --check \u68C0\u67E5\u6700\u65B0\u7248\u672C\uFF09`
|
|
9741
9882
|
});
|
|
9742
9883
|
let hasDeepStorm = false;
|
|
9743
|
-
if (!
|
|
9884
|
+
if (!fs25.existsSync(settingsPath)) {
|
|
9744
9885
|
checks.push({
|
|
9745
9886
|
name: "\u914D\u7F6E\u6587\u4EF6",
|
|
9746
9887
|
status: "warn",
|
|
@@ -9748,7 +9889,7 @@ function runDoctor(targetDir) {
|
|
|
9748
9889
|
});
|
|
9749
9890
|
} else {
|
|
9750
9891
|
try {
|
|
9751
|
-
const config = JSON.parse(
|
|
9892
|
+
const config = JSON.parse(fs25.readFileSync(settingsPath, "utf-8"));
|
|
9752
9893
|
if (config && Object.keys(config).length > 0) {
|
|
9753
9894
|
hasDeepStorm = true;
|
|
9754
9895
|
checks.push({
|
|
@@ -9771,20 +9912,20 @@ function runDoctor(targetDir) {
|
|
|
9771
9912
|
});
|
|
9772
9913
|
}
|
|
9773
9914
|
}
|
|
9774
|
-
const skillsDir =
|
|
9775
|
-
if (
|
|
9776
|
-
const skillDirs =
|
|
9777
|
-
(n) =>
|
|
9915
|
+
const skillsDir = path20.join(targetDir, ".claude", "skills");
|
|
9916
|
+
if (fs25.existsSync(skillsDir)) {
|
|
9917
|
+
const skillDirs = fs25.readdirSync(skillsDir).filter(
|
|
9918
|
+
(n) => fs25.statSync(path20.join(skillsDir, n)).isDirectory()
|
|
9778
9919
|
);
|
|
9779
9920
|
let validCount = 0;
|
|
9780
9921
|
let invalidCount = 0;
|
|
9781
9922
|
for (const skillName of skillDirs) {
|
|
9782
|
-
const skillMd =
|
|
9783
|
-
if (!
|
|
9923
|
+
const skillMd = path20.join(skillsDir, skillName, "SKILL.md");
|
|
9924
|
+
if (!fs25.existsSync(skillMd)) {
|
|
9784
9925
|
invalidCount++;
|
|
9785
9926
|
continue;
|
|
9786
9927
|
}
|
|
9787
|
-
const content =
|
|
9928
|
+
const content = fs25.readFileSync(skillMd, "utf-8");
|
|
9788
9929
|
const frontmatter = parseFrontmatter(content);
|
|
9789
9930
|
if (frontmatter && frontmatter.name) {
|
|
9790
9931
|
validCount++;
|
|
@@ -9814,7 +9955,7 @@ function runDoctor(targetDir) {
|
|
|
9814
9955
|
const installedSkills = getInstalledSkills(targetDir);
|
|
9815
9956
|
const missingSkills = [];
|
|
9816
9957
|
for (const skillId of installedSkills) {
|
|
9817
|
-
if (!
|
|
9958
|
+
if (!fs25.existsSync(path20.join(skillsDir, skillId))) {
|
|
9818
9959
|
missingSkills.push(skillId);
|
|
9819
9960
|
}
|
|
9820
9961
|
}
|
|
@@ -9838,10 +9979,10 @@ function runDoctor(targetDir) {
|
|
|
9838
9979
|
message: ".claude/skills/ \u4E0D\u5B58\u5728"
|
|
9839
9980
|
});
|
|
9840
9981
|
}
|
|
9841
|
-
const mcpPath =
|
|
9842
|
-
if (
|
|
9982
|
+
const mcpPath = path20.join(targetDir, ".mcp.json");
|
|
9983
|
+
if (fs25.existsSync(mcpPath)) {
|
|
9843
9984
|
try {
|
|
9844
|
-
const mcp = JSON.parse(
|
|
9985
|
+
const mcp = JSON.parse(fs25.readFileSync(mcpPath, "utf-8"));
|
|
9845
9986
|
const hasServers = mcp.mcpServers && Object.keys(mcp.mcpServers).length > 0;
|
|
9846
9987
|
checks.push({
|
|
9847
9988
|
name: "MCP \u670D\u52A1\u5668",
|
|
@@ -9862,12 +10003,12 @@ function runDoctor(targetDir) {
|
|
|
9862
10003
|
message: ".mcp.json \u4E0D\u5B58\u5728"
|
|
9863
10004
|
});
|
|
9864
10005
|
}
|
|
9865
|
-
if (hasDeepStorm &&
|
|
10006
|
+
if (hasDeepStorm && fs25.existsSync(settingsPath)) {
|
|
9866
10007
|
try {
|
|
9867
|
-
const config = JSON.parse(
|
|
10008
|
+
const config = JSON.parse(fs25.readFileSync(settingsPath, "utf-8"));
|
|
9868
10009
|
const installedMcp = config.installedMcpServers;
|
|
9869
10010
|
if (installedMcp && installedMcp.length > 0) {
|
|
9870
|
-
const mcpExists =
|
|
10011
|
+
const mcpExists = fs25.existsSync(mcpPath);
|
|
9871
10012
|
if (!mcpExists) {
|
|
9872
10013
|
checks.push({
|
|
9873
10014
|
name: "MCP \u4E00\u81F4\u6027",
|
|
@@ -9876,7 +10017,7 @@ function runDoctor(targetDir) {
|
|
|
9876
10017
|
});
|
|
9877
10018
|
} else {
|
|
9878
10019
|
try {
|
|
9879
|
-
const mcpConfig = JSON.parse(
|
|
10020
|
+
const mcpConfig = JSON.parse(fs25.readFileSync(mcpPath, "utf-8"));
|
|
9880
10021
|
const servers = mcpConfig.mcpServers || {};
|
|
9881
10022
|
const missing = [];
|
|
9882
10023
|
for (const toolName of installedMcp) {
|
|
@@ -9904,9 +10045,9 @@ function runDoctor(targetDir) {
|
|
|
9904
10045
|
} catch {
|
|
9905
10046
|
}
|
|
9906
10047
|
}
|
|
9907
|
-
if (hasDeepStorm &&
|
|
10048
|
+
if (hasDeepStorm && fs25.existsSync(settingsPath)) {
|
|
9908
10049
|
try {
|
|
9909
|
-
const config = JSON.parse(
|
|
10050
|
+
const config = JSON.parse(fs25.readFileSync(settingsPath, "utf-8"));
|
|
9910
10051
|
const validKeys = loadValidConfigKeys();
|
|
9911
10052
|
if (validKeys.size > 0 && config) {
|
|
9912
10053
|
const configKeys = [];
|
|
@@ -9959,18 +10100,18 @@ function printDoctorReport(report) {
|
|
|
9959
10100
|
}
|
|
9960
10101
|
|
|
9961
10102
|
// src/commands/uninstall.ts
|
|
9962
|
-
var
|
|
9963
|
-
var
|
|
10103
|
+
var fs26 = __toESM(require("node:fs"));
|
|
10104
|
+
var path21 = __toESM(require("node:path"));
|
|
9964
10105
|
var import_prompts4 = require("@clack/prompts");
|
|
9965
10106
|
async function uninstallDeepStorm(targetDir) {
|
|
9966
10107
|
const settingsPath = getDeepStormConfigPath(targetDir);
|
|
9967
|
-
if (!
|
|
10108
|
+
if (!fs26.existsSync(settingsPath)) {
|
|
9968
10109
|
console.log("DeepStorm \u5C1A\u672A\u914D\u7F6E\uFF0C\u65E0\u9700\u5378\u8F7D");
|
|
9969
10110
|
return;
|
|
9970
10111
|
}
|
|
9971
10112
|
let hasDeepStorm = false;
|
|
9972
10113
|
try {
|
|
9973
|
-
const settings = JSON.parse(
|
|
10114
|
+
const settings = JSON.parse(fs26.readFileSync(settingsPath, "utf-8"));
|
|
9974
10115
|
hasDeepStorm = !!settings && Object.keys(settings).length > 0;
|
|
9975
10116
|
} catch {
|
|
9976
10117
|
}
|
|
@@ -9980,14 +10121,14 @@ async function uninstallDeepStorm(targetDir) {
|
|
|
9980
10121
|
}
|
|
9981
10122
|
cleanInstalled(targetDir);
|
|
9982
10123
|
resetConfig(targetDir);
|
|
9983
|
-
const templatesDir =
|
|
9984
|
-
if (
|
|
10124
|
+
const templatesDir = path21.join(targetDir, ".deepstorm", "templates");
|
|
10125
|
+
if (fs26.existsSync(templatesDir)) {
|
|
9985
10126
|
const shouldDelete = await (0, import_prompts4.confirm)({
|
|
9986
10127
|
message: "\u662F\u5426\u5220\u9664 .deepstorm/templates/ \u76EE\u5F55\uFF1F",
|
|
9987
10128
|
initialValue: false
|
|
9988
10129
|
});
|
|
9989
10130
|
if (shouldDelete) {
|
|
9990
|
-
|
|
10131
|
+
fs26.rmSync(templatesDir, { recursive: true, force: true });
|
|
9991
10132
|
console.log("\u2714 .deepstorm/templates/ \u5DF2\u5220\u9664");
|
|
9992
10133
|
} else {
|
|
9993
10134
|
console.log("\u4FDD\u7559 .deepstorm/templates/");
|
|
@@ -10000,9 +10141,9 @@ async function uninstallDeepStorm(targetDir) {
|
|
|
10000
10141
|
var program = new import_commander.Command();
|
|
10001
10142
|
program.name("deepstorm").description("DeepStorm CLI \u2014 \u4E00\u952E\u914D\u7F6E\u9879\u76EE\u5F00\u53D1\u73AF\u5883").version(getCliVersion(), "-v, --version", "\u8F93\u51FA\u7248\u672C\u53F7");
|
|
10002
10143
|
function loadRegistry() {
|
|
10003
|
-
const registryPath =
|
|
10144
|
+
const registryPath = path22.join(__dirname, "registry.json");
|
|
10004
10145
|
try {
|
|
10005
|
-
const raw =
|
|
10146
|
+
const raw = fs27.readFileSync(registryPath, "utf-8");
|
|
10006
10147
|
return JSON.parse(raw);
|
|
10007
10148
|
} catch {
|
|
10008
10149
|
return { version: "1", tools: {}, wizards: {}, skills: {} };
|