rulesync 8.9.0 → 8.10.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/README.md +8 -0
- package/dist/{chunk-EHXIVMY2.js → chunk-RMITDFVW.js} +3 -0
- package/dist/cli/index.cjs +13607 -13293
- package/dist/cli/index.js +324 -7
- package/dist/index.js +1 -1
- package/package.json +1 -1
package/dist/cli/index.js
CHANGED
|
@@ -16,6 +16,7 @@ import {
|
|
|
16
16
|
JsonLogger,
|
|
17
17
|
MAX_FILE_SIZE,
|
|
18
18
|
McpProcessor,
|
|
19
|
+
PermissionsProcessor,
|
|
19
20
|
RULESYNC_AIIGNORE_FILE_NAME,
|
|
20
21
|
RULESYNC_AIIGNORE_RELATIVE_FILE_PATH,
|
|
21
22
|
RULESYNC_COMMANDS_RELATIVE_DIR_PATH,
|
|
@@ -53,6 +54,7 @@ import {
|
|
|
53
54
|
SKILL_FILE_NAME,
|
|
54
55
|
SkillsProcessor,
|
|
55
56
|
SubagentsProcessor,
|
|
57
|
+
ToolTargetSchema,
|
|
56
58
|
checkPathTraversal,
|
|
57
59
|
checkRulesyncDirExists,
|
|
58
60
|
createTempDirectory,
|
|
@@ -77,7 +79,7 @@ import {
|
|
|
77
79
|
stringifyFrontmatter,
|
|
78
80
|
toPosixPath,
|
|
79
81
|
writeFileContent
|
|
80
|
-
} from "../chunk-
|
|
82
|
+
} from "../chunk-RMITDFVW.js";
|
|
81
83
|
|
|
82
84
|
// src/cli/index.ts
|
|
83
85
|
import { Command } from "commander";
|
|
@@ -85,6 +87,311 @@ import { Command } from "commander";
|
|
|
85
87
|
// src/utils/parse-comma-separated-list.ts
|
|
86
88
|
var parseCommaSeparatedList = (value) => value.split(",").map((s) => s.trim()).filter(Boolean);
|
|
87
89
|
|
|
90
|
+
// src/lib/convert.ts
|
|
91
|
+
async function convertFromTool(params) {
|
|
92
|
+
const ctx = params;
|
|
93
|
+
const [
|
|
94
|
+
rulesCount,
|
|
95
|
+
ignoreCount,
|
|
96
|
+
mcpCount,
|
|
97
|
+
commandsCount,
|
|
98
|
+
subagentsCount,
|
|
99
|
+
skillsCount,
|
|
100
|
+
hooksCount,
|
|
101
|
+
permissionsCount
|
|
102
|
+
] = [
|
|
103
|
+
await runFeatureConvert(ctx, buildRulesStrategy(ctx)),
|
|
104
|
+
await runFeatureConvert(ctx, buildIgnoreStrategy(ctx)),
|
|
105
|
+
await runFeatureConvert(ctx, buildMcpStrategy(ctx)),
|
|
106
|
+
await runFeatureConvert(ctx, buildCommandsStrategy(ctx)),
|
|
107
|
+
await runFeatureConvert(ctx, buildSubagentsStrategy(ctx)),
|
|
108
|
+
await runFeatureConvert(ctx, buildSkillsStrategy(ctx)),
|
|
109
|
+
await runFeatureConvert(ctx, buildHooksStrategy(ctx)),
|
|
110
|
+
await runFeatureConvert(ctx, buildPermissionsStrategy(ctx))
|
|
111
|
+
];
|
|
112
|
+
return {
|
|
113
|
+
rulesCount,
|
|
114
|
+
ignoreCount,
|
|
115
|
+
mcpCount,
|
|
116
|
+
commandsCount,
|
|
117
|
+
subagentsCount,
|
|
118
|
+
skillsCount,
|
|
119
|
+
hooksCount,
|
|
120
|
+
permissionsCount
|
|
121
|
+
};
|
|
122
|
+
}
|
|
123
|
+
async function runFeatureConvert(ctx, strategy) {
|
|
124
|
+
if (!strategy) return 0;
|
|
125
|
+
const { config, fromTool, toTools, logger: logger5 } = ctx;
|
|
126
|
+
const {
|
|
127
|
+
feature,
|
|
128
|
+
itemLabel,
|
|
129
|
+
allTargets,
|
|
130
|
+
importableTargets = allTargets,
|
|
131
|
+
createProcessor,
|
|
132
|
+
loadSource,
|
|
133
|
+
toRulesync,
|
|
134
|
+
fromRulesync,
|
|
135
|
+
write
|
|
136
|
+
} = strategy;
|
|
137
|
+
if (!config.getFeatures(fromTool).includes(feature)) {
|
|
138
|
+
return 0;
|
|
139
|
+
}
|
|
140
|
+
if (!allTargets.includes(fromTool)) {
|
|
141
|
+
logger5.warn(`Source tool '${fromTool}' does not support feature '${feature}'. Skipping.`);
|
|
142
|
+
return 0;
|
|
143
|
+
}
|
|
144
|
+
if (!importableTargets.includes(fromTool)) {
|
|
145
|
+
logger5.warn(`Conversion from ${fromTool} ${feature} is not supported. Skipping.`);
|
|
146
|
+
return 0;
|
|
147
|
+
}
|
|
148
|
+
const sourceProcessor = createProcessor({ toolTarget: fromTool, dryRun: false });
|
|
149
|
+
const sourceItems = await loadSource(sourceProcessor);
|
|
150
|
+
if (sourceItems.length === 0) {
|
|
151
|
+
logger5.warn(`No ${feature} files found for ${fromTool}. Skipping ${feature} conversion.`);
|
|
152
|
+
return 0;
|
|
153
|
+
}
|
|
154
|
+
const rulesyncItems = await toRulesync(sourceProcessor, sourceItems);
|
|
155
|
+
let totalCount = 0;
|
|
156
|
+
for (const toTool of toTools) {
|
|
157
|
+
if (!allTargets.includes(toTool)) {
|
|
158
|
+
logger5.warn(`Destination tool '${toTool}' does not support feature '${feature}'. Skipping.`);
|
|
159
|
+
continue;
|
|
160
|
+
}
|
|
161
|
+
const destProcessor = createProcessor({
|
|
162
|
+
toolTarget: toTool,
|
|
163
|
+
dryRun: config.isPreviewMode()
|
|
164
|
+
});
|
|
165
|
+
const destItems = await fromRulesync(destProcessor, rulesyncItems);
|
|
166
|
+
const { count } = await write(destProcessor, destItems);
|
|
167
|
+
totalCount += count;
|
|
168
|
+
if (config.getVerbose() && count > 0) {
|
|
169
|
+
const verb = config.isPreviewMode() ? "Would convert" : "Converted";
|
|
170
|
+
logger5.success(`${verb} ${count} ${itemLabel} for ${toTool}`);
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
return totalCount;
|
|
174
|
+
}
|
|
175
|
+
function getBaseDir(config) {
|
|
176
|
+
return config.getBaseDirs()[0] ?? ".";
|
|
177
|
+
}
|
|
178
|
+
function buildRulesStrategy(ctx) {
|
|
179
|
+
const { config, logger: logger5 } = ctx;
|
|
180
|
+
const global = config.getGlobal();
|
|
181
|
+
const baseDir = getBaseDir(config);
|
|
182
|
+
const allTargets = RulesProcessor.getToolTargets({ global });
|
|
183
|
+
return {
|
|
184
|
+
feature: "rules",
|
|
185
|
+
itemLabel: "rule file(s)",
|
|
186
|
+
allTargets,
|
|
187
|
+
createProcessor: ({ toolTarget, dryRun }) => new RulesProcessor({ baseDir, toolTarget, global, dryRun, logger: logger5 }),
|
|
188
|
+
loadSource: (p) => p.loadToolFiles(),
|
|
189
|
+
toRulesync: (p, files) => p.convertToolFilesToRulesyncFiles(files),
|
|
190
|
+
fromRulesync: (p, files) => p.convertRulesyncFilesToToolFiles(files),
|
|
191
|
+
write: (p, files) => p.writeAiFiles(files)
|
|
192
|
+
};
|
|
193
|
+
}
|
|
194
|
+
function buildIgnoreStrategy(ctx) {
|
|
195
|
+
const { config, logger: logger5 } = ctx;
|
|
196
|
+
if (config.getGlobal()) {
|
|
197
|
+
logger5.debug("Skipping ignore conversion (not supported in global mode)");
|
|
198
|
+
return null;
|
|
199
|
+
}
|
|
200
|
+
const baseDir = getBaseDir(config);
|
|
201
|
+
const allTargets = IgnoreProcessor.getToolTargets();
|
|
202
|
+
return {
|
|
203
|
+
feature: "ignore",
|
|
204
|
+
itemLabel: "ignore file(s)",
|
|
205
|
+
allTargets,
|
|
206
|
+
createProcessor: ({ toolTarget, dryRun }) => new IgnoreProcessor({
|
|
207
|
+
baseDir,
|
|
208
|
+
toolTarget,
|
|
209
|
+
dryRun,
|
|
210
|
+
logger: logger5,
|
|
211
|
+
featureOptions: config.getFeatureOptions(toolTarget, "ignore")
|
|
212
|
+
}),
|
|
213
|
+
loadSource: (p) => p.loadToolFiles(),
|
|
214
|
+
toRulesync: (p, files) => p.convertToolFilesToRulesyncFiles(files),
|
|
215
|
+
fromRulesync: (p, files) => p.convertRulesyncFilesToToolFiles(files),
|
|
216
|
+
write: (p, files) => p.writeAiFiles(files)
|
|
217
|
+
};
|
|
218
|
+
}
|
|
219
|
+
function buildMcpStrategy(ctx) {
|
|
220
|
+
const { config, logger: logger5 } = ctx;
|
|
221
|
+
const global = config.getGlobal();
|
|
222
|
+
const baseDir = getBaseDir(config);
|
|
223
|
+
const allTargets = McpProcessor.getToolTargets({ global });
|
|
224
|
+
return {
|
|
225
|
+
feature: "mcp",
|
|
226
|
+
itemLabel: "MCP file(s)",
|
|
227
|
+
allTargets,
|
|
228
|
+
createProcessor: ({ toolTarget, dryRun }) => new McpProcessor({ baseDir, toolTarget, global, dryRun, logger: logger5 }),
|
|
229
|
+
loadSource: (p) => p.loadToolFiles(),
|
|
230
|
+
toRulesync: (p, files) => p.convertToolFilesToRulesyncFiles(files),
|
|
231
|
+
fromRulesync: (p, files) => p.convertRulesyncFilesToToolFiles(files),
|
|
232
|
+
write: (p, files) => p.writeAiFiles(files)
|
|
233
|
+
};
|
|
234
|
+
}
|
|
235
|
+
function buildCommandsStrategy(ctx) {
|
|
236
|
+
const { config, logger: logger5 } = ctx;
|
|
237
|
+
const global = config.getGlobal();
|
|
238
|
+
const baseDir = getBaseDir(config);
|
|
239
|
+
const allTargets = CommandsProcessor.getToolTargets({ global, includeSimulated: false });
|
|
240
|
+
return {
|
|
241
|
+
feature: "commands",
|
|
242
|
+
itemLabel: "command file(s)",
|
|
243
|
+
allTargets,
|
|
244
|
+
createProcessor: ({ toolTarget, dryRun }) => new CommandsProcessor({ baseDir, toolTarget, global, dryRun, logger: logger5 }),
|
|
245
|
+
loadSource: (p) => p.loadToolFiles(),
|
|
246
|
+
toRulesync: (p, files) => p.convertToolFilesToRulesyncFiles(files),
|
|
247
|
+
fromRulesync: (p, files) => p.convertRulesyncFilesToToolFiles(files),
|
|
248
|
+
write: (p, files) => p.writeAiFiles(files)
|
|
249
|
+
};
|
|
250
|
+
}
|
|
251
|
+
function buildSubagentsStrategy(ctx) {
|
|
252
|
+
const { config, logger: logger5 } = ctx;
|
|
253
|
+
const global = config.getGlobal();
|
|
254
|
+
const baseDir = getBaseDir(config);
|
|
255
|
+
const allTargets = SubagentsProcessor.getToolTargets({ global, includeSimulated: false });
|
|
256
|
+
return {
|
|
257
|
+
feature: "subagents",
|
|
258
|
+
itemLabel: "subagent file(s)",
|
|
259
|
+
allTargets,
|
|
260
|
+
createProcessor: ({ toolTarget, dryRun }) => new SubagentsProcessor({ baseDir, toolTarget, global, dryRun, logger: logger5 }),
|
|
261
|
+
loadSource: (p) => p.loadToolFiles(),
|
|
262
|
+
toRulesync: (p, files) => p.convertToolFilesToRulesyncFiles(files),
|
|
263
|
+
fromRulesync: (p, files) => p.convertRulesyncFilesToToolFiles(files),
|
|
264
|
+
write: (p, files) => p.writeAiFiles(files)
|
|
265
|
+
};
|
|
266
|
+
}
|
|
267
|
+
function buildSkillsStrategy(ctx) {
|
|
268
|
+
const { config, logger: logger5 } = ctx;
|
|
269
|
+
const global = config.getGlobal();
|
|
270
|
+
const baseDir = getBaseDir(config);
|
|
271
|
+
const allTargets = SkillsProcessor.getToolTargets({ global });
|
|
272
|
+
return {
|
|
273
|
+
feature: "skills",
|
|
274
|
+
itemLabel: "skill(s)",
|
|
275
|
+
allTargets,
|
|
276
|
+
createProcessor: ({ toolTarget, dryRun }) => new SkillsProcessor({ baseDir, toolTarget, global, dryRun, logger: logger5 }),
|
|
277
|
+
loadSource: (p) => p.loadToolDirs(),
|
|
278
|
+
toRulesync: (p, dirs) => p.convertToolDirsToRulesyncDirs(dirs),
|
|
279
|
+
fromRulesync: (p, dirs) => p.convertRulesyncDirsToToolDirs(dirs),
|
|
280
|
+
write: (p, dirs) => p.writeAiDirs(dirs)
|
|
281
|
+
};
|
|
282
|
+
}
|
|
283
|
+
function buildHooksStrategy(ctx) {
|
|
284
|
+
const { config, logger: logger5 } = ctx;
|
|
285
|
+
const global = config.getGlobal();
|
|
286
|
+
const baseDir = getBaseDir(config);
|
|
287
|
+
const allTargets = HooksProcessor.getToolTargets({ global });
|
|
288
|
+
const importableTargets = HooksProcessor.getToolTargets({ global, importOnly: true });
|
|
289
|
+
return {
|
|
290
|
+
feature: "hooks",
|
|
291
|
+
itemLabel: "hooks file(s)",
|
|
292
|
+
allTargets,
|
|
293
|
+
importableTargets,
|
|
294
|
+
createProcessor: ({ toolTarget, dryRun }) => new HooksProcessor({ baseDir, toolTarget, global, dryRun, logger: logger5 }),
|
|
295
|
+
loadSource: (p) => p.loadToolFiles(),
|
|
296
|
+
toRulesync: (p, files) => p.convertToolFilesToRulesyncFiles(files),
|
|
297
|
+
fromRulesync: (p, files) => p.convertRulesyncFilesToToolFiles(files),
|
|
298
|
+
write: (p, files) => p.writeAiFiles(files)
|
|
299
|
+
};
|
|
300
|
+
}
|
|
301
|
+
function buildPermissionsStrategy(ctx) {
|
|
302
|
+
const { config, logger: logger5 } = ctx;
|
|
303
|
+
const global = config.getGlobal();
|
|
304
|
+
const baseDir = getBaseDir(config);
|
|
305
|
+
const allTargets = PermissionsProcessor.getToolTargets({ global });
|
|
306
|
+
const importableTargets = PermissionsProcessor.getToolTargets({ global, importOnly: true });
|
|
307
|
+
return {
|
|
308
|
+
feature: "permissions",
|
|
309
|
+
itemLabel: "permissions file(s)",
|
|
310
|
+
allTargets,
|
|
311
|
+
importableTargets,
|
|
312
|
+
createProcessor: ({ toolTarget, dryRun }) => new PermissionsProcessor({ baseDir, toolTarget, global, dryRun, logger: logger5 }),
|
|
313
|
+
loadSource: (p) => p.loadToolFiles(),
|
|
314
|
+
toRulesync: (p, files) => p.convertToolFilesToRulesyncFiles(files),
|
|
315
|
+
fromRulesync: (p, files) => p.convertRulesyncFilesToToolFiles(files),
|
|
316
|
+
write: (p, files) => p.writeAiFiles(files)
|
|
317
|
+
};
|
|
318
|
+
}
|
|
319
|
+
|
|
320
|
+
// src/utils/result.ts
|
|
321
|
+
function calculateTotalCount(result) {
|
|
322
|
+
return result.rulesCount + result.ignoreCount + result.mcpCount + result.commandsCount + result.subagentsCount + result.skillsCount + result.hooksCount + result.permissionsCount;
|
|
323
|
+
}
|
|
324
|
+
|
|
325
|
+
// src/cli/commands/convert.ts
|
|
326
|
+
function parseToolTarget(value, label) {
|
|
327
|
+
const result = ToolTargetSchema.safeParse(value);
|
|
328
|
+
if (!result.success) {
|
|
329
|
+
throw new CLIError(
|
|
330
|
+
`Invalid ${label} tool '${value}'. Must be one of: ${ALL_TOOL_TARGETS.join(", ")}`,
|
|
331
|
+
ErrorCodes.CONVERT_FAILED
|
|
332
|
+
);
|
|
333
|
+
}
|
|
334
|
+
return result.data;
|
|
335
|
+
}
|
|
336
|
+
async function convertCommand(logger5, options) {
|
|
337
|
+
const fromTool = parseToolTarget(options.from ?? "", "source");
|
|
338
|
+
const toToolsRaw = (options.to ?? []).map((t) => parseToolTarget(t, "destination"));
|
|
339
|
+
const toTools = Array.from(new Set(toToolsRaw));
|
|
340
|
+
if (toTools.includes(fromTool)) {
|
|
341
|
+
throw new CLIError(
|
|
342
|
+
`Destination tools must not include the source tool '${fromTool}'. Converting a tool onto itself is likely a mistake and may cause lossy round-trips.`,
|
|
343
|
+
ErrorCodes.CONVERT_FAILED
|
|
344
|
+
);
|
|
345
|
+
}
|
|
346
|
+
const config = await ConfigResolver.resolve({
|
|
347
|
+
...options,
|
|
348
|
+
targets: [fromTool, ...toTools],
|
|
349
|
+
features: options.features ?? ["*"]
|
|
350
|
+
});
|
|
351
|
+
const isPreview = config.isPreviewMode();
|
|
352
|
+
const modePrefix = isPreview ? "[DRY RUN] " : "";
|
|
353
|
+
logger5.debug(`Converting files from ${fromTool} to ${toTools.join(", ")}...`);
|
|
354
|
+
const result = await convertFromTool({ config, fromTool, toTools, logger: logger5 });
|
|
355
|
+
const totalConverted = calculateTotalCount(result);
|
|
356
|
+
if (totalConverted === 0) {
|
|
357
|
+
const enabledFeatures = config.getFeatures(fromTool).join(", ");
|
|
358
|
+
logger5.warn(`No files converted for enabled features: ${enabledFeatures}`);
|
|
359
|
+
return;
|
|
360
|
+
}
|
|
361
|
+
if (logger5.jsonMode) {
|
|
362
|
+
logger5.captureData("from", fromTool);
|
|
363
|
+
logger5.captureData("to", toTools);
|
|
364
|
+
logger5.captureData("dryRun", isPreview);
|
|
365
|
+
logger5.captureData("features", {
|
|
366
|
+
rules: { count: result.rulesCount },
|
|
367
|
+
ignore: { count: result.ignoreCount },
|
|
368
|
+
mcp: { count: result.mcpCount },
|
|
369
|
+
commands: { count: result.commandsCount },
|
|
370
|
+
subagents: { count: result.subagentsCount },
|
|
371
|
+
skills: { count: result.skillsCount },
|
|
372
|
+
hooks: { count: result.hooksCount },
|
|
373
|
+
permissions: { count: result.permissionsCount }
|
|
374
|
+
});
|
|
375
|
+
logger5.captureData("totalFiles", totalConverted);
|
|
376
|
+
}
|
|
377
|
+
const parts = [];
|
|
378
|
+
if (result.rulesCount > 0) parts.push(`${result.rulesCount} rules`);
|
|
379
|
+
if (result.ignoreCount > 0) parts.push(`${result.ignoreCount} ignore files`);
|
|
380
|
+
if (result.mcpCount > 0) parts.push(`${result.mcpCount} MCP files`);
|
|
381
|
+
if (result.commandsCount > 0) parts.push(`${result.commandsCount} commands`);
|
|
382
|
+
if (result.subagentsCount > 0) parts.push(`${result.subagentsCount} subagents`);
|
|
383
|
+
if (result.skillsCount > 0) parts.push(`${result.skillsCount} skills`);
|
|
384
|
+
if (result.hooksCount > 0) parts.push(`${result.hooksCount} hooks`);
|
|
385
|
+
if (result.permissionsCount > 0) parts.push(`${result.permissionsCount} permissions`);
|
|
386
|
+
const verbPhrase = isPreview ? "Would convert" : "Converted";
|
|
387
|
+
const summary = `${modePrefix}${verbPhrase} ${totalConverted} file(s) total from ${fromTool} to ${toTools.join(", ")} (${parts.join(" + ")})`;
|
|
388
|
+
if (isPreview) {
|
|
389
|
+
logger5.info(summary);
|
|
390
|
+
} else {
|
|
391
|
+
logger5.success(summary);
|
|
392
|
+
}
|
|
393
|
+
}
|
|
394
|
+
|
|
88
395
|
// src/lib/fetch.ts
|
|
89
396
|
import { join, posix } from "path";
|
|
90
397
|
import { Semaphore } from "es-toolkit/promise";
|
|
@@ -1032,11 +1339,6 @@ async function fetchCommand(logger5, options) {
|
|
|
1032
1339
|
}
|
|
1033
1340
|
}
|
|
1034
1341
|
|
|
1035
|
-
// src/utils/result.ts
|
|
1036
|
-
function calculateTotalCount(result) {
|
|
1037
|
-
return result.rulesCount + result.ignoreCount + result.mcpCount + result.commandsCount + result.subagentsCount + result.skillsCount + result.hooksCount + result.permissionsCount;
|
|
1038
|
-
}
|
|
1039
|
-
|
|
1040
1342
|
// src/cli/commands/generate.ts
|
|
1041
1343
|
function logFeatureResult(logger5, params) {
|
|
1042
1344
|
const { count, paths, featureName, isPreview, modePrefix } = params;
|
|
@@ -6252,7 +6554,7 @@ function wrapCommand({
|
|
|
6252
6554
|
}
|
|
6253
6555
|
|
|
6254
6556
|
// src/cli/index.ts
|
|
6255
|
-
var getVersion = () => "8.
|
|
6557
|
+
var getVersion = () => "8.10.0";
|
|
6256
6558
|
function wrapCommand2(name, errorCode, handler) {
|
|
6257
6559
|
return wrapCommand({ name, errorCode, handler, getVersion });
|
|
6258
6560
|
}
|
|
@@ -6313,6 +6615,21 @@ var main = async () => {
|
|
|
6313
6615
|
await importCommand(logger5, options);
|
|
6314
6616
|
})
|
|
6315
6617
|
);
|
|
6618
|
+
program.command("convert").description(
|
|
6619
|
+
"Convert configurations from one AI tool to other AI tools without writing .rulesync/ files"
|
|
6620
|
+
).requiredOption("--from <tool>", "Source tool to convert from (e.g., 'cursor', 'claudecode')").requiredOption(
|
|
6621
|
+
"--to <tools>",
|
|
6622
|
+
"Comma-separated list of destination tools (e.g., 'copilot,claudecode')",
|
|
6623
|
+
parseCommaSeparatedList
|
|
6624
|
+
).option(
|
|
6625
|
+
"-f, --features <features>",
|
|
6626
|
+
`Comma-separated list of features to convert (${ALL_FEATURES.join(",")}) or '*' for all`,
|
|
6627
|
+
parseCommaSeparatedList
|
|
6628
|
+
).option("-V, --verbose", "Verbose output").option("-s, --silent", "Suppress all output").option("-g, --global", "Convert for global(user scope) configuration files").option("--dry-run", "Dry run: show changes without writing files").action(
|
|
6629
|
+
wrapCommand2("convert", "CONVERT_FAILED", async (logger5, options) => {
|
|
6630
|
+
await convertCommand(logger5, options);
|
|
6631
|
+
})
|
|
6632
|
+
);
|
|
6316
6633
|
program.command("mcp").description("Start MCP server for rulesync").action(
|
|
6317
6634
|
wrapCommand2("mcp", "MCP_FAILED", async (logger5, _options) => {
|
|
6318
6635
|
await mcpCommand(logger5, { version });
|
package/dist/index.js
CHANGED