rulesync 0.74.0 → 0.76.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (4) hide show
  1. package/README.md +9 -5
  2. package/dist/index.cjs +1559 -1202
  3. package/dist/index.js +1563 -1206
  4. package/package.json +1 -1
package/dist/index.cjs CHANGED
@@ -31,98 +31,13 @@ var import_commander = require("commander");
31
31
  // src/constants/announcements.ts
32
32
  var ANNOUNCEMENT = "".trim();
33
33
 
34
- // src/types/config-options.ts
35
- var import_mini2 = require("zod/mini");
36
-
37
- // src/types/tool-targets.ts
34
+ // src/types/features.ts
38
35
  var import_mini = require("zod/mini");
39
- var ALL_TOOL_TARGETS = [
40
- "agentsmd",
41
- "amazonqcli",
42
- "augmentcode",
43
- "augmentcode-legacy",
44
- "copilot",
45
- "cursor",
46
- "cline",
47
- "claudecode",
48
- "codexcli",
49
- "opencode",
50
- "qwencode",
51
- "roo",
52
- "geminicli",
53
- "kiro",
54
- "junie",
55
- "warp",
56
- "windsurf"
57
- ];
58
- var ALL_TOOL_TARGETS_WITH_WILDCARD = [...ALL_TOOL_TARGETS, "*"];
59
- var ToolTargetSchema = import_mini.z.enum(ALL_TOOL_TARGETS);
60
- var ToolTargetsSchema = import_mini.z.array(ToolTargetSchema);
61
- var RulesyncTargetsSchema = import_mini.z.array(import_mini.z.enum(ALL_TOOL_TARGETS_WITH_WILDCARD));
62
-
63
- // src/types/config-options.ts
64
- var FEATURE_TYPES = ["rules", "commands", "mcp", "ignore", "subagents"];
65
- var FeatureTypeSchema = import_mini2.z.enum(FEATURE_TYPES);
66
- var FeaturesSchema = import_mini2.z.union([import_mini2.z.array(FeatureTypeSchema), import_mini2.z.literal("*")]);
67
- var OutputPathsSchema = import_mini2.z.object({
68
- agentsmd: import_mini2.z.optional(import_mini2.z.string()),
69
- amazonqcli: import_mini2.z.optional(import_mini2.z.string()),
70
- augmentcode: import_mini2.z.optional(import_mini2.z.string()),
71
- "augmentcode-legacy": import_mini2.z.optional(import_mini2.z.string()),
72
- copilot: import_mini2.z.optional(import_mini2.z.string()),
73
- cursor: import_mini2.z.optional(import_mini2.z.string()),
74
- cline: import_mini2.z.optional(import_mini2.z.string()),
75
- claudecode: import_mini2.z.optional(import_mini2.z.string()),
76
- codexcli: import_mini2.z.optional(import_mini2.z.string()),
77
- opencode: import_mini2.z.optional(import_mini2.z.string()),
78
- qwencode: import_mini2.z.optional(import_mini2.z.string()),
79
- roo: import_mini2.z.optional(import_mini2.z.string()),
80
- geminicli: import_mini2.z.optional(import_mini2.z.string()),
81
- kiro: import_mini2.z.optional(import_mini2.z.string()),
82
- junie: import_mini2.z.optional(import_mini2.z.string()),
83
- windsurf: import_mini2.z.optional(import_mini2.z.string())
84
- });
85
- var ConfigOptionsSchema = import_mini2.z.object({
86
- aiRulesDir: import_mini2.z.optional(import_mini2.z.string()),
87
- outputPaths: import_mini2.z.optional(OutputPathsSchema),
88
- watchEnabled: import_mini2.z.optional(import_mini2.z.boolean()),
89
- defaultTargets: import_mini2.z.optional(ToolTargetsSchema),
90
- targets: import_mini2.z.optional(import_mini2.z.array(ToolTargetSchema)),
91
- exclude: import_mini2.z.optional(import_mini2.z.array(ToolTargetSchema)),
92
- features: import_mini2.z.optional(FeaturesSchema),
93
- verbose: import_mini2.z.optional(import_mini2.z.boolean()),
94
- delete: import_mini2.z.optional(import_mini2.z.boolean()),
95
- baseDir: import_mini2.z.optional(import_mini2.z.union([import_mini2.z.string(), import_mini2.z.array(import_mini2.z.string())])),
96
- legacy: import_mini2.z.optional(import_mini2.z.boolean()),
97
- watch: import_mini2.z.optional(
98
- import_mini2.z.object({
99
- enabled: import_mini2.z.optional(import_mini2.z.boolean()),
100
- interval: import_mini2.z.optional(import_mini2.z.number()),
101
- ignore: import_mini2.z.optional(import_mini2.z.array(import_mini2.z.string()))
102
- })
103
- )
104
- });
105
- var MergedConfigSchema = import_mini2.z.object({
106
- aiRulesDir: import_mini2.z.string(),
107
- outputPaths: import_mini2.z.record(ToolTargetSchema, import_mini2.z.string()),
108
- watchEnabled: import_mini2.z.boolean(),
109
- defaultTargets: ToolTargetsSchema,
110
- targets: import_mini2.z.optional(import_mini2.z.array(ToolTargetSchema)),
111
- exclude: import_mini2.z.optional(import_mini2.z.array(ToolTargetSchema)),
112
- features: import_mini2.z.optional(FeaturesSchema),
113
- verbose: import_mini2.z.optional(import_mini2.z.boolean()),
114
- delete: import_mini2.z.optional(import_mini2.z.boolean()),
115
- baseDir: import_mini2.z.optional(import_mini2.z.union([import_mini2.z.string(), import_mini2.z.array(import_mini2.z.string())])),
116
- configPath: import_mini2.z.optional(import_mini2.z.string()),
117
- legacy: import_mini2.z.optional(import_mini2.z.boolean()),
118
- watch: import_mini2.z.optional(
119
- import_mini2.z.object({
120
- enabled: import_mini2.z.optional(import_mini2.z.boolean()),
121
- interval: import_mini2.z.optional(import_mini2.z.number()),
122
- ignore: import_mini2.z.optional(import_mini2.z.array(import_mini2.z.string()))
123
- })
124
- )
125
- });
36
+ var ALL_FEATURES = ["rules", "ignore", "mcp", "subagents", "commands"];
37
+ var ALL_FEATURES_WITH_WILDCARD = [...ALL_FEATURES, "*"];
38
+ var FeatureSchema = import_mini.z.enum(ALL_FEATURES);
39
+ var FeaturesSchema = import_mini.z.array(FeatureSchema);
40
+ var RulesyncFeaturesSchema = import_mini.z.array(import_mini.z.enum(ALL_FEATURES_WITH_WILDCARD));
126
41
 
127
42
  // src/utils/file.ts
128
43
  var import_node_fs = require("fs");
@@ -430,6 +345,32 @@ var RulesyncFile = class extends AiFile {
430
345
  }
431
346
  };
432
347
 
348
+ // src/types/tool-targets.ts
349
+ var import_mini2 = require("zod/mini");
350
+ var ALL_TOOL_TARGETS = [
351
+ "agentsmd",
352
+ "amazonqcli",
353
+ "augmentcode",
354
+ "augmentcode-legacy",
355
+ "copilot",
356
+ "cursor",
357
+ "cline",
358
+ "claudecode",
359
+ "codexcli",
360
+ "opencode",
361
+ "qwencode",
362
+ "roo",
363
+ "geminicli",
364
+ "kiro",
365
+ "junie",
366
+ "warp",
367
+ "windsurf"
368
+ ];
369
+ var ALL_TOOL_TARGETS_WITH_WILDCARD = [...ALL_TOOL_TARGETS, "*"];
370
+ var ToolTargetSchema = import_mini2.z.enum(ALL_TOOL_TARGETS);
371
+ var ToolTargetsSchema = import_mini2.z.array(ToolTargetSchema);
372
+ var RulesyncTargetsSchema = import_mini2.z.array(import_mini2.z.enum(ALL_TOOL_TARGETS_WITH_WILDCARD));
373
+
433
374
  // src/commands/rulesync-command.ts
434
375
  var RulesyncCommandFrontmatterSchema = import_mini3.z.object({
435
376
  targets: RulesyncTargetsSchema,
@@ -532,6 +473,39 @@ var ToolCommand = class extends AiFile {
532
473
  static fromRulesyncCommand(_params) {
533
474
  throw new Error("Please implement this method in the subclass.");
534
475
  }
476
+ /**
477
+ * Check if this tool is targeted by a RulesyncCommand based on its targets field.
478
+ * Subclasses should override this to provide specific targeting logic.
479
+ *
480
+ * @param rulesyncCommand - The RulesyncCommand to check
481
+ * @returns True if this tool is targeted by the command
482
+ */
483
+ static isTargetedByRulesyncCommand(_rulesyncCommand) {
484
+ throw new Error("Please implement this method in the subclass.");
485
+ }
486
+ /**
487
+ * Default implementation for checking if a tool is targeted by a RulesyncCommand.
488
+ * Checks if the command's targets include the tool target or a wildcard.
489
+ *
490
+ * @param params - Parameters including the RulesyncCommand and tool target
491
+ * @returns True if the tool target is included in the command's targets
492
+ */
493
+ static isTargetedByRulesyncCommandDefault({
494
+ rulesyncCommand,
495
+ toolTarget
496
+ }) {
497
+ const targets = rulesyncCommand.getFrontmatter().targets;
498
+ if (!targets) {
499
+ return true;
500
+ }
501
+ if (targets.includes("*")) {
502
+ return true;
503
+ }
504
+ if (targets.includes(toolTarget)) {
505
+ return true;
506
+ }
507
+ return false;
508
+ }
535
509
  };
536
510
 
537
511
  // src/commands/claudecode-command.ts
@@ -612,6 +586,12 @@ var ClaudecodeCommand = class _ClaudecodeCommand extends ToolCommand {
612
586
  return { success: false, error: result.error };
613
587
  }
614
588
  }
589
+ static isTargetedByRulesyncCommand(rulesyncCommand) {
590
+ return this.isTargetedByRulesyncCommandDefault({
591
+ rulesyncCommand,
592
+ toolTarget: "claudecode"
593
+ });
594
+ }
615
595
  static async fromFile({
616
596
  baseDir = ".",
617
597
  relativeFilePath,
@@ -772,6 +752,12 @@ var CodexCliCommand = class _CodexCliCommand extends SimulatedCommand {
772
752
  validate
773
753
  });
774
754
  }
755
+ static isTargetedByRulesyncCommand(rulesyncCommand) {
756
+ return this.isTargetedByRulesyncCommandDefault({
757
+ rulesyncCommand,
758
+ toolTarget: "codexcli"
759
+ });
760
+ }
775
761
  };
776
762
 
777
763
  // src/commands/copilot-command.ts
@@ -779,7 +765,7 @@ var import_node_path7 = require("path");
779
765
  var CopilotCommand = class _CopilotCommand extends SimulatedCommand {
780
766
  static getSettablePaths() {
781
767
  return {
782
- relativeDirPath: ".copilot/commands"
768
+ relativeDirPath: ".github/commands"
783
769
  };
784
770
  }
785
771
  static fromRulesyncCommand({
@@ -816,6 +802,12 @@ var CopilotCommand = class _CopilotCommand extends SimulatedCommand {
816
802
  validate
817
803
  });
818
804
  }
805
+ static isTargetedByRulesyncCommand(rulesyncCommand) {
806
+ return this.isTargetedByRulesyncCommandDefault({
807
+ rulesyncCommand,
808
+ toolTarget: "copilot"
809
+ });
810
+ }
819
811
  };
820
812
 
821
813
  // src/commands/cursor-command.ts
@@ -860,6 +852,12 @@ var CursorCommand = class _CursorCommand extends SimulatedCommand {
860
852
  validate
861
853
  });
862
854
  }
855
+ static isTargetedByRulesyncCommand(rulesyncCommand) {
856
+ return this.isTargetedByRulesyncCommandDefault({
857
+ rulesyncCommand,
858
+ toolTarget: "cursor"
859
+ });
860
+ }
863
861
  };
864
862
 
865
863
  // src/commands/geminicli-command.ts
@@ -896,17 +894,6 @@ var GeminiCliCommand = class _GeminiCliCommand extends ToolCommand {
896
894
  throw new Error(`Failed to parse TOML command file: ${error}`);
897
895
  }
898
896
  }
899
- parseCommandFile(content) {
900
- const parsed = this.parseTomlContent(content);
901
- return {
902
- filename: "unknown.toml",
903
- filepath: "unknown.toml",
904
- frontmatter: {
905
- description: parsed.description
906
- },
907
- content: parsed.prompt
908
- };
909
- }
910
897
  getBody() {
911
898
  return this.body;
912
899
  }
@@ -981,6 +968,12 @@ ${geminiFrontmatter.prompt}
981
968
  return { success: false, error: error instanceof Error ? error : new Error(String(error)) };
982
969
  }
983
970
  }
971
+ static isTargetedByRulesyncCommand(rulesyncCommand) {
972
+ return this.isTargetedByRulesyncCommandDefault({
973
+ rulesyncCommand,
974
+ toolTarget: "geminicli"
975
+ });
976
+ }
984
977
  };
985
978
 
986
979
  // src/commands/roo-command.ts
@@ -1066,6 +1059,12 @@ var RooCommand = class _RooCommand extends ToolCommand {
1066
1059
  return { success: false, error: result.error };
1067
1060
  }
1068
1061
  }
1062
+ static isTargetedByRulesyncCommand(rulesyncCommand) {
1063
+ return this.isTargetedByRulesyncCommandDefault({
1064
+ rulesyncCommand,
1065
+ toolTarget: "roo"
1066
+ });
1067
+ }
1069
1068
  static async fromFile({
1070
1069
  baseDir = ".",
1071
1070
  relativeFilePath,
@@ -1117,31 +1116,49 @@ var CommandsProcessor = class extends FeatureProcessor {
1117
1116
  const toolCommands = rulesyncCommands.map((rulesyncCommand) => {
1118
1117
  switch (this.toolTarget) {
1119
1118
  case "claudecode":
1119
+ if (!ClaudecodeCommand.isTargetedByRulesyncCommand(rulesyncCommand)) {
1120
+ return null;
1121
+ }
1120
1122
  return ClaudecodeCommand.fromRulesyncCommand({
1121
1123
  baseDir: this.baseDir,
1122
1124
  rulesyncCommand
1123
1125
  });
1124
1126
  case "geminicli":
1127
+ if (!GeminiCliCommand.isTargetedByRulesyncCommand(rulesyncCommand)) {
1128
+ return null;
1129
+ }
1125
1130
  return GeminiCliCommand.fromRulesyncCommand({
1126
1131
  baseDir: this.baseDir,
1127
1132
  rulesyncCommand
1128
1133
  });
1129
1134
  case "roo":
1135
+ if (!RooCommand.isTargetedByRulesyncCommand(rulesyncCommand)) {
1136
+ return null;
1137
+ }
1130
1138
  return RooCommand.fromRulesyncCommand({
1131
1139
  baseDir: this.baseDir,
1132
1140
  rulesyncCommand
1133
1141
  });
1134
1142
  case "copilot":
1143
+ if (!CopilotCommand.isTargetedByRulesyncCommand(rulesyncCommand)) {
1144
+ return null;
1145
+ }
1135
1146
  return CopilotCommand.fromRulesyncCommand({
1136
1147
  baseDir: this.baseDir,
1137
1148
  rulesyncCommand
1138
1149
  });
1139
1150
  case "cursor":
1151
+ if (!CursorCommand.isTargetedByRulesyncCommand(rulesyncCommand)) {
1152
+ return null;
1153
+ }
1140
1154
  return CursorCommand.fromRulesyncCommand({
1141
1155
  baseDir: this.baseDir,
1142
1156
  rulesyncCommand
1143
1157
  });
1144
1158
  case "codexcli":
1159
+ if (!CodexCliCommand.isTargetedByRulesyncCommand(rulesyncCommand)) {
1160
+ return null;
1161
+ }
1145
1162
  return CodexCliCommand.fromRulesyncCommand({
1146
1163
  baseDir: this.baseDir,
1147
1164
  rulesyncCommand
@@ -1149,7 +1166,9 @@ var CommandsProcessor = class extends FeatureProcessor {
1149
1166
  default:
1150
1167
  throw new Error(`Unsupported tool target: ${this.toolTarget}`);
1151
1168
  }
1152
- });
1169
+ }).filter(
1170
+ (command) => command !== null
1171
+ );
1153
1172
  return toolCommands;
1154
1173
  }
1155
1174
  async convertToolFilesToRulesyncFiles(toolFiles) {
@@ -1304,19 +1323,14 @@ var CommandsProcessor = class extends FeatureProcessor {
1304
1323
  }
1305
1324
  return commandsProcessorToolTargets;
1306
1325
  }
1326
+ static getToolTargetsSimulated() {
1327
+ return commandsProcessorToolTargetsSimulated;
1328
+ }
1307
1329
  };
1308
1330
 
1309
1331
  // src/config/config-resolver.ts
1310
1332
  var import_c12 = require("c12");
1311
1333
 
1312
- // src/types/features.ts
1313
- var import_mini9 = require("zod/mini");
1314
- var ALL_FEATURES = ["rules", "ignore", "mcp", "subagents", "commands"];
1315
- var ALL_FEATURES_WITH_WILDCARD = [...ALL_FEATURES, "*"];
1316
- var FeatureSchema = import_mini9.z.enum(ALL_FEATURES);
1317
- var FeaturesSchema2 = import_mini9.z.array(FeatureSchema);
1318
- var RulesyncFeaturesSchema = import_mini9.z.array(import_mini9.z.enum(ALL_FEATURES_WITH_WILDCARD));
1319
-
1320
1334
  // src/config/config.ts
1321
1335
  var Config = class {
1322
1336
  baseDirs;
@@ -1431,7 +1445,7 @@ var ConfigResolver = class {
1431
1445
  };
1432
1446
 
1433
1447
  // src/ignore/ignore-processor.ts
1434
- var import_mini10 = require("zod/mini");
1448
+ var import_mini9 = require("zod/mini");
1435
1449
 
1436
1450
  // src/ignore/amazonqcli-ignore.ts
1437
1451
  var import_node_path12 = require("path");
@@ -2043,7 +2057,7 @@ var ignoreProcessorToolTargets = [
2043
2057
  "roo",
2044
2058
  "windsurf"
2045
2059
  ];
2046
- var IgnoreProcessorToolTargetSchema = import_mini10.z.enum(ignoreProcessorToolTargets);
2060
+ var IgnoreProcessorToolTargetSchema = import_mini9.z.enum(ignoreProcessorToolTargets);
2047
2061
  var IgnoreProcessor = class extends FeatureProcessor {
2048
2062
  toolTarget;
2049
2063
  constructor({
@@ -2205,47 +2219,40 @@ var IgnoreProcessor = class extends FeatureProcessor {
2205
2219
  };
2206
2220
 
2207
2221
  // src/mcp/mcp-processor.ts
2208
- var import_mini12 = require("zod/mini");
2222
+ var import_mini11 = require("zod/mini");
2209
2223
 
2210
2224
  // src/mcp/amazonqcli-mcp.ts
2211
2225
  var import_node_path24 = require("path");
2212
2226
 
2213
2227
  // src/mcp/rulesync-mcp.ts
2214
2228
  var import_node_path23 = require("path");
2215
-
2216
- // src/types/mcp.ts
2217
- var import_mini11 = require("zod/mini");
2218
- var McpTransportTypeSchema = import_mini11.z.enum(["stdio", "sse", "http"]);
2219
- var McpServerBaseSchema = import_mini11.z.object({
2220
- type: import_mini11.z.optional(import_mini11.z.enum(["stdio", "sse", "http"])),
2221
- command: import_mini11.z.optional(import_mini11.z.union([import_mini11.z.string(), import_mini11.z.array(import_mini11.z.string())])),
2222
- args: import_mini11.z.optional(import_mini11.z.array(import_mini11.z.string())),
2223
- url: import_mini11.z.optional(import_mini11.z.string()),
2224
- httpUrl: import_mini11.z.optional(import_mini11.z.string()),
2225
- env: import_mini11.z.optional(import_mini11.z.record(import_mini11.z.string(), import_mini11.z.string())),
2226
- disabled: import_mini11.z.optional(import_mini11.z.boolean()),
2227
- networkTimeout: import_mini11.z.optional(import_mini11.z.number()),
2228
- timeout: import_mini11.z.optional(import_mini11.z.number()),
2229
- trust: import_mini11.z.optional(import_mini11.z.boolean()),
2230
- cwd: import_mini11.z.optional(import_mini11.z.string()),
2231
- transport: import_mini11.z.optional(McpTransportTypeSchema),
2232
- alwaysAllow: import_mini11.z.optional(import_mini11.z.array(import_mini11.z.string())),
2233
- tools: import_mini11.z.optional(import_mini11.z.array(import_mini11.z.string())),
2234
- kiroAutoApprove: import_mini11.z.optional(import_mini11.z.array(import_mini11.z.string())),
2235
- kiroAutoBlock: import_mini11.z.optional(import_mini11.z.array(import_mini11.z.string())),
2236
- headers: import_mini11.z.optional(import_mini11.z.record(import_mini11.z.string(), import_mini11.z.string()))
2237
- });
2238
- var RulesyncMcpServerSchema = import_mini11.z.extend(McpServerBaseSchema, {
2239
- targets: import_mini11.z.optional(RulesyncTargetsSchema)
2229
+ var import_mini10 = require("zod/mini");
2230
+ var McpTransportTypeSchema = import_mini10.z.enum(["stdio", "sse", "http"]);
2231
+ var McpServerBaseSchema = import_mini10.z.object({
2232
+ type: import_mini10.z.optional(import_mini10.z.enum(["stdio", "sse", "http"])),
2233
+ command: import_mini10.z.optional(import_mini10.z.union([import_mini10.z.string(), import_mini10.z.array(import_mini10.z.string())])),
2234
+ args: import_mini10.z.optional(import_mini10.z.array(import_mini10.z.string())),
2235
+ url: import_mini10.z.optional(import_mini10.z.string()),
2236
+ httpUrl: import_mini10.z.optional(import_mini10.z.string()),
2237
+ env: import_mini10.z.optional(import_mini10.z.record(import_mini10.z.string(), import_mini10.z.string())),
2238
+ disabled: import_mini10.z.optional(import_mini10.z.boolean()),
2239
+ networkTimeout: import_mini10.z.optional(import_mini10.z.number()),
2240
+ timeout: import_mini10.z.optional(import_mini10.z.number()),
2241
+ trust: import_mini10.z.optional(import_mini10.z.boolean()),
2242
+ cwd: import_mini10.z.optional(import_mini10.z.string()),
2243
+ transport: import_mini10.z.optional(McpTransportTypeSchema),
2244
+ alwaysAllow: import_mini10.z.optional(import_mini10.z.array(import_mini10.z.string())),
2245
+ tools: import_mini10.z.optional(import_mini10.z.array(import_mini10.z.string())),
2246
+ kiroAutoApprove: import_mini10.z.optional(import_mini10.z.array(import_mini10.z.string())),
2247
+ kiroAutoBlock: import_mini10.z.optional(import_mini10.z.array(import_mini10.z.string())),
2248
+ headers: import_mini10.z.optional(import_mini10.z.record(import_mini10.z.string(), import_mini10.z.string()))
2240
2249
  });
2241
- var McpConfigSchema = import_mini11.z.object({
2242
- mcpServers: import_mini11.z.record(import_mini11.z.string(), McpServerBaseSchema)
2250
+ var RulesyncMcpServerSchema = import_mini10.z.extend(McpServerBaseSchema, {
2251
+ targets: import_mini10.z.optional(RulesyncTargetsSchema)
2243
2252
  });
2244
- var RulesyncMcpConfigSchema = import_mini11.z.object({
2245
- mcpServers: import_mini11.z.record(import_mini11.z.string(), RulesyncMcpServerSchema)
2253
+ var RulesyncMcpConfigSchema = import_mini10.z.object({
2254
+ mcpServers: import_mini10.z.record(import_mini10.z.string(), RulesyncMcpServerSchema)
2246
2255
  });
2247
-
2248
- // src/mcp/rulesync-mcp.ts
2249
2256
  var RulesyncMcp = class _RulesyncMcp extends RulesyncFile {
2250
2257
  json;
2251
2258
  constructor({ ...rest }) {
@@ -2637,7 +2644,7 @@ var mcpProcessorToolTargets = [
2637
2644
  "cursor",
2638
2645
  "roo"
2639
2646
  ];
2640
- var McpProcessorToolTargetSchema = import_mini12.z.enum(mcpProcessorToolTargets);
2647
+ var McpProcessorToolTargetSchema = import_mini11.z.enum(mcpProcessorToolTargets);
2641
2648
  var McpProcessor = class extends FeatureProcessor {
2642
2649
  toolTarget;
2643
2650
  constructor({
@@ -2796,9 +2803,9 @@ var McpProcessor = class extends FeatureProcessor {
2796
2803
  };
2797
2804
 
2798
2805
  // src/rules/rules-processor.ts
2799
- var import_node_path50 = require("path");
2806
+ var import_node_path53 = require("path");
2800
2807
  var import_fast_xml_parser = require("fast-xml-parser");
2801
- var import_mini18 = require("zod/mini");
2808
+ var import_mini20 = require("zod/mini");
2802
2809
 
2803
2810
  // src/constants/paths.ts
2804
2811
  var import_node_path30 = require("path");
@@ -2810,7 +2817,7 @@ var RULESYNC_SUBAGENTS_DIR = (0, import_node_path30.join)(".rulesync", "subagent
2810
2817
 
2811
2818
  // src/subagents/simulated-subagent.ts
2812
2819
  var import_node_path31 = require("path");
2813
- var import_mini13 = require("zod/mini");
2820
+ var import_mini12 = require("zod/mini");
2814
2821
 
2815
2822
  // src/subagents/tool-subagent.ts
2816
2823
  var ToolSubagent = class extends ToolFile {
@@ -2823,12 +2830,31 @@ var ToolSubagent = class extends ToolFile {
2823
2830
  static fromRulesyncSubagent(_params) {
2824
2831
  throw new Error("Please implement this method in the subclass.");
2825
2832
  }
2833
+ static isTargetedByRulesyncSubagent(_rulesyncSubagent) {
2834
+ throw new Error("Please implement this method in the subclass.");
2835
+ }
2836
+ static isTargetedByRulesyncSubagentDefault({
2837
+ rulesyncSubagent,
2838
+ toolTarget
2839
+ }) {
2840
+ const targets = rulesyncSubagent.getFrontmatter().targets;
2841
+ if (!targets) {
2842
+ return true;
2843
+ }
2844
+ if (targets.includes("*")) {
2845
+ return true;
2846
+ }
2847
+ if (targets.includes(toolTarget)) {
2848
+ return true;
2849
+ }
2850
+ return false;
2851
+ }
2826
2852
  };
2827
2853
 
2828
2854
  // src/subagents/simulated-subagent.ts
2829
- var SimulatedSubagentFrontmatterSchema = import_mini13.z.object({
2830
- name: import_mini13.z.string(),
2831
- description: import_mini13.z.string()
2855
+ var SimulatedSubagentFrontmatterSchema = import_mini12.z.object({
2856
+ name: import_mini12.z.string(),
2857
+ description: import_mini12.z.string()
2832
2858
  });
2833
2859
  var SimulatedSubagent = class extends ToolSubagent {
2834
2860
  frontmatter;
@@ -2925,13 +2951,19 @@ var CodexCliSubagent = class _CodexCliSubagent extends SimulatedSubagent {
2925
2951
  const baseParams = this.fromRulesyncSubagentDefault(params);
2926
2952
  return new _CodexCliSubagent(baseParams);
2927
2953
  }
2954
+ static isTargetedByRulesyncSubagent(rulesyncSubagent) {
2955
+ return this.isTargetedByRulesyncSubagentDefault({
2956
+ rulesyncSubagent,
2957
+ toolTarget: "codexcli"
2958
+ });
2959
+ }
2928
2960
  };
2929
2961
 
2930
2962
  // src/subagents/copilot-subagent.ts
2931
2963
  var CopilotSubagent = class _CopilotSubagent extends SimulatedSubagent {
2932
2964
  static getSettablePaths() {
2933
2965
  return {
2934
- relativeDirPath: ".copilot/subagents"
2966
+ relativeDirPath: ".github/subagents"
2935
2967
  };
2936
2968
  }
2937
2969
  static async fromFile(params) {
@@ -2942,6 +2974,12 @@ var CopilotSubagent = class _CopilotSubagent extends SimulatedSubagent {
2942
2974
  const baseParams = this.fromRulesyncSubagentDefault(params);
2943
2975
  return new _CopilotSubagent(baseParams);
2944
2976
  }
2977
+ static isTargetedByRulesyncSubagent(rulesyncSubagent) {
2978
+ return this.isTargetedByRulesyncSubagentDefault({
2979
+ rulesyncSubagent,
2980
+ toolTarget: "copilot"
2981
+ });
2982
+ }
2945
2983
  };
2946
2984
 
2947
2985
  // src/subagents/cursor-subagent.ts
@@ -2959,357 +2997,897 @@ var CursorSubagent = class _CursorSubagent extends SimulatedSubagent {
2959
2997
  const baseParams = this.fromRulesyncSubagentDefault(params);
2960
2998
  return new _CursorSubagent(baseParams);
2961
2999
  }
3000
+ static isTargetedByRulesyncSubagent(rulesyncSubagent) {
3001
+ return this.isTargetedByRulesyncSubagentDefault({
3002
+ rulesyncSubagent,
3003
+ toolTarget: "cursor"
3004
+ });
3005
+ }
2962
3006
  };
2963
3007
 
2964
- // src/rules/agentsmd-rule.ts
3008
+ // src/subagents/geminicli-subagent.ts
3009
+ var GeminiCliSubagent = class _GeminiCliSubagent extends SimulatedSubagent {
3010
+ static getSettablePaths() {
3011
+ return {
3012
+ relativeDirPath: ".gemini/subagents"
3013
+ };
3014
+ }
3015
+ static async fromFile(params) {
3016
+ const baseParams = await this.fromFileDefault(params);
3017
+ return new _GeminiCliSubagent(baseParams);
3018
+ }
3019
+ static fromRulesyncSubagent(params) {
3020
+ const baseParams = this.fromRulesyncSubagentDefault(params);
3021
+ return new _GeminiCliSubagent(baseParams);
3022
+ }
3023
+ static isTargetedByRulesyncSubagent(rulesyncSubagent) {
3024
+ return this.isTargetedByRulesyncSubagentDefault({
3025
+ rulesyncSubagent,
3026
+ toolTarget: "geminicli"
3027
+ });
3028
+ }
3029
+ };
3030
+
3031
+ // src/subagents/roo-subagent.ts
3032
+ var RooSubagent = class _RooSubagent extends SimulatedSubagent {
3033
+ static getSettablePaths() {
3034
+ return {
3035
+ relativeDirPath: ".roo/subagents"
3036
+ };
3037
+ }
3038
+ static async fromFile(params) {
3039
+ const baseParams = await this.fromFileDefault(params);
3040
+ return new _RooSubagent(baseParams);
3041
+ }
3042
+ static fromRulesyncSubagent(params) {
3043
+ const baseParams = this.fromRulesyncSubagentDefault(params);
3044
+ return new _RooSubagent(baseParams);
3045
+ }
3046
+ static isTargetedByRulesyncSubagent(rulesyncSubagent) {
3047
+ return this.isTargetedByRulesyncSubagentDefault({
3048
+ rulesyncSubagent,
3049
+ toolTarget: "roo"
3050
+ });
3051
+ }
3052
+ };
3053
+
3054
+ // src/subagents/subagents-processor.ts
3055
+ var import_node_path34 = require("path");
3056
+ var import_mini15 = require("zod/mini");
3057
+
3058
+ // src/subagents/claudecode-subagent.ts
2965
3059
  var import_node_path33 = require("path");
3060
+ var import_mini14 = require("zod/mini");
2966
3061
 
2967
- // src/rules/rulesync-rule.ts
3062
+ // src/subagents/rulesync-subagent.ts
2968
3063
  var import_node_path32 = require("path");
2969
- var import_mini14 = require("zod/mini");
2970
- var RulesyncRuleFrontmatterSchema = import_mini14.z.object({
2971
- root: import_mini14.z.optional(import_mini14.z.optional(import_mini14.z.boolean())),
2972
- targets: import_mini14.z.optional(RulesyncTargetsSchema),
2973
- description: import_mini14.z.optional(import_mini14.z.string()),
2974
- globs: import_mini14.z.optional(import_mini14.z.array(import_mini14.z.string())),
2975
- cursor: import_mini14.z.optional(
2976
- import_mini14.z.object({
2977
- alwaysApply: import_mini14.z.optional(import_mini14.z.boolean()),
2978
- description: import_mini14.z.optional(import_mini14.z.string()),
2979
- globs: import_mini14.z.optional(import_mini14.z.array(import_mini14.z.string()))
3064
+ var import_mini13 = require("zod/mini");
3065
+ var RulesyncSubagentModelSchema = import_mini13.z.enum(["opus", "sonnet", "haiku", "inherit"]);
3066
+ var RulesyncSubagentFrontmatterSchema = import_mini13.z.object({
3067
+ targets: RulesyncTargetsSchema,
3068
+ name: import_mini13.z.string(),
3069
+ description: import_mini13.z.string(),
3070
+ claudecode: import_mini13.z.optional(
3071
+ import_mini13.z.object({
3072
+ model: RulesyncSubagentModelSchema
2980
3073
  })
2981
3074
  )
2982
3075
  });
2983
- var RulesyncRule = class _RulesyncRule extends RulesyncFile {
3076
+ var RulesyncSubagent = class _RulesyncSubagent extends RulesyncFile {
2984
3077
  frontmatter;
2985
3078
  body;
2986
3079
  constructor({ frontmatter, body, ...rest }) {
2987
3080
  if (rest.validate !== false) {
2988
- const result = RulesyncRuleFrontmatterSchema.safeParse(frontmatter);
3081
+ const result = RulesyncSubagentFrontmatterSchema.safeParse(frontmatter);
2989
3082
  if (!result.success) {
2990
3083
  throw result.error;
2991
3084
  }
2992
3085
  }
2993
3086
  super({
2994
- ...rest,
2995
- fileContent: stringifyFrontmatter(body, frontmatter)
3087
+ ...rest
2996
3088
  });
2997
3089
  this.frontmatter = frontmatter;
2998
3090
  this.body = body;
2999
3091
  }
3000
3092
  static getSettablePaths() {
3001
3093
  return {
3002
- recommended: {
3003
- relativeDirPath: ".rulesync/rules"
3004
- },
3005
- legacy: {
3006
- relativeDirPath: ".rulesync"
3007
- }
3094
+ relativeDirPath: ".rulesync/subagents"
3008
3095
  };
3009
3096
  }
3010
3097
  getFrontmatter() {
3011
3098
  return this.frontmatter;
3012
3099
  }
3100
+ getBody() {
3101
+ return this.body;
3102
+ }
3013
3103
  validate() {
3014
3104
  if (!this.frontmatter) {
3015
3105
  return { success: true, error: null };
3016
3106
  }
3017
- const result = RulesyncRuleFrontmatterSchema.safeParse(this.frontmatter);
3107
+ const result = RulesyncSubagentFrontmatterSchema.safeParse(this.frontmatter);
3018
3108
  if (result.success) {
3019
3109
  return { success: true, error: null };
3020
3110
  } else {
3021
3111
  return { success: false, error: result.error };
3022
3112
  }
3023
3113
  }
3024
- static async fromFileLegacy({
3025
- relativeFilePath,
3026
- validate = true
3027
- }) {
3028
- const filePath = (0, import_node_path32.join)(this.getSettablePaths().legacy.relativeDirPath, relativeFilePath);
3029
- const fileContent = await readFileContent(filePath);
3030
- const { frontmatter, body: content } = parseFrontmatter(fileContent);
3031
- const result = RulesyncRuleFrontmatterSchema.safeParse(frontmatter);
3032
- if (!result.success) {
3033
- throw new Error(`Invalid frontmatter in ${filePath}: ${result.error.message}`);
3034
- }
3035
- const validatedFrontmatter = {
3036
- root: result.data.root ?? false,
3037
- targets: result.data.targets ?? ["*"],
3038
- description: result.data.description ?? "",
3039
- globs: result.data.globs ?? [],
3040
- cursor: result.data.cursor
3041
- };
3042
- const filename = (0, import_node_path32.basename)(filePath);
3043
- return new _RulesyncRule({
3044
- baseDir: ".",
3045
- relativeDirPath: this.getSettablePaths().recommended.relativeDirPath,
3046
- relativeFilePath: filename,
3047
- frontmatter: validatedFrontmatter,
3048
- body: content.trim(),
3049
- validate
3050
- });
3051
- }
3052
3114
  static async fromFile({
3053
- relativeFilePath,
3054
- validate = true
3115
+ relativeFilePath
3055
3116
  }) {
3056
- const filePath = (0, import_node_path32.join)(this.getSettablePaths().recommended.relativeDirPath, relativeFilePath);
3057
- const fileContent = await readFileContent(filePath);
3117
+ const fileContent = await readFileContent((0, import_node_path32.join)(RULESYNC_SUBAGENTS_DIR, relativeFilePath));
3058
3118
  const { frontmatter, body: content } = parseFrontmatter(fileContent);
3059
- const result = RulesyncRuleFrontmatterSchema.safeParse(frontmatter);
3119
+ const result = RulesyncSubagentFrontmatterSchema.safeParse(frontmatter);
3060
3120
  if (!result.success) {
3061
- throw new Error(`Invalid frontmatter in ${filePath}: ${result.error.message}`);
3121
+ throw new Error(`Invalid frontmatter in ${relativeFilePath}: ${result.error.message}`);
3062
3122
  }
3063
- const validatedFrontmatter = {
3064
- root: result.data.root ?? false,
3065
- targets: result.data.targets ?? ["*"],
3066
- description: result.data.description ?? "",
3067
- globs: result.data.globs ?? [],
3068
- cursor: result.data.cursor
3069
- };
3070
- const filename = (0, import_node_path32.basename)(filePath);
3071
- return new _RulesyncRule({
3123
+ const filename = (0, import_node_path32.basename)(relativeFilePath);
3124
+ return new _RulesyncSubagent({
3072
3125
  baseDir: ".",
3073
- relativeDirPath: this.getSettablePaths().recommended.relativeDirPath,
3126
+ relativeDirPath: this.getSettablePaths().relativeDirPath,
3074
3127
  relativeFilePath: filename,
3075
- frontmatter: validatedFrontmatter,
3128
+ frontmatter: result.data,
3076
3129
  body: content.trim(),
3077
- validate
3130
+ fileContent
3078
3131
  });
3079
3132
  }
3080
- getBody() {
3081
- return this.body;
3082
- }
3083
3133
  };
3084
3134
 
3085
- // src/rules/tool-rule.ts
3086
- var ToolRule = class extends ToolFile {
3087
- root;
3088
- constructor({ root = false, ...rest }) {
3089
- super(rest);
3090
- this.root = root;
3091
- }
3092
- static async fromFile(_params) {
3093
- throw new Error("Please implement this method in the subclass.");
3094
- }
3095
- static fromRulesyncRule(_params) {
3096
- throw new Error("Please implement this method in the subclass.");
3097
- }
3098
- static buildToolRuleParamsDefault({
3099
- baseDir = ".",
3100
- rulesyncRule,
3101
- validate = true,
3102
- rootPath = { relativeDirPath: ".", relativeFilePath: "AGENTS.md" },
3103
- nonRootPath = { relativeDirPath: ".agents/memories" }
3104
- }) {
3105
- const fileContent = rulesyncRule.getBody();
3106
- return {
3107
- baseDir,
3108
- relativeDirPath: rulesyncRule.getFrontmatter().root ? rootPath.relativeDirPath : nonRootPath.relativeDirPath,
3109
- relativeFilePath: rulesyncRule.getFrontmatter().root ? rootPath.relativeFilePath : rulesyncRule.getRelativeFilePath(),
3110
- fileContent,
3111
- validate,
3112
- root: rulesyncRule.getFrontmatter().root ?? false
3113
- };
3114
- }
3115
- toRulesyncRuleDefault() {
3116
- return new RulesyncRule({
3117
- baseDir: this.getBaseDir(),
3118
- relativeDirPath: RULESYNC_RULES_DIR,
3119
- relativeFilePath: this.getRelativeFilePath(),
3120
- frontmatter: {
3121
- root: this.isRoot(),
3122
- targets: ["*"],
3123
- description: "",
3124
- globs: this.isRoot() ? ["**/*"] : []
3125
- },
3126
- body: this.getFileContent()
3127
- });
3128
- }
3129
- isRoot() {
3130
- return this.root;
3131
- }
3132
- };
3133
-
3134
- // src/rules/agentsmd-rule.ts
3135
- var AgentsMdRule = class _AgentsMdRule extends ToolRule {
3136
- constructor({ fileContent, root, ...rest }) {
3135
+ // src/subagents/claudecode-subagent.ts
3136
+ var ClaudecodeSubagentFrontmatterSchema = import_mini14.z.object({
3137
+ name: import_mini14.z.string(),
3138
+ description: import_mini14.z.string(),
3139
+ model: import_mini14.z.optional(import_mini14.z.enum(["opus", "sonnet", "haiku", "inherit"]))
3140
+ });
3141
+ var ClaudecodeSubagent = class _ClaudecodeSubagent extends ToolSubagent {
3142
+ frontmatter;
3143
+ body;
3144
+ constructor({ frontmatter, body, ...rest }) {
3145
+ if (rest.validate !== false) {
3146
+ const result = ClaudecodeSubagentFrontmatterSchema.safeParse(frontmatter);
3147
+ if (!result.success) {
3148
+ throw result.error;
3149
+ }
3150
+ }
3137
3151
  super({
3138
- ...rest,
3139
- fileContent,
3140
- root: root ?? false
3152
+ ...rest
3141
3153
  });
3154
+ this.frontmatter = frontmatter;
3155
+ this.body = body;
3142
3156
  }
3143
3157
  static getSettablePaths() {
3144
3158
  return {
3145
- root: {
3146
- relativeDirPath: ".",
3147
- relativeFilePath: "AGENTS.md"
3148
- },
3149
- nonRoot: {
3150
- relativeDirPath: ".agents/memories"
3151
- }
3159
+ relativeDirPath: ".claude/agents"
3152
3160
  };
3153
3161
  }
3154
- static async fromFile({
3155
- baseDir = ".",
3156
- relativeFilePath,
3157
- validate = true
3158
- }) {
3159
- const isRoot = relativeFilePath === "AGENTS.md";
3160
- const relativePath = isRoot ? "AGENTS.md" : (0, import_node_path33.join)(".agents/memories", relativeFilePath);
3161
- const fileContent = await readFileContent((0, import_node_path33.join)(baseDir, relativePath));
3162
- return new _AgentsMdRule({
3163
- baseDir,
3164
- relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
3165
- relativeFilePath: isRoot ? "AGENTS.md" : relativeFilePath,
3166
- fileContent,
3167
- validate,
3168
- root: isRoot
3169
- });
3170
- }
3171
- static fromRulesyncRule({
3172
- baseDir = ".",
3173
- rulesyncRule,
3174
- validate = true
3175
- }) {
3176
- return new _AgentsMdRule(
3177
- this.buildToolRuleParamsDefault({
3178
- baseDir,
3179
- rulesyncRule,
3180
- validate,
3181
- rootPath: this.getSettablePaths().root,
3182
- nonRootPath: this.getSettablePaths().nonRoot
3183
- })
3184
- );
3185
- }
3186
- toRulesyncRule() {
3187
- return this.toRulesyncRuleDefault();
3162
+ getFrontmatter() {
3163
+ return this.frontmatter;
3188
3164
  }
3189
- validate() {
3190
- return { success: true, error: null };
3165
+ getBody() {
3166
+ return this.body;
3191
3167
  }
3192
- };
3193
-
3194
- // src/rules/amazonqcli-rule.ts
3195
- var import_node_path34 = require("path");
3196
- var AmazonQCliRule = class _AmazonQCliRule extends ToolRule {
3197
- static getSettablePaths() {
3198
- return {
3199
- nonRoot: {
3200
- relativeDirPath: ".amazonq/rules"
3168
+ toRulesyncSubagent() {
3169
+ const rulesyncFrontmatter = {
3170
+ targets: ["claudecode"],
3171
+ name: this.frontmatter.name,
3172
+ description: this.frontmatter.description,
3173
+ ...this.frontmatter.model && {
3174
+ claudecode: {
3175
+ model: this.frontmatter.model
3176
+ }
3201
3177
  }
3202
3178
  };
3179
+ const fileContent = stringifyFrontmatter(this.body, rulesyncFrontmatter);
3180
+ return new RulesyncSubagent({
3181
+ frontmatter: rulesyncFrontmatter,
3182
+ body: this.body,
3183
+ baseDir: this.baseDir,
3184
+ relativeDirPath: ".rulesync/subagents",
3185
+ relativeFilePath: this.getRelativeFilePath(),
3186
+ fileContent,
3187
+ validate: true
3188
+ });
3203
3189
  }
3204
- static async fromFile({
3190
+ static fromRulesyncSubagent({
3205
3191
  baseDir = ".",
3206
- relativeFilePath,
3192
+ rulesyncSubagent,
3207
3193
  validate = true
3208
3194
  }) {
3209
- const fileContent = await readFileContent(
3210
- (0, import_node_path34.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
3211
- );
3212
- return new _AmazonQCliRule({
3195
+ const rulesyncFrontmatter = rulesyncSubagent.getFrontmatter();
3196
+ const claudecodeFrontmatter = {
3197
+ name: rulesyncFrontmatter.name,
3198
+ description: rulesyncFrontmatter.description,
3199
+ model: rulesyncFrontmatter.claudecode?.model
3200
+ };
3201
+ const body = rulesyncSubagent.getBody();
3202
+ const fileContent = stringifyFrontmatter(body, claudecodeFrontmatter);
3203
+ return new _ClaudecodeSubagent({
3213
3204
  baseDir,
3214
- relativeDirPath: this.getSettablePaths().nonRoot.relativeDirPath,
3215
- relativeFilePath,
3205
+ frontmatter: claudecodeFrontmatter,
3206
+ body,
3207
+ relativeDirPath: ".claude/agents",
3208
+ relativeFilePath: rulesyncSubagent.getRelativeFilePath(),
3216
3209
  fileContent,
3217
- validate,
3218
- root: false
3210
+ validate
3219
3211
  });
3220
3212
  }
3221
- static fromRulesyncRule({
3222
- baseDir = ".",
3223
- rulesyncRule,
3224
- validate = true
3225
- }) {
3226
- return new _AmazonQCliRule(
3227
- this.buildToolRuleParamsDefault({
3228
- baseDir,
3229
- rulesyncRule,
3230
- validate,
3231
- nonRootPath: this.getSettablePaths().nonRoot
3232
- })
3233
- );
3234
- }
3235
- toRulesyncRule() {
3236
- return this.toRulesyncRuleDefault();
3237
- }
3238
3213
  validate() {
3239
- return { success: true, error: null };
3214
+ if (!this.frontmatter) {
3215
+ return { success: true, error: null };
3216
+ }
3217
+ const result = ClaudecodeSubagentFrontmatterSchema.safeParse(this.frontmatter);
3218
+ if (result.success) {
3219
+ return { success: true, error: null };
3220
+ } else {
3221
+ return { success: false, error: result.error };
3222
+ }
3240
3223
  }
3241
- };
3242
-
3243
- // src/rules/augmentcode-legacy-rule.ts
3244
- var import_node_path35 = require("path");
3245
- var AugmentcodeLegacyRule = class _AugmentcodeLegacyRule extends ToolRule {
3246
- toRulesyncRule() {
3247
- const rulesyncFrontmatter = {
3248
- root: this.isRoot(),
3249
- targets: ["*"],
3250
- description: "",
3251
- globs: this.isRoot() ? ["**/*"] : []
3252
- };
3253
- return new RulesyncRule({
3254
- baseDir: this.getBaseDir(),
3255
- frontmatter: rulesyncFrontmatter,
3256
- body: this.getFileContent(),
3257
- relativeDirPath: RULESYNC_RULES_DIR,
3258
- relativeFilePath: this.getRelativeFilePath(),
3259
- validate: true
3224
+ static isTargetedByRulesyncSubagent(rulesyncSubagent) {
3225
+ return this.isTargetedByRulesyncSubagentDefault({
3226
+ rulesyncSubagent,
3227
+ toolTarget: "claudecode"
3260
3228
  });
3261
3229
  }
3262
- static getSettablePaths() {
3263
- return {
3264
- root: {
3265
- relativeDirPath: ".",
3266
- relativeFilePath: ".augment-guidelines"
3267
- },
3268
- nonRoot: {
3269
- relativeDirPath: ".augment/rules"
3270
- }
3271
- };
3272
- }
3273
- static fromRulesyncRule({
3274
- baseDir = ".",
3275
- rulesyncRule,
3276
- validate = true
3277
- }) {
3278
- return new _AugmentcodeLegacyRule(
3279
- this.buildToolRuleParamsDefault({
3280
- baseDir,
3281
- rulesyncRule,
3282
- validate,
3283
- rootPath: this.getSettablePaths().root,
3284
- nonRootPath: this.getSettablePaths().nonRoot
3285
- })
3286
- );
3287
- }
3288
- validate() {
3289
- return { success: true, error: null };
3290
- }
3291
3230
  static async fromFile({
3292
3231
  baseDir = ".",
3293
3232
  relativeFilePath,
3294
3233
  validate = true
3295
3234
  }) {
3296
- const settablePaths = this.getSettablePaths();
3297
- const isRoot = relativeFilePath === settablePaths.root.relativeFilePath;
3298
- const relativePath = isRoot ? settablePaths.root.relativeFilePath : (0, import_node_path35.join)(settablePaths.nonRoot.relativeDirPath, relativeFilePath);
3299
- const fileContent = await readFileContent((0, import_node_path35.join)(baseDir, relativePath));
3300
- return new _AugmentcodeLegacyRule({
3235
+ const fileContent = await readFileContent((0, import_node_path33.join)(baseDir, ".claude/agents", relativeFilePath));
3236
+ const { frontmatter, body: content } = parseFrontmatter(fileContent);
3237
+ const result = ClaudecodeSubagentFrontmatterSchema.safeParse(frontmatter);
3238
+ if (!result.success) {
3239
+ throw new Error(`Invalid frontmatter in ${relativeFilePath}: ${result.error.message}`);
3240
+ }
3241
+ return new _ClaudecodeSubagent({
3301
3242
  baseDir,
3302
- relativeDirPath: isRoot ? settablePaths.root.relativeDirPath : settablePaths.nonRoot.relativeDirPath,
3303
- relativeFilePath: isRoot ? settablePaths.root.relativeFilePath : relativeFilePath,
3243
+ relativeDirPath: ".claude/agents",
3244
+ relativeFilePath,
3245
+ frontmatter: result.data,
3246
+ body: content.trim(),
3304
3247
  fileContent,
3305
- validate,
3306
- root: isRoot
3248
+ validate
3249
+ });
3250
+ }
3251
+ };
3252
+
3253
+ // src/subagents/subagents-processor.ts
3254
+ var subagentsProcessorToolTargets = [
3255
+ "claudecode",
3256
+ "copilot",
3257
+ "cursor",
3258
+ "codexcli",
3259
+ "geminicli",
3260
+ "roo"
3261
+ ];
3262
+ var subagentsProcessorToolTargetsSimulated = [
3263
+ "copilot",
3264
+ "cursor",
3265
+ "codexcli",
3266
+ "geminicli",
3267
+ "roo"
3268
+ ];
3269
+ var SubagentsProcessorToolTargetSchema = import_mini15.z.enum(subagentsProcessorToolTargets);
3270
+ var SubagentsProcessor = class extends FeatureProcessor {
3271
+ toolTarget;
3272
+ constructor({
3273
+ baseDir = ".",
3274
+ toolTarget
3275
+ }) {
3276
+ super({ baseDir });
3277
+ this.toolTarget = SubagentsProcessorToolTargetSchema.parse(toolTarget);
3278
+ }
3279
+ async convertRulesyncFilesToToolFiles(rulesyncFiles) {
3280
+ const rulesyncSubagents = rulesyncFiles.filter(
3281
+ (file) => file instanceof RulesyncSubagent
3282
+ );
3283
+ const toolSubagents = rulesyncSubagents.map((rulesyncSubagent) => {
3284
+ switch (this.toolTarget) {
3285
+ case "claudecode":
3286
+ if (!ClaudecodeSubagent.isTargetedByRulesyncSubagent(rulesyncSubagent)) {
3287
+ return null;
3288
+ }
3289
+ return ClaudecodeSubagent.fromRulesyncSubagent({
3290
+ baseDir: this.baseDir,
3291
+ relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
3292
+ rulesyncSubagent
3293
+ });
3294
+ case "copilot":
3295
+ if (!CopilotSubagent.isTargetedByRulesyncSubagent(rulesyncSubagent)) {
3296
+ return null;
3297
+ }
3298
+ return CopilotSubagent.fromRulesyncSubagent({
3299
+ baseDir: this.baseDir,
3300
+ relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
3301
+ rulesyncSubagent
3302
+ });
3303
+ case "cursor":
3304
+ if (!CursorSubagent.isTargetedByRulesyncSubagent(rulesyncSubagent)) {
3305
+ return null;
3306
+ }
3307
+ return CursorSubagent.fromRulesyncSubagent({
3308
+ baseDir: this.baseDir,
3309
+ relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
3310
+ rulesyncSubagent
3311
+ });
3312
+ case "codexcli":
3313
+ if (!CodexCliSubagent.isTargetedByRulesyncSubagent(rulesyncSubagent)) {
3314
+ return null;
3315
+ }
3316
+ return CodexCliSubagent.fromRulesyncSubagent({
3317
+ baseDir: this.baseDir,
3318
+ relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
3319
+ rulesyncSubagent
3320
+ });
3321
+ case "geminicli":
3322
+ if (!GeminiCliSubagent.isTargetedByRulesyncSubagent(rulesyncSubagent)) {
3323
+ return null;
3324
+ }
3325
+ return GeminiCliSubagent.fromRulesyncSubagent({
3326
+ baseDir: this.baseDir,
3327
+ relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
3328
+ rulesyncSubagent
3329
+ });
3330
+ case "roo":
3331
+ if (!RooSubagent.isTargetedByRulesyncSubagent(rulesyncSubagent)) {
3332
+ return null;
3333
+ }
3334
+ return RooSubagent.fromRulesyncSubagent({
3335
+ baseDir: this.baseDir,
3336
+ relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
3337
+ rulesyncSubagent
3338
+ });
3339
+ default:
3340
+ throw new Error(`Unsupported tool target: ${this.toolTarget}`);
3341
+ }
3342
+ }).filter((subagent) => subagent !== null);
3343
+ return toolSubagents;
3344
+ }
3345
+ async convertToolFilesToRulesyncFiles(toolFiles) {
3346
+ const toolSubagents = toolFiles.filter(
3347
+ (file) => file instanceof ToolSubagent
3348
+ );
3349
+ const rulesyncSubagents = [];
3350
+ for (const toolSubagent of toolSubagents) {
3351
+ if (toolSubagent instanceof SimulatedSubagent) {
3352
+ logger.debug(
3353
+ `Skipping simulated subagent conversion: ${toolSubagent.getRelativeFilePath()}`
3354
+ );
3355
+ continue;
3356
+ }
3357
+ rulesyncSubagents.push(toolSubagent.toRulesyncSubagent());
3358
+ }
3359
+ return rulesyncSubagents;
3360
+ }
3361
+ /**
3362
+ * Implementation of abstract method from Processor
3363
+ * Load and parse rulesync subagent files from .rulesync/subagents/ directory
3364
+ */
3365
+ async loadRulesyncFiles() {
3366
+ const subagentsDir = (0, import_node_path34.join)(this.baseDir, RulesyncSubagent.getSettablePaths().relativeDirPath);
3367
+ const dirExists = await directoryExists(subagentsDir);
3368
+ if (!dirExists) {
3369
+ logger.debug(`Rulesync subagents directory not found: ${subagentsDir}`);
3370
+ return [];
3371
+ }
3372
+ const entries = await listDirectoryFiles(subagentsDir);
3373
+ const mdFiles = entries.filter((file) => file.endsWith(".md"));
3374
+ if (mdFiles.length === 0) {
3375
+ logger.debug(`No markdown files found in rulesync subagents directory: ${subagentsDir}`);
3376
+ return [];
3377
+ }
3378
+ logger.info(`Found ${mdFiles.length} subagent files in ${subagentsDir}`);
3379
+ const rulesyncSubagents = [];
3380
+ for (const mdFile of mdFiles) {
3381
+ const filepath = (0, import_node_path34.join)(subagentsDir, mdFile);
3382
+ try {
3383
+ const rulesyncSubagent = await RulesyncSubagent.fromFile({
3384
+ relativeFilePath: mdFile,
3385
+ validate: true
3386
+ });
3387
+ rulesyncSubagents.push(rulesyncSubagent);
3388
+ logger.debug(`Successfully loaded subagent: ${mdFile}`);
3389
+ } catch (error) {
3390
+ logger.warn(`Failed to load subagent file ${filepath}:`, error);
3391
+ continue;
3392
+ }
3393
+ }
3394
+ if (rulesyncSubagents.length === 0) {
3395
+ logger.debug(`No valid subagents found in ${subagentsDir}`);
3396
+ return [];
3397
+ }
3398
+ logger.info(`Successfully loaded ${rulesyncSubagents.length} rulesync subagents`);
3399
+ return rulesyncSubagents;
3400
+ }
3401
+ /**
3402
+ * Implementation of abstract method from Processor
3403
+ * Load tool-specific subagent configurations and parse them into ToolSubagent instances
3404
+ */
3405
+ async loadToolFiles() {
3406
+ switch (this.toolTarget) {
3407
+ case "claudecode":
3408
+ return await this.loadClaudecodeSubagents();
3409
+ case "copilot":
3410
+ return await this.loadCopilotSubagents();
3411
+ case "cursor":
3412
+ return await this.loadCursorSubagents();
3413
+ case "codexcli":
3414
+ return await this.loadCodexCliSubagents();
3415
+ case "geminicli":
3416
+ return await this.loadGeminiCliSubagents();
3417
+ case "roo":
3418
+ return await this.loadRooSubagents();
3419
+ default:
3420
+ throw new Error(`Unsupported tool target: ${this.toolTarget}`);
3421
+ }
3422
+ }
3423
+ /**
3424
+ * Load Claude Code subagent configurations from .claude/agents/ directory
3425
+ */
3426
+ async loadClaudecodeSubagents() {
3427
+ return await this.loadToolSubagentsDefault({
3428
+ relativeDirPath: ClaudecodeSubagent.getSettablePaths().relativeDirPath,
3429
+ fromFile: (relativeFilePath) => ClaudecodeSubagent.fromFile({ relativeFilePath })
3430
+ });
3431
+ }
3432
+ /**
3433
+ * Load Copilot subagent configurations from .github/subagents/ directory
3434
+ */
3435
+ async loadCopilotSubagents() {
3436
+ return await this.loadToolSubagentsDefault({
3437
+ relativeDirPath: CopilotSubagent.getSettablePaths().relativeDirPath,
3438
+ fromFile: (relativeFilePath) => CopilotSubagent.fromFile({ relativeFilePath })
3439
+ });
3440
+ }
3441
+ /**
3442
+ * Load Cursor subagent configurations from .cursor/subagents/ directory
3443
+ */
3444
+ async loadCursorSubagents() {
3445
+ return await this.loadToolSubagentsDefault({
3446
+ relativeDirPath: CursorSubagent.getSettablePaths().relativeDirPath,
3447
+ fromFile: (relativeFilePath) => CursorSubagent.fromFile({ relativeFilePath })
3448
+ });
3449
+ }
3450
+ /**
3451
+ * Load CodexCli subagent configurations from .codex/subagents/ directory
3452
+ */
3453
+ async loadCodexCliSubagents() {
3454
+ return await this.loadToolSubagentsDefault({
3455
+ relativeDirPath: CodexCliSubagent.getSettablePaths().relativeDirPath,
3456
+ fromFile: (relativeFilePath) => CodexCliSubagent.fromFile({ relativeFilePath })
3457
+ });
3458
+ }
3459
+ /**
3460
+ * Load GeminiCli subagent configurations from .gemini/subagents/ directory
3461
+ */
3462
+ async loadGeminiCliSubagents() {
3463
+ return await this.loadToolSubagentsDefault({
3464
+ relativeDirPath: GeminiCliSubagent.getSettablePaths().relativeDirPath,
3465
+ fromFile: (relativeFilePath) => GeminiCliSubagent.fromFile({ relativeFilePath })
3466
+ });
3467
+ }
3468
+ /**
3469
+ * Load Roo subagent configurations from .roo/subagents/ directory
3470
+ */
3471
+ async loadRooSubagents() {
3472
+ return await this.loadToolSubagentsDefault({
3473
+ relativeDirPath: RooSubagent.getSettablePaths().relativeDirPath,
3474
+ fromFile: (relativeFilePath) => RooSubagent.fromFile({ relativeFilePath })
3475
+ });
3476
+ }
3477
+ async loadToolSubagentsDefault({
3478
+ relativeDirPath,
3479
+ fromFile
3480
+ }) {
3481
+ const paths = await findFilesByGlobs((0, import_node_path34.join)(this.baseDir, relativeDirPath, "*.md"));
3482
+ const subagents = (await Promise.allSettled(paths.map((path2) => fromFile((0, import_node_path34.basename)(path2))))).filter((r) => r.status === "fulfilled").map((r) => r.value);
3483
+ logger.info(`Successfully loaded ${subagents.length} ${relativeDirPath} subagents`);
3484
+ return subagents;
3485
+ }
3486
+ /**
3487
+ * Implementation of abstract method from FeatureProcessor
3488
+ * Return the tool targets that this processor supports
3489
+ */
3490
+ static getToolTargets({
3491
+ includeSimulated = false
3492
+ } = {}) {
3493
+ if (!includeSimulated) {
3494
+ return subagentsProcessorToolTargets.filter(
3495
+ (target) => !subagentsProcessorToolTargetsSimulated.includes(target)
3496
+ );
3497
+ }
3498
+ return subagentsProcessorToolTargets;
3499
+ }
3500
+ static getToolTargetsSimulated() {
3501
+ return subagentsProcessorToolTargetsSimulated;
3502
+ }
3503
+ };
3504
+
3505
+ // src/rules/agentsmd-rule.ts
3506
+ var import_node_path36 = require("path");
3507
+
3508
+ // src/rules/rulesync-rule.ts
3509
+ var import_node_path35 = require("path");
3510
+ var import_mini16 = require("zod/mini");
3511
+ var RulesyncRuleFrontmatterSchema = import_mini16.z.object({
3512
+ root: import_mini16.z.optional(import_mini16.z.optional(import_mini16.z.boolean())),
3513
+ targets: import_mini16.z.optional(RulesyncTargetsSchema),
3514
+ description: import_mini16.z.optional(import_mini16.z.string()),
3515
+ globs: import_mini16.z.optional(import_mini16.z.array(import_mini16.z.string())),
3516
+ cursor: import_mini16.z.optional(
3517
+ import_mini16.z.object({
3518
+ alwaysApply: import_mini16.z.optional(import_mini16.z.boolean()),
3519
+ description: import_mini16.z.optional(import_mini16.z.string()),
3520
+ globs: import_mini16.z.optional(import_mini16.z.array(import_mini16.z.string()))
3521
+ })
3522
+ )
3523
+ });
3524
+ var RulesyncRule = class _RulesyncRule extends RulesyncFile {
3525
+ frontmatter;
3526
+ body;
3527
+ constructor({ frontmatter, body, ...rest }) {
3528
+ if (rest.validate !== false) {
3529
+ const result = RulesyncRuleFrontmatterSchema.safeParse(frontmatter);
3530
+ if (!result.success) {
3531
+ throw result.error;
3532
+ }
3533
+ }
3534
+ super({
3535
+ ...rest,
3536
+ fileContent: stringifyFrontmatter(body, frontmatter)
3537
+ });
3538
+ this.frontmatter = frontmatter;
3539
+ this.body = body;
3540
+ }
3541
+ static getSettablePaths() {
3542
+ return {
3543
+ recommended: {
3544
+ relativeDirPath: ".rulesync/rules"
3545
+ },
3546
+ legacy: {
3547
+ relativeDirPath: ".rulesync"
3548
+ }
3549
+ };
3550
+ }
3551
+ getFrontmatter() {
3552
+ return this.frontmatter;
3553
+ }
3554
+ validate() {
3555
+ if (!this.frontmatter) {
3556
+ return { success: true, error: null };
3557
+ }
3558
+ const result = RulesyncRuleFrontmatterSchema.safeParse(this.frontmatter);
3559
+ if (result.success) {
3560
+ return { success: true, error: null };
3561
+ } else {
3562
+ return { success: false, error: result.error };
3563
+ }
3564
+ }
3565
+ static async fromFileLegacy({
3566
+ relativeFilePath,
3567
+ validate = true
3568
+ }) {
3569
+ const filePath = (0, import_node_path35.join)(this.getSettablePaths().legacy.relativeDirPath, relativeFilePath);
3570
+ const fileContent = await readFileContent(filePath);
3571
+ const { frontmatter, body: content } = parseFrontmatter(fileContent);
3572
+ const result = RulesyncRuleFrontmatterSchema.safeParse(frontmatter);
3573
+ if (!result.success) {
3574
+ throw new Error(`Invalid frontmatter in ${filePath}: ${result.error.message}`);
3575
+ }
3576
+ const validatedFrontmatter = {
3577
+ root: result.data.root ?? false,
3578
+ targets: result.data.targets ?? ["*"],
3579
+ description: result.data.description ?? "",
3580
+ globs: result.data.globs ?? [],
3581
+ cursor: result.data.cursor
3582
+ };
3583
+ const filename = (0, import_node_path35.basename)(filePath);
3584
+ return new _RulesyncRule({
3585
+ baseDir: ".",
3586
+ relativeDirPath: this.getSettablePaths().recommended.relativeDirPath,
3587
+ relativeFilePath: filename,
3588
+ frontmatter: validatedFrontmatter,
3589
+ body: content.trim(),
3590
+ validate
3591
+ });
3592
+ }
3593
+ static async fromFile({
3594
+ relativeFilePath,
3595
+ validate = true
3596
+ }) {
3597
+ const filePath = (0, import_node_path35.join)(this.getSettablePaths().recommended.relativeDirPath, relativeFilePath);
3598
+ const fileContent = await readFileContent(filePath);
3599
+ const { frontmatter, body: content } = parseFrontmatter(fileContent);
3600
+ const result = RulesyncRuleFrontmatterSchema.safeParse(frontmatter);
3601
+ if (!result.success) {
3602
+ throw new Error(`Invalid frontmatter in ${filePath}: ${result.error.message}`);
3603
+ }
3604
+ const validatedFrontmatter = {
3605
+ root: result.data.root ?? false,
3606
+ targets: result.data.targets ?? ["*"],
3607
+ description: result.data.description ?? "",
3608
+ globs: result.data.globs ?? [],
3609
+ cursor: result.data.cursor
3610
+ };
3611
+ const filename = (0, import_node_path35.basename)(filePath);
3612
+ return new _RulesyncRule({
3613
+ baseDir: ".",
3614
+ relativeDirPath: this.getSettablePaths().recommended.relativeDirPath,
3615
+ relativeFilePath: filename,
3616
+ frontmatter: validatedFrontmatter,
3617
+ body: content.trim(),
3618
+ validate
3619
+ });
3620
+ }
3621
+ getBody() {
3622
+ return this.body;
3623
+ }
3624
+ };
3625
+
3626
+ // src/rules/tool-rule.ts
3627
+ var ToolRule = class extends ToolFile {
3628
+ root;
3629
+ constructor({ root = false, ...rest }) {
3630
+ super(rest);
3631
+ this.root = root;
3632
+ }
3633
+ static async fromFile(_params) {
3634
+ throw new Error("Please implement this method in the subclass.");
3635
+ }
3636
+ static fromRulesyncRule(_params) {
3637
+ throw new Error("Please implement this method in the subclass.");
3638
+ }
3639
+ static buildToolRuleParamsDefault({
3640
+ baseDir = ".",
3641
+ rulesyncRule,
3642
+ validate = true,
3643
+ rootPath = { relativeDirPath: ".", relativeFilePath: "AGENTS.md" },
3644
+ nonRootPath = { relativeDirPath: ".agents/memories" }
3645
+ }) {
3646
+ const fileContent = rulesyncRule.getBody();
3647
+ return {
3648
+ baseDir,
3649
+ relativeDirPath: rulesyncRule.getFrontmatter().root ? rootPath.relativeDirPath : nonRootPath.relativeDirPath,
3650
+ relativeFilePath: rulesyncRule.getFrontmatter().root ? rootPath.relativeFilePath : rulesyncRule.getRelativeFilePath(),
3651
+ fileContent,
3652
+ validate,
3653
+ root: rulesyncRule.getFrontmatter().root ?? false
3654
+ };
3655
+ }
3656
+ toRulesyncRuleDefault() {
3657
+ return new RulesyncRule({
3658
+ baseDir: this.getBaseDir(),
3659
+ relativeDirPath: RULESYNC_RULES_DIR,
3660
+ relativeFilePath: this.getRelativeFilePath(),
3661
+ frontmatter: {
3662
+ root: this.isRoot(),
3663
+ targets: ["*"],
3664
+ description: "",
3665
+ globs: this.isRoot() ? ["**/*"] : []
3666
+ },
3667
+ body: this.getFileContent()
3668
+ });
3669
+ }
3670
+ isRoot() {
3671
+ return this.root;
3672
+ }
3673
+ static isTargetedByRulesyncRule(_rulesyncRule) {
3674
+ throw new Error("Please implement this method in the subclass.");
3675
+ }
3676
+ static isTargetedByRulesyncRuleDefault({
3677
+ rulesyncRule,
3678
+ toolTarget
3679
+ }) {
3680
+ const targets = rulesyncRule.getFrontmatter().targets;
3681
+ if (!targets) {
3682
+ return true;
3683
+ }
3684
+ if (targets.includes("*")) {
3685
+ return true;
3686
+ }
3687
+ if (targets.includes(toolTarget)) {
3688
+ return true;
3689
+ }
3690
+ return false;
3691
+ }
3692
+ };
3693
+
3694
+ // src/rules/agentsmd-rule.ts
3695
+ var AgentsMdRule = class _AgentsMdRule extends ToolRule {
3696
+ constructor({ fileContent, root, ...rest }) {
3697
+ super({
3698
+ ...rest,
3699
+ fileContent,
3700
+ root: root ?? false
3701
+ });
3702
+ }
3703
+ static getSettablePaths() {
3704
+ return {
3705
+ root: {
3706
+ relativeDirPath: ".",
3707
+ relativeFilePath: "AGENTS.md"
3708
+ },
3709
+ nonRoot: {
3710
+ relativeDirPath: ".agents/memories"
3711
+ }
3712
+ };
3713
+ }
3714
+ static async fromFile({
3715
+ baseDir = ".",
3716
+ relativeFilePath,
3717
+ validate = true
3718
+ }) {
3719
+ const isRoot = relativeFilePath === "AGENTS.md";
3720
+ const relativePath = isRoot ? "AGENTS.md" : (0, import_node_path36.join)(".agents/memories", relativeFilePath);
3721
+ const fileContent = await readFileContent((0, import_node_path36.join)(baseDir, relativePath));
3722
+ return new _AgentsMdRule({
3723
+ baseDir,
3724
+ relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
3725
+ relativeFilePath: isRoot ? "AGENTS.md" : relativeFilePath,
3726
+ fileContent,
3727
+ validate,
3728
+ root: isRoot
3729
+ });
3730
+ }
3731
+ static fromRulesyncRule({
3732
+ baseDir = ".",
3733
+ rulesyncRule,
3734
+ validate = true
3735
+ }) {
3736
+ return new _AgentsMdRule(
3737
+ this.buildToolRuleParamsDefault({
3738
+ baseDir,
3739
+ rulesyncRule,
3740
+ validate,
3741
+ rootPath: this.getSettablePaths().root,
3742
+ nonRootPath: this.getSettablePaths().nonRoot
3743
+ })
3744
+ );
3745
+ }
3746
+ toRulesyncRule() {
3747
+ return this.toRulesyncRuleDefault();
3748
+ }
3749
+ validate() {
3750
+ return { success: true, error: null };
3751
+ }
3752
+ static isTargetedByRulesyncRule(rulesyncRule) {
3753
+ return this.isTargetedByRulesyncRuleDefault({
3754
+ rulesyncRule,
3755
+ toolTarget: "agentsmd"
3756
+ });
3757
+ }
3758
+ };
3759
+
3760
+ // src/rules/amazonqcli-rule.ts
3761
+ var import_node_path37 = require("path");
3762
+ var AmazonQCliRule = class _AmazonQCliRule extends ToolRule {
3763
+ static getSettablePaths() {
3764
+ return {
3765
+ nonRoot: {
3766
+ relativeDirPath: ".amazonq/rules"
3767
+ }
3768
+ };
3769
+ }
3770
+ static async fromFile({
3771
+ baseDir = ".",
3772
+ relativeFilePath,
3773
+ validate = true
3774
+ }) {
3775
+ const fileContent = await readFileContent(
3776
+ (0, import_node_path37.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
3777
+ );
3778
+ return new _AmazonQCliRule({
3779
+ baseDir,
3780
+ relativeDirPath: this.getSettablePaths().nonRoot.relativeDirPath,
3781
+ relativeFilePath,
3782
+ fileContent,
3783
+ validate,
3784
+ root: false
3785
+ });
3786
+ }
3787
+ static fromRulesyncRule({
3788
+ baseDir = ".",
3789
+ rulesyncRule,
3790
+ validate = true
3791
+ }) {
3792
+ return new _AmazonQCliRule(
3793
+ this.buildToolRuleParamsDefault({
3794
+ baseDir,
3795
+ rulesyncRule,
3796
+ validate,
3797
+ nonRootPath: this.getSettablePaths().nonRoot
3798
+ })
3799
+ );
3800
+ }
3801
+ toRulesyncRule() {
3802
+ return this.toRulesyncRuleDefault();
3803
+ }
3804
+ validate() {
3805
+ return { success: true, error: null };
3806
+ }
3807
+ static isTargetedByRulesyncRule(rulesyncRule) {
3808
+ return this.isTargetedByRulesyncRuleDefault({
3809
+ rulesyncRule,
3810
+ toolTarget: "amazonqcli"
3811
+ });
3812
+ }
3813
+ };
3814
+
3815
+ // src/rules/augmentcode-legacy-rule.ts
3816
+ var import_node_path38 = require("path");
3817
+ var AugmentcodeLegacyRule = class _AugmentcodeLegacyRule extends ToolRule {
3818
+ toRulesyncRule() {
3819
+ const rulesyncFrontmatter = {
3820
+ root: this.isRoot(),
3821
+ targets: ["*"],
3822
+ description: "",
3823
+ globs: this.isRoot() ? ["**/*"] : []
3824
+ };
3825
+ return new RulesyncRule({
3826
+ baseDir: this.getBaseDir(),
3827
+ frontmatter: rulesyncFrontmatter,
3828
+ body: this.getFileContent(),
3829
+ relativeDirPath: RULESYNC_RULES_DIR,
3830
+ relativeFilePath: this.getRelativeFilePath(),
3831
+ validate: true
3832
+ });
3833
+ }
3834
+ static getSettablePaths() {
3835
+ return {
3836
+ root: {
3837
+ relativeDirPath: ".",
3838
+ relativeFilePath: ".augment-guidelines"
3839
+ },
3840
+ nonRoot: {
3841
+ relativeDirPath: ".augment/rules"
3842
+ }
3843
+ };
3844
+ }
3845
+ static fromRulesyncRule({
3846
+ baseDir = ".",
3847
+ rulesyncRule,
3848
+ validate = true
3849
+ }) {
3850
+ return new _AugmentcodeLegacyRule(
3851
+ this.buildToolRuleParamsDefault({
3852
+ baseDir,
3853
+ rulesyncRule,
3854
+ validate,
3855
+ rootPath: this.getSettablePaths().root,
3856
+ nonRootPath: this.getSettablePaths().nonRoot
3857
+ })
3858
+ );
3859
+ }
3860
+ validate() {
3861
+ return { success: true, error: null };
3862
+ }
3863
+ static isTargetedByRulesyncRule(rulesyncRule) {
3864
+ return this.isTargetedByRulesyncRuleDefault({
3865
+ rulesyncRule,
3866
+ toolTarget: "augmentcode-legacy"
3867
+ });
3868
+ }
3869
+ static async fromFile({
3870
+ baseDir = ".",
3871
+ relativeFilePath,
3872
+ validate = true
3873
+ }) {
3874
+ const settablePaths = this.getSettablePaths();
3875
+ const isRoot = relativeFilePath === settablePaths.root.relativeFilePath;
3876
+ const relativePath = isRoot ? settablePaths.root.relativeFilePath : (0, import_node_path38.join)(settablePaths.nonRoot.relativeDirPath, relativeFilePath);
3877
+ const fileContent = await readFileContent((0, import_node_path38.join)(baseDir, relativePath));
3878
+ return new _AugmentcodeLegacyRule({
3879
+ baseDir,
3880
+ relativeDirPath: isRoot ? settablePaths.root.relativeDirPath : settablePaths.nonRoot.relativeDirPath,
3881
+ relativeFilePath: isRoot ? settablePaths.root.relativeFilePath : relativeFilePath,
3882
+ fileContent,
3883
+ validate,
3884
+ root: isRoot
3307
3885
  });
3308
3886
  }
3309
3887
  };
3310
3888
 
3311
3889
  // src/rules/augmentcode-rule.ts
3312
- var import_node_path36 = require("path");
3890
+ var import_node_path39 = require("path");
3313
3891
  var AugmentcodeRule = class _AugmentcodeRule extends ToolRule {
3314
3892
  toRulesyncRule() {
3315
3893
  return this.toRulesyncRuleDefault();
@@ -3341,7 +3919,7 @@ var AugmentcodeRule = class _AugmentcodeRule extends ToolRule {
3341
3919
  validate = true
3342
3920
  }) {
3343
3921
  const fileContent = await readFileContent(
3344
- (0, import_node_path36.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
3922
+ (0, import_node_path39.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
3345
3923
  );
3346
3924
  const { body: content } = parseFrontmatter(fileContent);
3347
3925
  return new _AugmentcodeRule({
@@ -3355,10 +3933,16 @@ var AugmentcodeRule = class _AugmentcodeRule extends ToolRule {
3355
3933
  validate() {
3356
3934
  return { success: true, error: null };
3357
3935
  }
3936
+ static isTargetedByRulesyncRule(rulesyncRule) {
3937
+ return this.isTargetedByRulesyncRuleDefault({
3938
+ rulesyncRule,
3939
+ toolTarget: "augmentcode"
3940
+ });
3941
+ }
3358
3942
  };
3359
3943
 
3360
3944
  // src/rules/claudecode-rule.ts
3361
- var import_node_path37 = require("path");
3945
+ var import_node_path40 = require("path");
3362
3946
  var ClaudecodeRule = class _ClaudecodeRule extends ToolRule {
3363
3947
  static getSettablePaths() {
3364
3948
  return {
@@ -3377,8 +3961,8 @@ var ClaudecodeRule = class _ClaudecodeRule extends ToolRule {
3377
3961
  validate = true
3378
3962
  }) {
3379
3963
  const isRoot = relativeFilePath === this.getSettablePaths().root.relativeFilePath;
3380
- const relativePath = isRoot ? this.getSettablePaths().root.relativeFilePath : (0, import_node_path37.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
3381
- const fileContent = await readFileContent((0, import_node_path37.join)(baseDir, relativePath));
3964
+ const relativePath = isRoot ? this.getSettablePaths().root.relativeFilePath : (0, import_node_path40.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
3965
+ const fileContent = await readFileContent((0, import_node_path40.join)(baseDir, relativePath));
3382
3966
  return new _ClaudecodeRule({
3383
3967
  baseDir,
3384
3968
  relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
@@ -3409,13 +3993,19 @@ var ClaudecodeRule = class _ClaudecodeRule extends ToolRule {
3409
3993
  validate() {
3410
3994
  return { success: true, error: null };
3411
3995
  }
3996
+ static isTargetedByRulesyncRule(rulesyncRule) {
3997
+ return this.isTargetedByRulesyncRuleDefault({
3998
+ rulesyncRule,
3999
+ toolTarget: "claudecode"
4000
+ });
4001
+ }
3412
4002
  };
3413
4003
 
3414
4004
  // src/rules/cline-rule.ts
3415
- var import_node_path38 = require("path");
3416
- var import_mini15 = require("zod/mini");
3417
- var ClineRuleFrontmatterSchema = import_mini15.z.object({
3418
- description: import_mini15.z.string()
4005
+ var import_node_path41 = require("path");
4006
+ var import_mini17 = require("zod/mini");
4007
+ var ClineRuleFrontmatterSchema = import_mini17.z.object({
4008
+ description: import_mini17.z.string()
3419
4009
  });
3420
4010
  var ClineRule = class _ClineRule extends ToolRule {
3421
4011
  static getSettablePaths() {
@@ -3445,13 +4035,19 @@ var ClineRule = class _ClineRule extends ToolRule {
3445
4035
  validate() {
3446
4036
  return { success: true, error: null };
3447
4037
  }
4038
+ static isTargetedByRulesyncRule(rulesyncRule) {
4039
+ return this.isTargetedByRulesyncRuleDefault({
4040
+ rulesyncRule,
4041
+ toolTarget: "cline"
4042
+ });
4043
+ }
3448
4044
  static async fromFile({
3449
4045
  baseDir = ".",
3450
4046
  relativeFilePath,
3451
4047
  validate = true
3452
4048
  }) {
3453
4049
  const fileContent = await readFileContent(
3454
- (0, import_node_path38.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
4050
+ (0, import_node_path41.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
3455
4051
  );
3456
4052
  return new _ClineRule({
3457
4053
  baseDir,
@@ -3464,7 +4060,7 @@ var ClineRule = class _ClineRule extends ToolRule {
3464
4060
  };
3465
4061
 
3466
4062
  // src/rules/codexcli-rule.ts
3467
- var import_node_path39 = require("path");
4063
+ var import_node_path42 = require("path");
3468
4064
  var CodexcliRule = class _CodexcliRule extends ToolRule {
3469
4065
  static getSettablePaths() {
3470
4066
  return {
@@ -3483,8 +4079,8 @@ var CodexcliRule = class _CodexcliRule extends ToolRule {
3483
4079
  validate = true
3484
4080
  }) {
3485
4081
  const isRoot = relativeFilePath === "AGENTS.md";
3486
- const relativePath = isRoot ? "AGENTS.md" : (0, import_node_path39.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
3487
- const fileContent = await readFileContent((0, import_node_path39.join)(baseDir, relativePath));
4082
+ const relativePath = isRoot ? "AGENTS.md" : (0, import_node_path42.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
4083
+ const fileContent = await readFileContent((0, import_node_path42.join)(baseDir, relativePath));
3488
4084
  return new _CodexcliRule({
3489
4085
  baseDir,
3490
4086
  relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
@@ -3515,14 +4111,20 @@ var CodexcliRule = class _CodexcliRule extends ToolRule {
3515
4111
  validate() {
3516
4112
  return { success: true, error: null };
3517
4113
  }
4114
+ static isTargetedByRulesyncRule(rulesyncRule) {
4115
+ return this.isTargetedByRulesyncRuleDefault({
4116
+ rulesyncRule,
4117
+ toolTarget: "codexcli"
4118
+ });
4119
+ }
3518
4120
  };
3519
4121
 
3520
4122
  // src/rules/copilot-rule.ts
3521
- var import_node_path40 = require("path");
3522
- var import_mini16 = require("zod/mini");
3523
- var CopilotRuleFrontmatterSchema = import_mini16.z.object({
3524
- description: import_mini16.z.optional(import_mini16.z.string()),
3525
- applyTo: import_mini16.z.optional(import_mini16.z.string())
4123
+ var import_node_path43 = require("path");
4124
+ var import_mini18 = require("zod/mini");
4125
+ var CopilotRuleFrontmatterSchema = import_mini18.z.object({
4126
+ description: import_mini18.z.optional(import_mini18.z.string()),
4127
+ applyTo: import_mini18.z.optional(import_mini18.z.string())
3526
4128
  });
3527
4129
  var CopilotRule = class _CopilotRule extends ToolRule {
3528
4130
  frontmatter;
@@ -3610,11 +4212,11 @@ var CopilotRule = class _CopilotRule extends ToolRule {
3610
4212
  validate = true
3611
4213
  }) {
3612
4214
  const isRoot = relativeFilePath === "copilot-instructions.md";
3613
- const relativePath = isRoot ? (0, import_node_path40.join)(
4215
+ const relativePath = isRoot ? (0, import_node_path43.join)(
3614
4216
  this.getSettablePaths().root.relativeDirPath,
3615
4217
  this.getSettablePaths().root.relativeFilePath
3616
- ) : (0, import_node_path40.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
3617
- const fileContent = await readFileContent((0, import_node_path40.join)(baseDir, relativePath));
4218
+ ) : (0, import_node_path43.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
4219
+ const fileContent = await readFileContent((0, import_node_path43.join)(baseDir, relativePath));
3618
4220
  if (isRoot) {
3619
4221
  return new _CopilotRule({
3620
4222
  baseDir,
@@ -3633,7 +4235,7 @@ var CopilotRule = class _CopilotRule extends ToolRule {
3633
4235
  const result = CopilotRuleFrontmatterSchema.safeParse(frontmatter);
3634
4236
  if (!result.success) {
3635
4237
  throw new Error(
3636
- `Invalid frontmatter in ${(0, import_node_path40.join)(baseDir, relativeFilePath)}: ${result.error.message}`
4238
+ `Invalid frontmatter in ${(0, import_node_path43.join)(baseDir, relativeFilePath)}: ${result.error.message}`
3637
4239
  );
3638
4240
  }
3639
4241
  return new _CopilotRule({
@@ -3663,15 +4265,21 @@ var CopilotRule = class _CopilotRule extends ToolRule {
3663
4265
  getBody() {
3664
4266
  return this.body;
3665
4267
  }
4268
+ static isTargetedByRulesyncRule(rulesyncRule) {
4269
+ return this.isTargetedByRulesyncRuleDefault({
4270
+ rulesyncRule,
4271
+ toolTarget: "copilot"
4272
+ });
4273
+ }
3666
4274
  };
3667
4275
 
3668
4276
  // src/rules/cursor-rule.ts
3669
- var import_node_path41 = require("path");
3670
- var import_mini17 = require("zod/mini");
3671
- var CursorRuleFrontmatterSchema = import_mini17.z.object({
3672
- description: import_mini17.z.optional(import_mini17.z.string()),
3673
- globs: import_mini17.z.optional(import_mini17.z.string()),
3674
- alwaysApply: import_mini17.z.optional(import_mini17.z.boolean())
4277
+ var import_node_path44 = require("path");
4278
+ var import_mini19 = require("zod/mini");
4279
+ var CursorRuleFrontmatterSchema = import_mini19.z.object({
4280
+ description: import_mini19.z.optional(import_mini19.z.string()),
4281
+ globs: import_mini19.z.optional(import_mini19.z.string()),
4282
+ alwaysApply: import_mini19.z.optional(import_mini19.z.boolean())
3675
4283
  });
3676
4284
  var CursorRule = class _CursorRule extends ToolRule {
3677
4285
  frontmatter;
@@ -3796,19 +4404,19 @@ var CursorRule = class _CursorRule extends ToolRule {
3796
4404
  validate = true
3797
4405
  }) {
3798
4406
  const fileContent = await readFileContent(
3799
- (0, import_node_path41.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
4407
+ (0, import_node_path44.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
3800
4408
  );
3801
4409
  const { frontmatter, body: content } = _CursorRule.parseCursorFrontmatter(fileContent);
3802
4410
  const result = CursorRuleFrontmatterSchema.safeParse(frontmatter);
3803
4411
  if (!result.success) {
3804
4412
  throw new Error(
3805
- `Invalid frontmatter in ${(0, import_node_path41.join)(baseDir, relativeFilePath)}: ${result.error.message}`
4413
+ `Invalid frontmatter in ${(0, import_node_path44.join)(baseDir, relativeFilePath)}: ${result.error.message}`
3806
4414
  );
3807
4415
  }
3808
4416
  return new _CursorRule({
3809
4417
  baseDir,
3810
4418
  relativeDirPath: this.getSettablePaths().nonRoot.relativeDirPath,
3811
- relativeFilePath: (0, import_node_path41.basename)(relativeFilePath),
4419
+ relativeFilePath: (0, import_node_path44.basename)(relativeFilePath),
3812
4420
  frontmatter: result.data,
3813
4421
  body: content.trim(),
3814
4422
  validate
@@ -3831,10 +4439,16 @@ var CursorRule = class _CursorRule extends ToolRule {
3831
4439
  getBody() {
3832
4440
  return this.body;
3833
4441
  }
4442
+ static isTargetedByRulesyncRule(rulesyncRule) {
4443
+ return this.isTargetedByRulesyncRuleDefault({
4444
+ rulesyncRule,
4445
+ toolTarget: "cursor"
4446
+ });
4447
+ }
3834
4448
  };
3835
4449
 
3836
4450
  // src/rules/geminicli-rule.ts
3837
- var import_node_path42 = require("path");
4451
+ var import_node_path45 = require("path");
3838
4452
  var GeminiCliRule = class _GeminiCliRule extends ToolRule {
3839
4453
  static getSettablePaths() {
3840
4454
  return {
@@ -3853,8 +4467,8 @@ var GeminiCliRule = class _GeminiCliRule extends ToolRule {
3853
4467
  validate = true
3854
4468
  }) {
3855
4469
  const isRoot = relativeFilePath === "GEMINI.md";
3856
- const relativePath = isRoot ? "GEMINI.md" : (0, import_node_path42.join)(".gemini/memories", relativeFilePath);
3857
- const fileContent = await readFileContent((0, import_node_path42.join)(baseDir, relativePath));
4470
+ const relativePath = isRoot ? "GEMINI.md" : (0, import_node_path45.join)(".gemini/memories", relativeFilePath);
4471
+ const fileContent = await readFileContent((0, import_node_path45.join)(baseDir, relativePath));
3858
4472
  return new _GeminiCliRule({
3859
4473
  baseDir,
3860
4474
  relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
@@ -3885,10 +4499,16 @@ var GeminiCliRule = class _GeminiCliRule extends ToolRule {
3885
4499
  validate() {
3886
4500
  return { success: true, error: null };
3887
4501
  }
4502
+ static isTargetedByRulesyncRule(rulesyncRule) {
4503
+ return this.isTargetedByRulesyncRuleDefault({
4504
+ rulesyncRule,
4505
+ toolTarget: "geminicli"
4506
+ });
4507
+ }
3888
4508
  };
3889
4509
 
3890
4510
  // src/rules/junie-rule.ts
3891
- var import_node_path43 = require("path");
4511
+ var import_node_path46 = require("path");
3892
4512
  var JunieRule = class _JunieRule extends ToolRule {
3893
4513
  static getSettablePaths() {
3894
4514
  return {
@@ -3907,8 +4527,8 @@ var JunieRule = class _JunieRule extends ToolRule {
3907
4527
  validate = true
3908
4528
  }) {
3909
4529
  const isRoot = relativeFilePath === "guidelines.md";
3910
- const relativePath = isRoot ? "guidelines.md" : (0, import_node_path43.join)(".junie/memories", relativeFilePath);
3911
- const fileContent = await readFileContent((0, import_node_path43.join)(baseDir, relativePath));
4530
+ const relativePath = isRoot ? "guidelines.md" : (0, import_node_path46.join)(".junie/memories", relativeFilePath);
4531
+ const fileContent = await readFileContent((0, import_node_path46.join)(baseDir, relativePath));
3912
4532
  return new _JunieRule({
3913
4533
  baseDir,
3914
4534
  relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
@@ -3939,10 +4559,16 @@ var JunieRule = class _JunieRule extends ToolRule {
3939
4559
  validate() {
3940
4560
  return { success: true, error: null };
3941
4561
  }
4562
+ static isTargetedByRulesyncRule(rulesyncRule) {
4563
+ return this.isTargetedByRulesyncRuleDefault({
4564
+ rulesyncRule,
4565
+ toolTarget: "junie"
4566
+ });
4567
+ }
3942
4568
  };
3943
4569
 
3944
4570
  // src/rules/kiro-rule.ts
3945
- var import_node_path44 = require("path");
4571
+ var import_node_path47 = require("path");
3946
4572
  var KiroRule = class _KiroRule extends ToolRule {
3947
4573
  static getSettablePaths() {
3948
4574
  return {
@@ -3957,7 +4583,7 @@ var KiroRule = class _KiroRule extends ToolRule {
3957
4583
  validate = true
3958
4584
  }) {
3959
4585
  const fileContent = await readFileContent(
3960
- (0, import_node_path44.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
4586
+ (0, import_node_path47.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
3961
4587
  );
3962
4588
  return new _KiroRule({
3963
4589
  baseDir,
@@ -3988,10 +4614,16 @@ var KiroRule = class _KiroRule extends ToolRule {
3988
4614
  validate() {
3989
4615
  return { success: true, error: null };
3990
4616
  }
4617
+ static isTargetedByRulesyncRule(rulesyncRule) {
4618
+ return this.isTargetedByRulesyncRuleDefault({
4619
+ rulesyncRule,
4620
+ toolTarget: "kiro"
4621
+ });
4622
+ }
3991
4623
  };
3992
4624
 
3993
4625
  // src/rules/opencode-rule.ts
3994
- var import_node_path45 = require("path");
4626
+ var import_node_path48 = require("path");
3995
4627
  var OpenCodeRule = class _OpenCodeRule extends ToolRule {
3996
4628
  static getSettablePaths() {
3997
4629
  return {
@@ -4010,8 +4642,8 @@ var OpenCodeRule = class _OpenCodeRule extends ToolRule {
4010
4642
  validate = true
4011
4643
  }) {
4012
4644
  const isRoot = relativeFilePath === "AGENTS.md";
4013
- const relativePath = isRoot ? "AGENTS.md" : (0, import_node_path45.join)(".opencode/memories", relativeFilePath);
4014
- const fileContent = await readFileContent((0, import_node_path45.join)(baseDir, relativePath));
4645
+ const relativePath = isRoot ? "AGENTS.md" : (0, import_node_path48.join)(".opencode/memories", relativeFilePath);
4646
+ const fileContent = await readFileContent((0, import_node_path48.join)(baseDir, relativePath));
4015
4647
  return new _OpenCodeRule({
4016
4648
  baseDir,
4017
4649
  relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
@@ -4042,10 +4674,16 @@ var OpenCodeRule = class _OpenCodeRule extends ToolRule {
4042
4674
  validate() {
4043
4675
  return { success: true, error: null };
4044
4676
  }
4677
+ static isTargetedByRulesyncRule(rulesyncRule) {
4678
+ return this.isTargetedByRulesyncRuleDefault({
4679
+ rulesyncRule,
4680
+ toolTarget: "opencode"
4681
+ });
4682
+ }
4045
4683
  };
4046
4684
 
4047
4685
  // src/rules/qwencode-rule.ts
4048
- var import_node_path46 = require("path");
4686
+ var import_node_path49 = require("path");
4049
4687
  var QwencodeRule = class _QwencodeRule extends ToolRule {
4050
4688
  static getSettablePaths() {
4051
4689
  return {
@@ -4064,8 +4702,8 @@ var QwencodeRule = class _QwencodeRule extends ToolRule {
4064
4702
  validate = true
4065
4703
  }) {
4066
4704
  const isRoot = relativeFilePath === "QWEN.md";
4067
- const relativePath = isRoot ? "QWEN.md" : (0, import_node_path46.join)(".qwen/memories", relativeFilePath);
4068
- const fileContent = await readFileContent((0, import_node_path46.join)(baseDir, relativePath));
4705
+ const relativePath = isRoot ? "QWEN.md" : (0, import_node_path49.join)(".qwen/memories", relativeFilePath);
4706
+ const fileContent = await readFileContent((0, import_node_path49.join)(baseDir, relativePath));
4069
4707
  return new _QwencodeRule({
4070
4708
  baseDir,
4071
4709
  relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : this.getSettablePaths().nonRoot.relativeDirPath,
@@ -4093,10 +4731,16 @@ var QwencodeRule = class _QwencodeRule extends ToolRule {
4093
4731
  validate() {
4094
4732
  return { success: true, error: null };
4095
4733
  }
4734
+ static isTargetedByRulesyncRule(rulesyncRule) {
4735
+ return this.isTargetedByRulesyncRuleDefault({
4736
+ rulesyncRule,
4737
+ toolTarget: "qwencode"
4738
+ });
4739
+ }
4096
4740
  };
4097
4741
 
4098
4742
  // src/rules/roo-rule.ts
4099
- var import_node_path47 = require("path");
4743
+ var import_node_path50 = require("path");
4100
4744
  var RooRule = class _RooRule extends ToolRule {
4101
4745
  static getSettablePaths() {
4102
4746
  return {
@@ -4111,7 +4755,7 @@ var RooRule = class _RooRule extends ToolRule {
4111
4755
  validate = true
4112
4756
  }) {
4113
4757
  const fileContent = await readFileContent(
4114
- (0, import_node_path47.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
4758
+ (0, import_node_path50.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
4115
4759
  );
4116
4760
  return new _RooRule({
4117
4761
  baseDir,
@@ -4157,10 +4801,16 @@ var RooRule = class _RooRule extends ToolRule {
4157
4801
  validate() {
4158
4802
  return { success: true, error: null };
4159
4803
  }
4804
+ static isTargetedByRulesyncRule(rulesyncRule) {
4805
+ return this.isTargetedByRulesyncRuleDefault({
4806
+ rulesyncRule,
4807
+ toolTarget: "roo"
4808
+ });
4809
+ }
4160
4810
  };
4161
4811
 
4162
4812
  // src/rules/warp-rule.ts
4163
- var import_node_path48 = require("path");
4813
+ var import_node_path51 = require("path");
4164
4814
  var WarpRule = class _WarpRule extends ToolRule {
4165
4815
  constructor({ fileContent, root, ...rest }) {
4166
4816
  super({
@@ -4186,8 +4836,8 @@ var WarpRule = class _WarpRule extends ToolRule {
4186
4836
  validate = true
4187
4837
  }) {
4188
4838
  const isRoot = relativeFilePath === this.getSettablePaths().root.relativeFilePath;
4189
- const relativePath = isRoot ? this.getSettablePaths().root.relativeFilePath : (0, import_node_path48.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
4190
- const fileContent = await readFileContent((0, import_node_path48.join)(baseDir, relativePath));
4839
+ const relativePath = isRoot ? this.getSettablePaths().root.relativeFilePath : (0, import_node_path51.join)(this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath);
4840
+ const fileContent = await readFileContent((0, import_node_path51.join)(baseDir, relativePath));
4191
4841
  return new _WarpRule({
4192
4842
  baseDir,
4193
4843
  relativeDirPath: isRoot ? this.getSettablePaths().root.relativeDirPath : ".warp",
@@ -4218,10 +4868,16 @@ var WarpRule = class _WarpRule extends ToolRule {
4218
4868
  validate() {
4219
4869
  return { success: true, error: null };
4220
4870
  }
4871
+ static isTargetedByRulesyncRule(rulesyncRule) {
4872
+ return this.isTargetedByRulesyncRuleDefault({
4873
+ rulesyncRule,
4874
+ toolTarget: "warp"
4875
+ });
4876
+ }
4221
4877
  };
4222
4878
 
4223
4879
  // src/rules/windsurf-rule.ts
4224
- var import_node_path49 = require("path");
4880
+ var import_node_path52 = require("path");
4225
4881
  var WindsurfRule = class _WindsurfRule extends ToolRule {
4226
4882
  static getSettablePaths() {
4227
4883
  return {
@@ -4236,7 +4892,7 @@ var WindsurfRule = class _WindsurfRule extends ToolRule {
4236
4892
  validate = true
4237
4893
  }) {
4238
4894
  const fileContent = await readFileContent(
4239
- (0, import_node_path49.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
4895
+ (0, import_node_path52.join)(baseDir, this.getSettablePaths().nonRoot.relativeDirPath, relativeFilePath)
4240
4896
  );
4241
4897
  return new _WindsurfRule({
4242
4898
  baseDir,
@@ -4266,6 +4922,12 @@ var WindsurfRule = class _WindsurfRule extends ToolRule {
4266
4922
  validate() {
4267
4923
  return { success: true, error: null };
4268
4924
  }
4925
+ static isTargetedByRulesyncRule(rulesyncRule) {
4926
+ return this.isTargetedByRulesyncRuleDefault({
4927
+ rulesyncRule,
4928
+ toolTarget: "windsurf"
4929
+ });
4930
+ }
4269
4931
  };
4270
4932
 
4271
4933
  // src/rules/rules-processor.ts
@@ -4288,7 +4950,7 @@ var rulesProcessorToolTargets = [
4288
4950
  "warp",
4289
4951
  "windsurf"
4290
4952
  ];
4291
- var RulesProcessorToolTargetSchema = import_mini18.z.enum(rulesProcessorToolTargets);
4953
+ var RulesProcessorToolTargetSchema = import_mini20.z.enum(rulesProcessorToolTargets);
4292
4954
  var RulesProcessor = class extends FeatureProcessor {
4293
4955
  toolTarget;
4294
4956
  simulateCommands;
@@ -4311,102 +4973,153 @@ var RulesProcessor = class extends FeatureProcessor {
4311
4973
  const toolRules = rulesyncRules.map((rulesyncRule) => {
4312
4974
  switch (this.toolTarget) {
4313
4975
  case "agentsmd":
4976
+ if (!AgentsMdRule.isTargetedByRulesyncRule(rulesyncRule)) {
4977
+ return null;
4978
+ }
4314
4979
  return AgentsMdRule.fromRulesyncRule({
4315
4980
  baseDir: this.baseDir,
4316
4981
  rulesyncRule,
4317
4982
  validate: true
4318
4983
  });
4319
4984
  case "amazonqcli":
4985
+ if (!AmazonQCliRule.isTargetedByRulesyncRule(rulesyncRule)) {
4986
+ return null;
4987
+ }
4320
4988
  return AmazonQCliRule.fromRulesyncRule({
4321
4989
  baseDir: this.baseDir,
4322
4990
  rulesyncRule,
4323
4991
  validate: true
4324
4992
  });
4325
4993
  case "augmentcode":
4994
+ if (!AugmentcodeRule.isTargetedByRulesyncRule(rulesyncRule)) {
4995
+ return null;
4996
+ }
4326
4997
  return AugmentcodeRule.fromRulesyncRule({
4327
4998
  baseDir: this.baseDir,
4328
4999
  rulesyncRule,
4329
5000
  validate: true
4330
5001
  });
4331
5002
  case "augmentcode-legacy":
5003
+ if (!AugmentcodeLegacyRule.isTargetedByRulesyncRule(rulesyncRule)) {
5004
+ return null;
5005
+ }
4332
5006
  return AugmentcodeLegacyRule.fromRulesyncRule({
4333
5007
  baseDir: this.baseDir,
4334
5008
  rulesyncRule,
4335
5009
  validate: true
4336
5010
  });
4337
5011
  case "claudecode":
5012
+ if (!ClaudecodeRule.isTargetedByRulesyncRule(rulesyncRule)) {
5013
+ return null;
5014
+ }
4338
5015
  return ClaudecodeRule.fromRulesyncRule({
4339
5016
  baseDir: this.baseDir,
4340
5017
  rulesyncRule,
4341
5018
  validate: true
4342
5019
  });
4343
5020
  case "cline":
5021
+ if (!ClineRule.isTargetedByRulesyncRule(rulesyncRule)) {
5022
+ return null;
5023
+ }
4344
5024
  return ClineRule.fromRulesyncRule({
4345
5025
  baseDir: this.baseDir,
4346
5026
  rulesyncRule,
4347
5027
  validate: true
4348
5028
  });
4349
5029
  case "codexcli":
5030
+ if (!CodexcliRule.isTargetedByRulesyncRule(rulesyncRule)) {
5031
+ return null;
5032
+ }
4350
5033
  return CodexcliRule.fromRulesyncRule({
4351
5034
  baseDir: this.baseDir,
4352
5035
  rulesyncRule,
4353
5036
  validate: true
4354
5037
  });
4355
5038
  case "copilot":
5039
+ if (!CopilotRule.isTargetedByRulesyncRule(rulesyncRule)) {
5040
+ return null;
5041
+ }
4356
5042
  return CopilotRule.fromRulesyncRule({
4357
5043
  baseDir: this.baseDir,
4358
5044
  rulesyncRule,
4359
5045
  validate: true
4360
5046
  });
4361
5047
  case "cursor":
5048
+ if (!CursorRule.isTargetedByRulesyncRule(rulesyncRule)) {
5049
+ return null;
5050
+ }
4362
5051
  return CursorRule.fromRulesyncRule({
4363
5052
  baseDir: this.baseDir,
4364
5053
  rulesyncRule,
4365
5054
  validate: true
4366
5055
  });
4367
5056
  case "geminicli":
5057
+ if (!GeminiCliRule.isTargetedByRulesyncRule(rulesyncRule)) {
5058
+ return null;
5059
+ }
4368
5060
  return GeminiCliRule.fromRulesyncRule({
4369
5061
  baseDir: this.baseDir,
4370
5062
  rulesyncRule,
4371
5063
  validate: true
4372
5064
  });
4373
5065
  case "junie":
5066
+ if (!JunieRule.isTargetedByRulesyncRule(rulesyncRule)) {
5067
+ return null;
5068
+ }
4374
5069
  return JunieRule.fromRulesyncRule({
4375
5070
  baseDir: this.baseDir,
4376
5071
  rulesyncRule,
4377
5072
  validate: true
4378
5073
  });
4379
5074
  case "kiro":
5075
+ if (!KiroRule.isTargetedByRulesyncRule(rulesyncRule)) {
5076
+ return null;
5077
+ }
4380
5078
  return KiroRule.fromRulesyncRule({
4381
5079
  baseDir: this.baseDir,
4382
5080
  rulesyncRule,
4383
5081
  validate: true
4384
5082
  });
4385
5083
  case "opencode":
5084
+ if (!OpenCodeRule.isTargetedByRulesyncRule(rulesyncRule)) {
5085
+ return null;
5086
+ }
4386
5087
  return OpenCodeRule.fromRulesyncRule({
4387
5088
  baseDir: this.baseDir,
4388
5089
  rulesyncRule,
4389
5090
  validate: true
4390
5091
  });
4391
5092
  case "qwencode":
5093
+ if (!QwencodeRule.isTargetedByRulesyncRule(rulesyncRule)) {
5094
+ return null;
5095
+ }
4392
5096
  return QwencodeRule.fromRulesyncRule({
4393
5097
  baseDir: this.baseDir,
4394
5098
  rulesyncRule,
4395
5099
  validate: true
4396
5100
  });
4397
5101
  case "roo":
5102
+ if (!RooRule.isTargetedByRulesyncRule(rulesyncRule)) {
5103
+ return null;
5104
+ }
4398
5105
  return RooRule.fromRulesyncRule({
4399
5106
  baseDir: this.baseDir,
4400
5107
  rulesyncRule,
4401
5108
  validate: true
4402
5109
  });
4403
5110
  case "warp":
5111
+ if (!WarpRule.isTargetedByRulesyncRule(rulesyncRule)) {
5112
+ return null;
5113
+ }
4404
5114
  return WarpRule.fromRulesyncRule({
4405
5115
  baseDir: this.baseDir,
4406
5116
  rulesyncRule,
4407
5117
  validate: true
4408
5118
  });
4409
5119
  case "windsurf":
5120
+ if (!WindsurfRule.isTargetedByRulesyncRule(rulesyncRule)) {
5121
+ return null;
5122
+ }
4410
5123
  return WindsurfRule.fromRulesyncRule({
4411
5124
  baseDir: this.baseDir,
4412
5125
  rulesyncRule,
@@ -4415,8 +5128,9 @@ var RulesProcessor = class extends FeatureProcessor {
4415
5128
  default:
4416
5129
  throw new Error(`Unsupported tool target: ${this.toolTarget}`);
4417
5130
  }
4418
- });
4419
- if (this.toolTarget === "cursor" && (this.simulateCommands || this.simulateSubagents)) {
5131
+ }).filter((rule) => rule !== null);
5132
+ const isSimulated = this.simulateCommands || this.simulateSubagents;
5133
+ if (isSimulated && this.toolTarget === "cursor") {
4420
5134
  toolRules.push(
4421
5135
  new CursorRule({
4422
5136
  baseDir: this.baseDir,
@@ -4435,6 +5149,22 @@ var RulesProcessor = class extends FeatureProcessor {
4435
5149
  })
4436
5150
  );
4437
5151
  }
5152
+ if (isSimulated && this.toolTarget === "roo") {
5153
+ toolRules.push(
5154
+ new RooRule({
5155
+ baseDir: this.baseDir,
5156
+ relativeDirPath: RooRule.getSettablePaths().nonRoot.relativeDirPath,
5157
+ relativeFilePath: "additional-conventions.md",
5158
+ fileContent: this.generateAdditionalConventionsSection({
5159
+ commands: { relativeDirPath: RooCommand.getSettablePaths().relativeDirPath },
5160
+ subagents: {
5161
+ relativeDirPath: RooSubagent.getSettablePaths().relativeDirPath
5162
+ }
5163
+ }),
5164
+ validate: true
5165
+ })
5166
+ );
5167
+ }
4438
5168
  const rootRuleIndex = toolRules.findIndex((rule) => rule.isRoot());
4439
5169
  if (rootRuleIndex === -1) {
4440
5170
  return toolRules;
@@ -4488,7 +5218,12 @@ var RulesProcessor = class extends FeatureProcessor {
4488
5218
  case "geminicli": {
4489
5219
  const rootRule = toolRules[rootRuleIndex];
4490
5220
  rootRule?.setFileContent(
4491
- this.generateXmlReferencesSection(toolRules) + rootRule.getFileContent()
5221
+ this.generateXmlReferencesSection(toolRules) + this.generateAdditionalConventionsSection({
5222
+ commands: { relativeDirPath: GeminiCliCommand.getSettablePaths().relativeDirPath },
5223
+ subagents: {
5224
+ relativeDirPath: GeminiCliSubagent.getSettablePaths().relativeDirPath
5225
+ }
5226
+ }) + rootRule.getFileContent()
4492
5227
  );
4493
5228
  return toolRules;
4494
5229
  }
@@ -4536,17 +5271,17 @@ var RulesProcessor = class extends FeatureProcessor {
4536
5271
  * Load and parse rulesync rule files from .rulesync/rules/ directory
4537
5272
  */
4538
5273
  async loadRulesyncFiles() {
4539
- const files = await findFilesByGlobs((0, import_node_path50.join)(RULESYNC_RULES_DIR, "*.md"));
5274
+ const files = await findFilesByGlobs((0, import_node_path53.join)(RULESYNC_RULES_DIR, "*.md"));
4540
5275
  logger.debug(`Found ${files.length} rulesync files`);
4541
5276
  return Promise.all(
4542
- files.map((file) => RulesyncRule.fromFile({ relativeFilePath: (0, import_node_path50.basename)(file) }))
5277
+ files.map((file) => RulesyncRule.fromFile({ relativeFilePath: (0, import_node_path53.basename)(file) }))
4543
5278
  );
4544
5279
  }
4545
5280
  async loadRulesyncFilesLegacy() {
4546
- const legacyFiles = await findFilesByGlobs((0, import_node_path50.join)(RULESYNC_RULES_DIR_LEGACY, "*.md"));
5281
+ const legacyFiles = await findFilesByGlobs((0, import_node_path53.join)(RULESYNC_RULES_DIR_LEGACY, "*.md"));
4547
5282
  logger.debug(`Found ${legacyFiles.length} legacy rulesync files`);
4548
5283
  return Promise.all(
4549
- legacyFiles.map((file) => RulesyncRule.fromFileLegacy({ relativeFilePath: (0, import_node_path50.basename)(file) }))
5284
+ legacyFiles.map((file) => RulesyncRule.fromFileLegacy({ relativeFilePath: (0, import_node_path53.basename)(file) }))
4550
5285
  );
4551
5286
  }
4552
5287
  /**
@@ -4599,793 +5334,413 @@ var RulesProcessor = class extends FeatureProcessor {
4599
5334
  }
4600
5335
  }
4601
5336
  async loadToolRulesDefault({
4602
- root,
4603
- nonRoot
4604
- }) {
4605
- const rootToolRules = await (async () => {
4606
- if (!root) {
4607
- return [];
4608
- }
4609
- const rootFilePaths = await findFilesByGlobs(
4610
- (0, import_node_path50.join)(this.baseDir, root.relativeDirPath ?? ".", root.relativeFilePath)
4611
- );
4612
- return await Promise.all(
4613
- rootFilePaths.map(
4614
- (filePath) => root.fromFile({
4615
- baseDir: this.baseDir,
4616
- relativeFilePath: (0, import_node_path50.basename)(filePath)
4617
- })
4618
- )
4619
- );
4620
- })();
4621
- logger.debug(`Found ${rootToolRules.length} root tool rule files`);
4622
- const nonRootToolRules = await (async () => {
4623
- if (!nonRoot) {
4624
- return [];
4625
- }
4626
- const nonRootFilePaths = await findFilesByGlobs(
4627
- (0, import_node_path50.join)(this.baseDir, nonRoot.relativeDirPath, `*.${nonRoot.extension}`)
4628
- );
4629
- return await Promise.all(
4630
- nonRootFilePaths.map(
4631
- (filePath) => nonRoot.fromFile({
4632
- baseDir: this.baseDir,
4633
- relativeFilePath: (0, import_node_path50.basename)(filePath)
4634
- })
4635
- )
4636
- );
4637
- })();
4638
- logger.debug(`Found ${nonRootToolRules.length} non-root tool rule files`);
4639
- return [...rootToolRules, ...nonRootToolRules];
4640
- }
4641
- /**
4642
- * Load AGENTS.md rule configuration
4643
- */
4644
- async loadAgentsmdRules() {
4645
- const settablePaths = AgentsMdRule.getSettablePaths();
4646
- return await this.loadToolRulesDefault({
4647
- root: {
4648
- relativeDirPath: settablePaths.root.relativeDirPath,
4649
- relativeFilePath: settablePaths.root.relativeFilePath,
4650
- fromFile: (params) => AgentsMdRule.fromFile(params)
4651
- },
4652
- nonRoot: {
4653
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4654
- fromFile: (params) => AgentsMdRule.fromFile(params),
4655
- extension: "md"
4656
- }
4657
- });
4658
- }
4659
- async loadWarpRules() {
4660
- const settablePaths = WarpRule.getSettablePaths();
4661
- return await this.loadToolRulesDefault({
4662
- root: {
4663
- relativeDirPath: settablePaths.root.relativeDirPath,
4664
- relativeFilePath: settablePaths.root.relativeFilePath,
4665
- fromFile: (params) => WarpRule.fromFile(params)
4666
- },
4667
- nonRoot: {
4668
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4669
- fromFile: (params) => WarpRule.fromFile(params),
4670
- extension: "md"
4671
- }
4672
- });
4673
- }
4674
- /**
4675
- * Load Amazon Q Developer CLI rule configurations from .amazonq/rules/ directory
4676
- */
4677
- async loadAmazonqcliRules() {
4678
- const settablePaths = AmazonQCliRule.getSettablePaths();
4679
- return await this.loadToolRulesDefault({
4680
- nonRoot: {
4681
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4682
- fromFile: (params) => AmazonQCliRule.fromFile(params),
4683
- extension: "md"
4684
- }
4685
- });
4686
- }
4687
- /**
4688
- * Load AugmentCode rule configurations from .augment/rules/ directory
4689
- */
4690
- async loadAugmentcodeRules() {
4691
- const settablePaths = AugmentcodeRule.getSettablePaths();
4692
- return await this.loadToolRulesDefault({
4693
- nonRoot: {
4694
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4695
- fromFile: (params) => AugmentcodeRule.fromFile(params),
4696
- extension: "md"
4697
- }
4698
- });
4699
- }
4700
- /**
4701
- * Load AugmentCode legacy rule configuration from .augment-guidelines file and .augment/rules/ directory
4702
- */
4703
- async loadAugmentcodeLegacyRules() {
4704
- const settablePaths = AugmentcodeLegacyRule.getSettablePaths();
4705
- return await this.loadToolRulesDefault({
4706
- root: {
4707
- relativeDirPath: settablePaths.root.relativeDirPath,
4708
- relativeFilePath: settablePaths.root.relativeFilePath,
4709
- fromFile: (params) => AugmentcodeLegacyRule.fromFile(params)
4710
- },
4711
- nonRoot: {
4712
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4713
- fromFile: (params) => AugmentcodeLegacyRule.fromFile(params),
4714
- extension: "md"
4715
- }
4716
- });
4717
- }
4718
- /**
4719
- * Load Claude Code rule configuration from CLAUDE.md file
4720
- */
4721
- async loadClaudecodeRules() {
4722
- const settablePaths = ClaudecodeRule.getSettablePaths();
4723
- return await this.loadToolRulesDefault({
4724
- root: {
4725
- relativeDirPath: settablePaths.root.relativeDirPath,
4726
- relativeFilePath: settablePaths.root.relativeFilePath,
4727
- fromFile: (params) => ClaudecodeRule.fromFile(params)
4728
- },
4729
- nonRoot: {
4730
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4731
- fromFile: (params) => ClaudecodeRule.fromFile(params),
4732
- extension: "md"
4733
- }
4734
- });
4735
- }
4736
- /**
4737
- * Load Cline rule configurations from .clinerules/ directory
4738
- */
4739
- async loadClineRules() {
4740
- const settablePaths = ClineRule.getSettablePaths();
4741
- return await this.loadToolRulesDefault({
4742
- nonRoot: {
4743
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4744
- fromFile: (params) => ClineRule.fromFile(params),
4745
- extension: "md"
4746
- }
4747
- });
4748
- }
4749
- /**
4750
- * Load OpenAI Codex CLI rule configuration from AGENTS.md and .codex/memories/*.md files
4751
- */
4752
- async loadCodexcliRules() {
4753
- const settablePaths = CodexcliRule.getSettablePaths();
4754
- return await this.loadToolRulesDefault({
4755
- root: {
4756
- relativeDirPath: settablePaths.root.relativeDirPath,
4757
- relativeFilePath: settablePaths.root.relativeFilePath,
4758
- fromFile: (params) => CodexcliRule.fromFile(params)
4759
- },
4760
- nonRoot: {
4761
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4762
- fromFile: (params) => CodexcliRule.fromFile(params),
4763
- extension: "md"
4764
- }
4765
- });
4766
- }
4767
- /**
4768
- * Load GitHub Copilot rule configuration from .github/copilot-instructions.md file
4769
- */
4770
- async loadCopilotRules() {
4771
- const settablePaths = CopilotRule.getSettablePaths();
4772
- return await this.loadToolRulesDefault({
4773
- root: {
4774
- relativeDirPath: settablePaths.root.relativeDirPath,
4775
- relativeFilePath: settablePaths.root.relativeFilePath,
4776
- fromFile: (params) => CopilotRule.fromFile(params)
4777
- },
4778
- nonRoot: {
4779
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4780
- fromFile: (params) => CopilotRule.fromFile(params),
4781
- extension: "md"
4782
- }
4783
- });
4784
- }
4785
- /**
4786
- * Load Cursor rule configurations from .cursor/rules/ directory
4787
- */
4788
- async loadCursorRules() {
4789
- const settablePaths = CursorRule.getSettablePaths();
4790
- return await this.loadToolRulesDefault({
4791
- nonRoot: {
4792
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4793
- fromFile: (params) => CursorRule.fromFile(params),
4794
- extension: "mdc"
4795
- }
4796
- });
4797
- }
4798
- /**
4799
- * Load Gemini CLI rule configuration from GEMINI.md file
4800
- */
4801
- async loadGeminicliRules() {
4802
- const settablePaths = GeminiCliRule.getSettablePaths();
4803
- return await this.loadToolRulesDefault({
4804
- root: {
4805
- relativeDirPath: settablePaths.root.relativeDirPath,
4806
- relativeFilePath: settablePaths.root.relativeFilePath,
4807
- fromFile: (params) => GeminiCliRule.fromFile(params)
4808
- },
4809
- nonRoot: {
4810
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4811
- fromFile: (params) => GeminiCliRule.fromFile(params),
4812
- extension: "md"
4813
- }
4814
- });
4815
- }
4816
- /**
4817
- * Load JetBrains Junie rule configuration from .junie/guidelines.md file
4818
- */
4819
- async loadJunieRules() {
4820
- const settablePaths = JunieRule.getSettablePaths();
4821
- return await this.loadToolRulesDefault({
4822
- root: {
4823
- relativeDirPath: settablePaths.root.relativeDirPath,
4824
- relativeFilePath: settablePaths.root.relativeFilePath,
4825
- fromFile: (params) => JunieRule.fromFile(params)
4826
- },
4827
- nonRoot: {
4828
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4829
- fromFile: (params) => JunieRule.fromFile(params),
4830
- extension: "md"
4831
- }
4832
- });
4833
- }
4834
- /**
4835
- * Load Kiro rule configurations from .kiro/steering/ directory
4836
- */
4837
- async loadKiroRules() {
4838
- const settablePaths = KiroRule.getSettablePaths();
4839
- return await this.loadToolRulesDefault({
4840
- nonRoot: {
4841
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4842
- fromFile: (params) => KiroRule.fromFile(params),
4843
- extension: "md"
5337
+ root,
5338
+ nonRoot
5339
+ }) {
5340
+ const rootToolRules = await (async () => {
5341
+ if (!root) {
5342
+ return [];
4844
5343
  }
4845
- });
5344
+ const rootFilePaths = await findFilesByGlobs(
5345
+ (0, import_node_path53.join)(this.baseDir, root.relativeDirPath ?? ".", root.relativeFilePath)
5346
+ );
5347
+ return await Promise.all(
5348
+ rootFilePaths.map(
5349
+ (filePath) => root.fromFile({
5350
+ baseDir: this.baseDir,
5351
+ relativeFilePath: (0, import_node_path53.basename)(filePath)
5352
+ })
5353
+ )
5354
+ );
5355
+ })();
5356
+ logger.debug(`Found ${rootToolRules.length} root tool rule files`);
5357
+ const nonRootToolRules = await (async () => {
5358
+ if (!nonRoot) {
5359
+ return [];
5360
+ }
5361
+ const nonRootFilePaths = await findFilesByGlobs(
5362
+ (0, import_node_path53.join)(this.baseDir, nonRoot.relativeDirPath, `*.${nonRoot.extension}`)
5363
+ );
5364
+ return await Promise.all(
5365
+ nonRootFilePaths.map(
5366
+ (filePath) => nonRoot.fromFile({
5367
+ baseDir: this.baseDir,
5368
+ relativeFilePath: (0, import_node_path53.basename)(filePath)
5369
+ })
5370
+ )
5371
+ );
5372
+ })();
5373
+ logger.debug(`Found ${nonRootToolRules.length} non-root tool rule files`);
5374
+ return [...rootToolRules, ...nonRootToolRules];
4846
5375
  }
4847
5376
  /**
4848
- * Load OpenCode rule configuration from AGENTS.md file and .opencode/memories/*.md files
5377
+ * Load AGENTS.md rule configuration
4849
5378
  */
4850
- async loadOpencodeRules() {
4851
- const settablePaths = OpenCodeRule.getSettablePaths();
5379
+ async loadAgentsmdRules() {
5380
+ const settablePaths = AgentsMdRule.getSettablePaths();
4852
5381
  return await this.loadToolRulesDefault({
4853
5382
  root: {
4854
5383
  relativeDirPath: settablePaths.root.relativeDirPath,
4855
5384
  relativeFilePath: settablePaths.root.relativeFilePath,
4856
- fromFile: (params) => OpenCodeRule.fromFile(params)
5385
+ fromFile: (params) => AgentsMdRule.fromFile(params)
4857
5386
  },
4858
5387
  nonRoot: {
4859
5388
  relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4860
- fromFile: (params) => OpenCodeRule.fromFile(params),
5389
+ fromFile: (params) => AgentsMdRule.fromFile(params),
4861
5390
  extension: "md"
4862
5391
  }
4863
5392
  });
4864
5393
  }
4865
- /**
4866
- * Load Qwen Code rule configuration from QWEN.md file and .qwen/memories/*.md files
4867
- */
4868
- async loadQwencodeRules() {
4869
- const settablePaths = QwencodeRule.getSettablePaths();
5394
+ async loadWarpRules() {
5395
+ const settablePaths = WarpRule.getSettablePaths();
4870
5396
  return await this.loadToolRulesDefault({
4871
5397
  root: {
4872
5398
  relativeDirPath: settablePaths.root.relativeDirPath,
4873
5399
  relativeFilePath: settablePaths.root.relativeFilePath,
4874
- fromFile: (params) => QwencodeRule.fromFile(params)
5400
+ fromFile: (params) => WarpRule.fromFile(params)
4875
5401
  },
4876
5402
  nonRoot: {
4877
5403
  relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4878
- fromFile: (params) => QwencodeRule.fromFile(params),
4879
- extension: "md"
4880
- }
4881
- });
4882
- }
4883
- /**
4884
- * Load Roo Code rule configurations from .roo/rules/ directory
4885
- */
4886
- async loadRooRules() {
4887
- const settablePaths = RooRule.getSettablePaths();
4888
- return await this.loadToolRulesDefault({
4889
- nonRoot: {
4890
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4891
- fromFile: (params) => RooRule.fromFile(params),
4892
- extension: "md"
4893
- }
4894
- });
4895
- }
4896
- /**
4897
- * Load Windsurf rule configurations from .windsurf/rules/ directory
4898
- */
4899
- async loadWindsurfRules() {
4900
- const settablePaths = WindsurfRule.getSettablePaths();
4901
- return await this.loadToolRulesDefault({
4902
- nonRoot: {
4903
- relativeDirPath: settablePaths.nonRoot.relativeDirPath,
4904
- fromFile: (params) => WindsurfRule.fromFile(params),
4905
- extension: "md"
4906
- }
4907
- });
4908
- }
4909
- /**
4910
- * Implementation of abstract method from FeatureProcessor
4911
- * Return the tool targets that this processor supports
4912
- */
4913
- static getToolTargets() {
4914
- return rulesProcessorToolTargets;
4915
- }
4916
- generateXmlReferencesSection(toolRules) {
4917
- const toolRulesWithoutRoot = toolRules.filter((rule) => !rule.isRoot());
4918
- if (toolRulesWithoutRoot.length === 0) {
4919
- return "";
4920
- }
4921
- const lines = [];
4922
- lines.push(
4923
- "Please also reference the following documents as needed. In this case, `@` stands for the project root directory."
4924
- );
4925
- lines.push("");
4926
- const documentsData = {
4927
- Documents: {
4928
- Document: toolRulesWithoutRoot.map((rule) => {
4929
- const rulesyncRule = rule.toRulesyncRule();
4930
- const frontmatter = rulesyncRule.getFrontmatter();
4931
- const relativePath = `@${rule.getRelativePathFromCwd()}`;
4932
- const document = {
4933
- Path: relativePath
4934
- };
4935
- if (frontmatter.description) {
4936
- document.Description = frontmatter.description;
4937
- }
4938
- if (frontmatter.globs && frontmatter.globs.length > 0) {
4939
- document.FilePatterns = frontmatter.globs.join(", ");
4940
- }
4941
- return document;
4942
- })
4943
- }
4944
- };
4945
- const builder = new import_fast_xml_parser.XMLBuilder({
4946
- format: true,
4947
- ignoreAttributes: false,
4948
- suppressEmptyNode: false
4949
- });
4950
- const xmlContent = builder.build(documentsData);
4951
- lines.push(xmlContent);
4952
- return lines.join("\n") + "\n";
4953
- }
4954
- generateReferencesSection(toolRules) {
4955
- const toolRulesWithoutRoot = toolRules.filter((rule) => !rule.isRoot());
4956
- if (toolRulesWithoutRoot.length === 0) {
4957
- return "";
4958
- }
4959
- const lines = [];
4960
- lines.push("Please also reference the following documents as needed:");
4961
- lines.push("");
4962
- for (const rule of toolRulesWithoutRoot) {
4963
- const rulesyncRule = rule.toRulesyncRule();
4964
- const frontmatter = rulesyncRule.getFrontmatter();
4965
- const escapedDescription = frontmatter.description?.replace(/"/g, '\\"');
4966
- const globsText = frontmatter.globs?.join(",");
4967
- lines.push(
4968
- `@${rule.getRelativePathFromCwd()} description: "${escapedDescription}" globs: "${globsText}"`
4969
- );
4970
- }
4971
- return lines.join("\n") + "\n";
4972
- }
4973
- generateAdditionalConventionsSection({
4974
- commands,
4975
- subagents
4976
- }) {
4977
- return `# Additional Conventions Beyond the Built-in Functions
4978
-
4979
- As this project's AI coding tool, you must follow the additional conventions below, in addition to the built-in functions.
4980
-
4981
- ${this.simulateCommands ? `## Simulated Custom Slash Commands
4982
-
4983
- Custom slash commands allow you to define frequently-used prompts as Markdown files that you can execute.
4984
-
4985
- ### Syntax
4986
-
4987
- Users can use following syntax to invoke a custom command.
4988
-
4989
- \`\`\`txt
4990
- s/<command> [arguments]
4991
- \`\`\`
4992
-
4993
- This syntax employs a double slash (\`s/\`) to prevent conflicts with built-in slash commands.
4994
- The \`s\` in \`s/\` stands for *simulate*. Because custom slash commands are not built-in, this syntax provides a pseudo way to invoke them.
4995
-
4996
- When users call a custom slash command, you have to look for the markdown file, \`${(0, import_node_path50.join)(commands.relativeDirPath, "{command}.md")}\`, then execute the contents of that file as the block of operations.` : ""}
4997
-
4998
- ${this.simulateSubagents ? `## Simulated Subagents
4999
-
5000
- Simulated subagents are specialized AI assistants that can be invoked to handle specific types of tasks. In this case, it can be appear something like simulated custom slash commands simply. Simulated subagents can be called by simulated custom slash commands.
5001
-
5002
- When users call a simulated subagent, it will look for the corresponding markdown file, \`${(0, import_node_path50.join)(subagents.relativeDirPath, "{subagent}.md")}\`, and execute its contents as the block of operations.` : ""}`.trim();
5003
- }
5004
- };
5005
-
5006
- // src/subagents/subagents-processor.ts
5007
- var import_node_path53 = require("path");
5008
- var import_mini21 = require("zod/mini");
5009
-
5010
- // src/subagents/claudecode-subagent.ts
5011
- var import_node_path52 = require("path");
5012
- var import_mini20 = require("zod/mini");
5013
-
5014
- // src/subagents/rulesync-subagent.ts
5015
- var import_node_path51 = require("path");
5016
- var import_mini19 = require("zod/mini");
5017
- var RulesyncSubagentModelSchema = import_mini19.z.enum(["opus", "sonnet", "haiku", "inherit"]);
5018
- var RulesyncSubagentFrontmatterSchema = import_mini19.z.object({
5019
- targets: RulesyncTargetsSchema,
5020
- name: import_mini19.z.string(),
5021
- description: import_mini19.z.string(),
5022
- claudecode: import_mini19.z.optional(
5023
- import_mini19.z.object({
5024
- model: RulesyncSubagentModelSchema
5025
- })
5026
- )
5027
- });
5028
- var RulesyncSubagent = class _RulesyncSubagent extends RulesyncFile {
5029
- frontmatter;
5030
- body;
5031
- constructor({ frontmatter, body, ...rest }) {
5032
- if (rest.validate !== false) {
5033
- const result = RulesyncSubagentFrontmatterSchema.safeParse(frontmatter);
5034
- if (!result.success) {
5035
- throw result.error;
5036
- }
5037
- }
5038
- super({
5039
- ...rest
5040
- });
5041
- this.frontmatter = frontmatter;
5042
- this.body = body;
5043
- }
5044
- static getSettablePaths() {
5045
- return {
5046
- relativeDirPath: ".rulesync/subagents"
5047
- };
5048
- }
5049
- getFrontmatter() {
5050
- return this.frontmatter;
5051
- }
5052
- getBody() {
5053
- return this.body;
5054
- }
5055
- validate() {
5056
- if (!this.frontmatter) {
5057
- return { success: true, error: null };
5058
- }
5059
- const result = RulesyncSubagentFrontmatterSchema.safeParse(this.frontmatter);
5060
- if (result.success) {
5061
- return { success: true, error: null };
5062
- } else {
5063
- return { success: false, error: result.error };
5064
- }
5065
- }
5066
- static async fromFile({
5067
- relativeFilePath
5068
- }) {
5069
- const fileContent = await readFileContent((0, import_node_path51.join)(RULESYNC_SUBAGENTS_DIR, relativeFilePath));
5070
- const { frontmatter, body: content } = parseFrontmatter(fileContent);
5071
- const result = RulesyncSubagentFrontmatterSchema.safeParse(frontmatter);
5072
- if (!result.success) {
5073
- throw new Error(`Invalid frontmatter in ${relativeFilePath}: ${result.error.message}`);
5074
- }
5075
- const filename = (0, import_node_path51.basename)(relativeFilePath);
5076
- return new _RulesyncSubagent({
5077
- baseDir: ".",
5078
- relativeDirPath: this.getSettablePaths().relativeDirPath,
5079
- relativeFilePath: filename,
5080
- frontmatter: result.data,
5081
- body: content.trim(),
5082
- fileContent
5083
- });
5084
- }
5085
- };
5086
-
5087
- // src/subagents/claudecode-subagent.ts
5088
- var ClaudecodeSubagentFrontmatterSchema = import_mini20.z.object({
5089
- name: import_mini20.z.string(),
5090
- description: import_mini20.z.string(),
5091
- model: import_mini20.z.optional(import_mini20.z.enum(["opus", "sonnet", "haiku", "inherit"]))
5092
- });
5093
- var ClaudecodeSubagent = class _ClaudecodeSubagent extends ToolSubagent {
5094
- frontmatter;
5095
- body;
5096
- constructor({ frontmatter, body, ...rest }) {
5097
- if (rest.validate !== false) {
5098
- const result = ClaudecodeSubagentFrontmatterSchema.safeParse(frontmatter);
5099
- if (!result.success) {
5100
- throw result.error;
5404
+ fromFile: (params) => WarpRule.fromFile(params),
5405
+ extension: "md"
5101
5406
  }
5102
- }
5103
- super({
5104
- ...rest
5105
5407
  });
5106
- this.frontmatter = frontmatter;
5107
- this.body = body;
5108
- }
5109
- static getSettablePaths() {
5110
- return {
5111
- relativeDirPath: ".claude/agents"
5112
- };
5113
5408
  }
5114
- getFrontmatter() {
5115
- return this.frontmatter;
5116
- }
5117
- getBody() {
5118
- return this.body;
5409
+ /**
5410
+ * Load Amazon Q Developer CLI rule configurations from .amazonq/rules/ directory
5411
+ */
5412
+ async loadAmazonqcliRules() {
5413
+ const settablePaths = AmazonQCliRule.getSettablePaths();
5414
+ return await this.loadToolRulesDefault({
5415
+ nonRoot: {
5416
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5417
+ fromFile: (params) => AmazonQCliRule.fromFile(params),
5418
+ extension: "md"
5419
+ }
5420
+ });
5119
5421
  }
5120
- toRulesyncSubagent() {
5121
- const rulesyncFrontmatter = {
5122
- targets: ["claudecode"],
5123
- name: this.frontmatter.name,
5124
- description: this.frontmatter.description,
5125
- ...this.frontmatter.model && {
5126
- claudecode: {
5127
- model: this.frontmatter.model
5128
- }
5422
+ /**
5423
+ * Load AugmentCode rule configurations from .augment/rules/ directory
5424
+ */
5425
+ async loadAugmentcodeRules() {
5426
+ const settablePaths = AugmentcodeRule.getSettablePaths();
5427
+ return await this.loadToolRulesDefault({
5428
+ nonRoot: {
5429
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5430
+ fromFile: (params) => AugmentcodeRule.fromFile(params),
5431
+ extension: "md"
5129
5432
  }
5130
- };
5131
- const fileContent = stringifyFrontmatter(this.body, rulesyncFrontmatter);
5132
- return new RulesyncSubagent({
5133
- frontmatter: rulesyncFrontmatter,
5134
- body: this.body,
5135
- baseDir: this.baseDir,
5136
- relativeDirPath: ".rulesync/subagents",
5137
- relativeFilePath: this.getRelativeFilePath(),
5138
- fileContent,
5139
- validate: true
5140
5433
  });
5141
5434
  }
5142
- static fromRulesyncSubagent({
5143
- baseDir = ".",
5144
- rulesyncSubagent,
5145
- validate = true
5146
- }) {
5147
- const rulesyncFrontmatter = rulesyncSubagent.getFrontmatter();
5148
- const claudecodeFrontmatter = {
5149
- name: rulesyncFrontmatter.name,
5150
- description: rulesyncFrontmatter.description,
5151
- model: rulesyncFrontmatter.claudecode?.model
5152
- };
5153
- const body = rulesyncSubagent.getBody();
5154
- const fileContent = stringifyFrontmatter(body, claudecodeFrontmatter);
5155
- return new _ClaudecodeSubagent({
5156
- baseDir,
5157
- frontmatter: claudecodeFrontmatter,
5158
- body,
5159
- relativeDirPath: ".claude/agents",
5160
- relativeFilePath: rulesyncSubagent.getRelativeFilePath(),
5161
- fileContent,
5162
- validate
5435
+ /**
5436
+ * Load AugmentCode legacy rule configuration from .augment-guidelines file and .augment/rules/ directory
5437
+ */
5438
+ async loadAugmentcodeLegacyRules() {
5439
+ const settablePaths = AugmentcodeLegacyRule.getSettablePaths();
5440
+ return await this.loadToolRulesDefault({
5441
+ root: {
5442
+ relativeDirPath: settablePaths.root.relativeDirPath,
5443
+ relativeFilePath: settablePaths.root.relativeFilePath,
5444
+ fromFile: (params) => AugmentcodeLegacyRule.fromFile(params)
5445
+ },
5446
+ nonRoot: {
5447
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5448
+ fromFile: (params) => AugmentcodeLegacyRule.fromFile(params),
5449
+ extension: "md"
5450
+ }
5163
5451
  });
5164
5452
  }
5165
- validate() {
5166
- if (!this.frontmatter) {
5167
- return { success: true, error: null };
5168
- }
5169
- const result = ClaudecodeSubagentFrontmatterSchema.safeParse(this.frontmatter);
5170
- if (result.success) {
5171
- return { success: true, error: null };
5172
- } else {
5173
- return { success: false, error: result.error };
5174
- }
5453
+ /**
5454
+ * Load Claude Code rule configuration from CLAUDE.md file
5455
+ */
5456
+ async loadClaudecodeRules() {
5457
+ const settablePaths = ClaudecodeRule.getSettablePaths();
5458
+ return await this.loadToolRulesDefault({
5459
+ root: {
5460
+ relativeDirPath: settablePaths.root.relativeDirPath,
5461
+ relativeFilePath: settablePaths.root.relativeFilePath,
5462
+ fromFile: (params) => ClaudecodeRule.fromFile(params)
5463
+ },
5464
+ nonRoot: {
5465
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5466
+ fromFile: (params) => ClaudecodeRule.fromFile(params),
5467
+ extension: "md"
5468
+ }
5469
+ });
5175
5470
  }
5176
- static async fromFile({
5177
- baseDir = ".",
5178
- relativeFilePath,
5179
- validate = true
5180
- }) {
5181
- const fileContent = await readFileContent((0, import_node_path52.join)(baseDir, ".claude/agents", relativeFilePath));
5182
- const { frontmatter, body: content } = parseFrontmatter(fileContent);
5183
- const result = ClaudecodeSubagentFrontmatterSchema.safeParse(frontmatter);
5184
- if (!result.success) {
5185
- throw new Error(`Invalid frontmatter in ${relativeFilePath}: ${result.error.message}`);
5186
- }
5187
- return new _ClaudecodeSubagent({
5188
- baseDir,
5189
- relativeDirPath: ".claude/agents",
5190
- relativeFilePath,
5191
- frontmatter: result.data,
5192
- body: content.trim(),
5193
- fileContent,
5194
- validate
5471
+ /**
5472
+ * Load Cline rule configurations from .clinerules/ directory
5473
+ */
5474
+ async loadClineRules() {
5475
+ const settablePaths = ClineRule.getSettablePaths();
5476
+ return await this.loadToolRulesDefault({
5477
+ nonRoot: {
5478
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5479
+ fromFile: (params) => ClineRule.fromFile(params),
5480
+ extension: "md"
5481
+ }
5195
5482
  });
5196
5483
  }
5197
- };
5198
-
5199
- // src/subagents/subagents-processor.ts
5200
- var subagentsProcessorToolTargets = [
5201
- "claudecode",
5202
- "copilot",
5203
- "cursor",
5204
- "codexcli"
5205
- ];
5206
- var subagentsProcessorToolTargetsSimulated = [
5207
- "copilot",
5208
- "cursor",
5209
- "codexcli"
5210
- ];
5211
- var SubagentsProcessorToolTargetSchema = import_mini21.z.enum(subagentsProcessorToolTargets);
5212
- var SubagentsProcessor = class extends FeatureProcessor {
5213
- toolTarget;
5214
- constructor({
5215
- baseDir = ".",
5216
- toolTarget
5217
- }) {
5218
- super({ baseDir });
5219
- this.toolTarget = SubagentsProcessorToolTargetSchema.parse(toolTarget);
5484
+ /**
5485
+ * Load OpenAI Codex CLI rule configuration from AGENTS.md and .codex/memories/*.md files
5486
+ */
5487
+ async loadCodexcliRules() {
5488
+ const settablePaths = CodexcliRule.getSettablePaths();
5489
+ return await this.loadToolRulesDefault({
5490
+ root: {
5491
+ relativeDirPath: settablePaths.root.relativeDirPath,
5492
+ relativeFilePath: settablePaths.root.relativeFilePath,
5493
+ fromFile: (params) => CodexcliRule.fromFile(params)
5494
+ },
5495
+ nonRoot: {
5496
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5497
+ fromFile: (params) => CodexcliRule.fromFile(params),
5498
+ extension: "md"
5499
+ }
5500
+ });
5220
5501
  }
5221
- async convertRulesyncFilesToToolFiles(rulesyncFiles) {
5222
- const rulesyncSubagents = rulesyncFiles.filter(
5223
- (file) => file instanceof RulesyncSubagent
5224
- );
5225
- const toolSubagents = rulesyncSubagents.map((rulesyncSubagent) => {
5226
- switch (this.toolTarget) {
5227
- case "claudecode":
5228
- return ClaudecodeSubagent.fromRulesyncSubagent({
5229
- baseDir: this.baseDir,
5230
- relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
5231
- rulesyncSubagent
5232
- });
5233
- case "copilot":
5234
- return CopilotSubagent.fromRulesyncSubagent({
5235
- baseDir: this.baseDir,
5236
- relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
5237
- rulesyncSubagent
5238
- });
5239
- case "cursor":
5240
- return CursorSubagent.fromRulesyncSubagent({
5241
- baseDir: this.baseDir,
5242
- relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
5243
- rulesyncSubagent
5244
- });
5245
- case "codexcli":
5246
- return CodexCliSubagent.fromRulesyncSubagent({
5247
- baseDir: this.baseDir,
5248
- relativeDirPath: RulesyncSubagent.getSettablePaths().relativeDirPath,
5249
- rulesyncSubagent
5250
- });
5251
- default:
5252
- throw new Error(`Unsupported tool target: ${this.toolTarget}`);
5502
+ /**
5503
+ * Load GitHub Copilot rule configuration from .github/copilot-instructions.md file
5504
+ */
5505
+ async loadCopilotRules() {
5506
+ const settablePaths = CopilotRule.getSettablePaths();
5507
+ return await this.loadToolRulesDefault({
5508
+ root: {
5509
+ relativeDirPath: settablePaths.root.relativeDirPath,
5510
+ relativeFilePath: settablePaths.root.relativeFilePath,
5511
+ fromFile: (params) => CopilotRule.fromFile(params)
5512
+ },
5513
+ nonRoot: {
5514
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5515
+ fromFile: (params) => CopilotRule.fromFile(params),
5516
+ extension: "md"
5253
5517
  }
5254
5518
  });
5255
- return toolSubagents;
5256
5519
  }
5257
- async convertToolFilesToRulesyncFiles(toolFiles) {
5258
- const toolSubagents = toolFiles.filter(
5259
- (file) => file instanceof ToolSubagent
5260
- );
5261
- const rulesyncSubagents = [];
5262
- for (const toolSubagent of toolSubagents) {
5263
- if (toolSubagent instanceof SimulatedSubagent) {
5264
- logger.debug(
5265
- `Skipping simulated subagent conversion: ${toolSubagent.getRelativeFilePath()}`
5266
- );
5267
- continue;
5520
+ /**
5521
+ * Load Cursor rule configurations from .cursor/rules/ directory
5522
+ */
5523
+ async loadCursorRules() {
5524
+ const settablePaths = CursorRule.getSettablePaths();
5525
+ return await this.loadToolRulesDefault({
5526
+ nonRoot: {
5527
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5528
+ fromFile: (params) => CursorRule.fromFile(params),
5529
+ extension: "mdc"
5268
5530
  }
5269
- rulesyncSubagents.push(toolSubagent.toRulesyncSubagent());
5270
- }
5271
- return rulesyncSubagents;
5531
+ });
5272
5532
  }
5273
5533
  /**
5274
- * Implementation of abstract method from Processor
5275
- * Load and parse rulesync subagent files from .rulesync/subagents/ directory
5534
+ * Load Gemini CLI rule configuration from GEMINI.md file
5276
5535
  */
5277
- async loadRulesyncFiles() {
5278
- const subagentsDir = (0, import_node_path53.join)(this.baseDir, RulesyncSubagent.getSettablePaths().relativeDirPath);
5279
- const dirExists = await directoryExists(subagentsDir);
5280
- if (!dirExists) {
5281
- logger.debug(`Rulesync subagents directory not found: ${subagentsDir}`);
5282
- return [];
5283
- }
5284
- const entries = await listDirectoryFiles(subagentsDir);
5285
- const mdFiles = entries.filter((file) => file.endsWith(".md"));
5286
- if (mdFiles.length === 0) {
5287
- logger.debug(`No markdown files found in rulesync subagents directory: ${subagentsDir}`);
5288
- return [];
5289
- }
5290
- logger.info(`Found ${mdFiles.length} subagent files in ${subagentsDir}`);
5291
- const rulesyncSubagents = [];
5292
- for (const mdFile of mdFiles) {
5293
- const filepath = (0, import_node_path53.join)(subagentsDir, mdFile);
5294
- try {
5295
- const rulesyncSubagent = await RulesyncSubagent.fromFile({
5296
- relativeFilePath: mdFile,
5297
- validate: true
5298
- });
5299
- rulesyncSubagents.push(rulesyncSubagent);
5300
- logger.debug(`Successfully loaded subagent: ${mdFile}`);
5301
- } catch (error) {
5302
- logger.warn(`Failed to load subagent file ${filepath}:`, error);
5303
- continue;
5536
+ async loadGeminicliRules() {
5537
+ const settablePaths = GeminiCliRule.getSettablePaths();
5538
+ return await this.loadToolRulesDefault({
5539
+ root: {
5540
+ relativeDirPath: settablePaths.root.relativeDirPath,
5541
+ relativeFilePath: settablePaths.root.relativeFilePath,
5542
+ fromFile: (params) => GeminiCliRule.fromFile(params)
5543
+ },
5544
+ nonRoot: {
5545
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5546
+ fromFile: (params) => GeminiCliRule.fromFile(params),
5547
+ extension: "md"
5304
5548
  }
5305
- }
5306
- if (rulesyncSubagents.length === 0) {
5307
- logger.debug(`No valid subagents found in ${subagentsDir}`);
5308
- return [];
5309
- }
5310
- logger.info(`Successfully loaded ${rulesyncSubagents.length} rulesync subagents`);
5311
- return rulesyncSubagents;
5549
+ });
5312
5550
  }
5313
5551
  /**
5314
- * Implementation of abstract method from Processor
5315
- * Load tool-specific subagent configurations and parse them into ToolSubagent instances
5552
+ * Load JetBrains Junie rule configuration from .junie/guidelines.md file
5316
5553
  */
5317
- async loadToolFiles() {
5318
- switch (this.toolTarget) {
5319
- case "claudecode":
5320
- return await this.loadClaudecodeSubagents();
5321
- case "copilot":
5322
- return await this.loadCopilotSubagents();
5323
- case "cursor":
5324
- return await this.loadCursorSubagents();
5325
- case "codexcli":
5326
- return await this.loadCodexCliSubagents();
5327
- default:
5328
- throw new Error(`Unsupported tool target: ${this.toolTarget}`);
5329
- }
5554
+ async loadJunieRules() {
5555
+ const settablePaths = JunieRule.getSettablePaths();
5556
+ return await this.loadToolRulesDefault({
5557
+ root: {
5558
+ relativeDirPath: settablePaths.root.relativeDirPath,
5559
+ relativeFilePath: settablePaths.root.relativeFilePath,
5560
+ fromFile: (params) => JunieRule.fromFile(params)
5561
+ },
5562
+ nonRoot: {
5563
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5564
+ fromFile: (params) => JunieRule.fromFile(params),
5565
+ extension: "md"
5566
+ }
5567
+ });
5330
5568
  }
5331
5569
  /**
5332
- * Load Claude Code subagent configurations from .claude/agents/ directory
5570
+ * Load Kiro rule configurations from .kiro/steering/ directory
5333
5571
  */
5334
- async loadClaudecodeSubagents() {
5335
- return await this.loadToolSubagentsDefault({
5336
- relativeDirPath: ClaudecodeSubagent.getSettablePaths().relativeDirPath,
5337
- fromFile: (relativeFilePath) => ClaudecodeSubagent.fromFile({ relativeFilePath })
5572
+ async loadKiroRules() {
5573
+ const settablePaths = KiroRule.getSettablePaths();
5574
+ return await this.loadToolRulesDefault({
5575
+ nonRoot: {
5576
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5577
+ fromFile: (params) => KiroRule.fromFile(params),
5578
+ extension: "md"
5579
+ }
5338
5580
  });
5339
5581
  }
5340
5582
  /**
5341
- * Load Copilot subagent configurations from .copilot/subagents/ directory
5583
+ * Load OpenCode rule configuration from AGENTS.md file and .opencode/memories/*.md files
5342
5584
  */
5343
- async loadCopilotSubagents() {
5344
- return await this.loadToolSubagentsDefault({
5345
- relativeDirPath: CopilotSubagent.getSettablePaths().relativeDirPath,
5346
- fromFile: (relativeFilePath) => CopilotSubagent.fromFile({ relativeFilePath })
5585
+ async loadOpencodeRules() {
5586
+ const settablePaths = OpenCodeRule.getSettablePaths();
5587
+ return await this.loadToolRulesDefault({
5588
+ root: {
5589
+ relativeDirPath: settablePaths.root.relativeDirPath,
5590
+ relativeFilePath: settablePaths.root.relativeFilePath,
5591
+ fromFile: (params) => OpenCodeRule.fromFile(params)
5592
+ },
5593
+ nonRoot: {
5594
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5595
+ fromFile: (params) => OpenCodeRule.fromFile(params),
5596
+ extension: "md"
5597
+ }
5347
5598
  });
5348
5599
  }
5349
5600
  /**
5350
- * Load Cursor subagent configurations from .cursor/subagents/ directory
5601
+ * Load Qwen Code rule configuration from QWEN.md file and .qwen/memories/*.md files
5351
5602
  */
5352
- async loadCursorSubagents() {
5353
- return await this.loadToolSubagentsDefault({
5354
- relativeDirPath: CursorSubagent.getSettablePaths().relativeDirPath,
5355
- fromFile: (relativeFilePath) => CursorSubagent.fromFile({ relativeFilePath })
5603
+ async loadQwencodeRules() {
5604
+ const settablePaths = QwencodeRule.getSettablePaths();
5605
+ return await this.loadToolRulesDefault({
5606
+ root: {
5607
+ relativeDirPath: settablePaths.root.relativeDirPath,
5608
+ relativeFilePath: settablePaths.root.relativeFilePath,
5609
+ fromFile: (params) => QwencodeRule.fromFile(params)
5610
+ },
5611
+ nonRoot: {
5612
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5613
+ fromFile: (params) => QwencodeRule.fromFile(params),
5614
+ extension: "md"
5615
+ }
5356
5616
  });
5357
5617
  }
5358
5618
  /**
5359
- * Load CodexCli subagent configurations from .codex/subagents/ directory
5619
+ * Load Roo Code rule configurations from .roo/rules/ directory
5360
5620
  */
5361
- async loadCodexCliSubagents() {
5362
- return await this.loadToolSubagentsDefault({
5363
- relativeDirPath: CodexCliSubagent.getSettablePaths().relativeDirPath,
5364
- fromFile: (relativeFilePath) => CodexCliSubagent.fromFile({ relativeFilePath })
5621
+ async loadRooRules() {
5622
+ const settablePaths = RooRule.getSettablePaths();
5623
+ return await this.loadToolRulesDefault({
5624
+ nonRoot: {
5625
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5626
+ fromFile: (params) => RooRule.fromFile(params),
5627
+ extension: "md"
5628
+ }
5365
5629
  });
5366
5630
  }
5367
- async loadToolSubagentsDefault({
5368
- relativeDirPath,
5369
- fromFile
5370
- }) {
5371
- const paths = await findFilesByGlobs((0, import_node_path53.join)(this.baseDir, relativeDirPath, "*.md"));
5372
- const subagents = (await Promise.allSettled(paths.map((path2) => fromFile((0, import_node_path53.basename)(path2))))).filter((r) => r.status === "fulfilled").map((r) => r.value);
5373
- logger.info(`Successfully loaded ${subagents.length} ${relativeDirPath} subagents`);
5374
- return subagents;
5631
+ /**
5632
+ * Load Windsurf rule configurations from .windsurf/rules/ directory
5633
+ */
5634
+ async loadWindsurfRules() {
5635
+ const settablePaths = WindsurfRule.getSettablePaths();
5636
+ return await this.loadToolRulesDefault({
5637
+ nonRoot: {
5638
+ relativeDirPath: settablePaths.nonRoot.relativeDirPath,
5639
+ fromFile: (params) => WindsurfRule.fromFile(params),
5640
+ extension: "md"
5641
+ }
5642
+ });
5375
5643
  }
5376
5644
  /**
5377
5645
  * Implementation of abstract method from FeatureProcessor
5378
5646
  * Return the tool targets that this processor supports
5379
5647
  */
5380
- static getToolTargets({
5381
- includeSimulated = false
5382
- } = {}) {
5383
- if (!includeSimulated) {
5384
- return subagentsProcessorToolTargets.filter(
5385
- (target) => !subagentsProcessorToolTargetsSimulated.includes(target)
5648
+ static getToolTargets() {
5649
+ return rulesProcessorToolTargets;
5650
+ }
5651
+ generateXmlReferencesSection(toolRules) {
5652
+ const toolRulesWithoutRoot = toolRules.filter((rule) => !rule.isRoot());
5653
+ if (toolRulesWithoutRoot.length === 0) {
5654
+ return "";
5655
+ }
5656
+ const lines = [];
5657
+ lines.push(
5658
+ "Please also reference the following documents as needed. In this case, `@` stands for the project root directory."
5659
+ );
5660
+ lines.push("");
5661
+ const documentsData = {
5662
+ Documents: {
5663
+ Document: toolRulesWithoutRoot.map((rule) => {
5664
+ const rulesyncRule = rule.toRulesyncRule();
5665
+ const frontmatter = rulesyncRule.getFrontmatter();
5666
+ const relativePath = `@${rule.getRelativePathFromCwd()}`;
5667
+ const document = {
5668
+ Path: relativePath
5669
+ };
5670
+ if (frontmatter.description) {
5671
+ document.Description = frontmatter.description;
5672
+ }
5673
+ if (frontmatter.globs && frontmatter.globs.length > 0) {
5674
+ document.FilePatterns = frontmatter.globs.join(", ");
5675
+ }
5676
+ return document;
5677
+ })
5678
+ }
5679
+ };
5680
+ const builder = new import_fast_xml_parser.XMLBuilder({
5681
+ format: true,
5682
+ ignoreAttributes: false,
5683
+ suppressEmptyNode: false
5684
+ });
5685
+ const xmlContent = builder.build(documentsData);
5686
+ lines.push(xmlContent);
5687
+ return lines.join("\n") + "\n";
5688
+ }
5689
+ generateReferencesSection(toolRules) {
5690
+ const toolRulesWithoutRoot = toolRules.filter((rule) => !rule.isRoot());
5691
+ if (toolRulesWithoutRoot.length === 0) {
5692
+ return "";
5693
+ }
5694
+ const lines = [];
5695
+ lines.push("Please also reference the following documents as needed:");
5696
+ lines.push("");
5697
+ for (const rule of toolRulesWithoutRoot) {
5698
+ const rulesyncRule = rule.toRulesyncRule();
5699
+ const frontmatter = rulesyncRule.getFrontmatter();
5700
+ const escapedDescription = frontmatter.description?.replace(/"/g, '\\"');
5701
+ const globsText = frontmatter.globs?.join(",");
5702
+ lines.push(
5703
+ `@${rule.getRelativePathFromCwd()} description: "${escapedDescription}" globs: "${globsText}"`
5386
5704
  );
5387
5705
  }
5388
- return subagentsProcessorToolTargets;
5706
+ return lines.join("\n") + "\n";
5707
+ }
5708
+ generateAdditionalConventionsSection({
5709
+ commands,
5710
+ subagents
5711
+ }) {
5712
+ const overview = `# Additional Conventions Beyond the Built-in Functions
5713
+
5714
+ As this project's AI coding tool, you must follow the additional conventions below, in addition to the built-in functions.`;
5715
+ const commandsSection = `## Simulated Custom Slash Commands
5716
+
5717
+ Custom slash commands allow you to define frequently-used prompts as Markdown files that you can execute.
5718
+
5719
+ ### Syntax
5720
+
5721
+ Users can use following syntax to invoke a custom command.
5722
+
5723
+ \`\`\`txt
5724
+ s/<command> [arguments]
5725
+ \`\`\`
5726
+
5727
+ This syntax employs a double slash (\`s/\`) to prevent conflicts with built-in slash commands.
5728
+ The \`s\` in \`s/\` stands for *simulate*. Because custom slash commands are not built-in, this syntax provides a pseudo way to invoke them.
5729
+
5730
+ When users call a custom slash command, you have to look for the markdown file, \`${(0, import_node_path53.join)(commands.relativeDirPath, "{command}.md")}\`, then execute the contents of that file as the block of operations.`;
5731
+ const subagentsSection = `## Simulated Subagents
5732
+
5733
+ Simulated subagents are specialized AI assistants that can be invoked to handle specific types of tasks. In this case, it can be appear something like custom slash commands simply. Simulated subagents can be called by custom slash commands.
5734
+
5735
+ When users call a simulated subagent, it will look for the corresponding markdown file, \`${(0, import_node_path53.join)(subagents.relativeDirPath, "{subagent}.md")}\`, and execute its contents as the block of operations.
5736
+
5737
+ For example, if the user instructs \`Call planner subagent to plan the refactoring\`, you have to look for the markdown file, \`${(0, import_node_path53.join)(subagents.relativeDirPath, "planner.md")}\`, and execute its contents as the block of operations.`;
5738
+ const result = [
5739
+ overview,
5740
+ ...this.simulateCommands && CommandsProcessor.getToolTargetsSimulated().includes(this.toolTarget) ? [commandsSection] : [],
5741
+ ...this.simulateSubagents && SubagentsProcessor.getToolTargetsSimulated().includes(this.toolTarget) ? [subagentsSection] : []
5742
+ ].join("\n\n");
5743
+ return result;
5389
5744
  }
5390
5745
  };
5391
5746
 
@@ -5558,7 +5913,7 @@ async function generateCommand(options) {
5558
5913
  const parts = [];
5559
5914
  if (totalRulesOutputs > 0) parts.push(`${totalRulesOutputs} rules`);
5560
5915
  if (totalIgnoreOutputs > 0) parts.push(`${totalIgnoreOutputs} ignore files`);
5561
- if (totalMcpOutputs > 0) parts.push(`${totalMcpOutputs} MCPs`);
5916
+ if (totalMcpOutputs > 0) parts.push(`${totalMcpOutputs} MCP files`);
5562
5917
  if (totalCommandOutputs > 0) parts.push(`${totalCommandOutputs} commands`);
5563
5918
  if (totalSubagentOutputs > 0) parts.push(`${totalSubagentOutputs} subagents`);
5564
5919
  logger.success(`\u{1F389} All done! Generated ${totalGenerated} file(s) total (${parts.join(" + ")})`);
@@ -5590,6 +5945,7 @@ var gitignoreCommand = async () => {
5590
5945
  "**/GEMINI.md",
5591
5946
  "**/.gemini/memories/",
5592
5947
  "**/.gemini/commands/",
5948
+ "**/.gemini/subagents/",
5593
5949
  "**/QWEN.md",
5594
5950
  "**/.qwen/memories/",
5595
5951
  "**/.aiexclude",
@@ -5607,6 +5963,7 @@ var gitignoreCommand = async () => {
5607
5963
  "**/.cursor/mcp.json",
5608
5964
  "**/.cline/mcp.json",
5609
5965
  "**/.roo/mcp.json",
5966
+ "**/.roo/subagents/",
5610
5967
  "**/.vscode/mcp.json",
5611
5968
  "**/.github/commands/",
5612
5969
  "**/.github/subagents/",
@@ -5631,8 +5988,8 @@ var gitignoreCommand = async () => {
5631
5988
  }
5632
5989
  const newContent = gitignoreContent ? `${gitignoreContent.trimEnd()}
5633
5990
 
5634
- ${linesToAdd.join("")}
5635
- ` : `${linesToAdd.join("")}
5991
+ ${linesToAdd.join("\n")}
5992
+ ` : `${linesToAdd.join("\n")}
5636
5993
  `;
5637
5994
  await writeFileContent(gitignorePath, newContent);
5638
5995
  logger.success(`Added ${linesToAdd.length} rules to .gitignore:`);
@@ -5829,7 +6186,7 @@ var getVersion = async () => {
5829
6186
  const packageJson = await readJsonFile(packageJsonPath);
5830
6187
  return packageJson.version;
5831
6188
  } catch {
5832
- return "0.74.0";
6189
+ return "0.76.0";
5833
6190
  }
5834
6191
  };
5835
6192
  var main = async () => {
@@ -5851,7 +6208,7 @@ var main = async () => {
5851
6208
  }
5852
6209
  ).option(
5853
6210
  "-f, --features <features>",
5854
- `Comma-separated list of features to import (${FEATURE_TYPES.join(",")}) or '*' for all`,
6211
+ `Comma-separated list of features to import (${ALL_FEATURES.join(",")}) or '*' for all`,
5855
6212
  (value) => {
5856
6213
  return value.split(",").map((f) => f.trim());
5857
6214
  }
@@ -5876,7 +6233,7 @@ var main = async () => {
5876
6233
  }
5877
6234
  ).option(
5878
6235
  "-f, --features <features>",
5879
- `Comma-separated list of features to generate (${FEATURE_TYPES.join(",")}) or '*' for all`,
6236
+ `Comma-separated list of features to generate (${ALL_FEATURES.join(",")}) or '*' for all`,
5880
6237
  (value) => {
5881
6238
  return value.split(",").map((f) => f.trim());
5882
6239
  }