@ruan-cat/utils 4.11.0 → 4.12.1

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.
@@ -39,6 +39,74 @@ declare function hasChangelogMd(): boolean;
39
39
  */
40
40
  declare function copyChangelogMd(/** 目标文件夹 */ target: string): void;
41
41
 
42
+ /**
43
+ * 检查指定根目录是否存在 .claude/agents 文件夹
44
+ * @param options - 配置选项
45
+ * @param options.rootDir - 可选的根目录路径,支持相对路径(如 `../../../` 表示向上三级目录)。
46
+ * 如果不传入,将自动向上查找包含 pnpm-workspace.yaml 的 monorepo 根目录。
47
+ * 相对路径会基于当前工作目录 (process.cwd()) 解析为绝对路径。
48
+ * @returns 是否存在 .claude/agents 文件夹
49
+ * @example
50
+ * // 自动检测 monorepo 根目录
51
+ * hasClaudeAgents()
52
+ *
53
+ * // 手动指定相对路径(从当前工作目录向上三级)
54
+ * hasClaudeAgents({ rootDir: '../../../' })
55
+ *
56
+ * // 手动指定绝对路径
57
+ * hasClaudeAgents({ rootDir: '/path/to/monorepo' })
58
+ */
59
+ declare function hasClaudeAgents(options?: {
60
+ rootDir?: string;
61
+ }): boolean;
62
+ /**
63
+ * 将 .claude/agents 文件夹复制到指定位置的配置选项
64
+ */
65
+ interface CopyClaudeAgentsOptions {
66
+ /**
67
+ * 目标文件夹路径(相对于当前工作目录)
68
+ * @example 'dist', 'build/output', './public'
69
+ */
70
+ target: string;
71
+ /**
72
+ * 可选的根目录路径,支持相对路径(如 `../../../` 表示向上三级目录)
73
+ * @description
74
+ * - 如果不传入,将自动向上查找包含 pnpm-workspace.yaml 的 monorepo 根目录
75
+ * - 相对路径会基于当前工作目录 (process.cwd()) 解析为绝对路径
76
+ * - 绝对路径将直接使用
77
+ * @example
78
+ * // 相对路径:向上三级目录
79
+ * '../../../'
80
+ *
81
+ * // 绝对路径
82
+ * '/absolute/path/to/monorepo'
83
+ */
84
+ rootDir?: string;
85
+ }
86
+ /**
87
+ * 将 .claude/agents 文件夹复制到指定位置
88
+ * @param options - 配置选项
89
+ * @description
90
+ * 该函数相当于实现 `cpx .claude/agents <target>` 命令。
91
+ * 从根目录的 .claude/agents 复制到目标位置。
92
+ * @example
93
+ * // 自动检测 monorepo 根目录,复制到当前目录的 dist 文件夹
94
+ * copyClaudeAgents({ target: 'dist' })
95
+ *
96
+ * // 手动指定根目录为向上三级,复制到 build 文件夹
97
+ * copyClaudeAgents({
98
+ * target: 'build',
99
+ * rootDir: '../../../'
100
+ * })
101
+ *
102
+ * // 使用绝对路径指定根目录
103
+ * copyClaudeAgents({
104
+ * target: 'dist',
105
+ * rootDir: '/absolute/path/to/monorepo'
106
+ * })
107
+ */
108
+ declare function copyClaudeAgents(options: CopyClaudeAgentsOptions): void;
109
+
42
110
  /** 检查当前运行的根目录 是否存在文件名大写的 `README.md` 文件 */
43
111
  declare function hasCapitalReadmeMd(): boolean;
44
112
  /** 检查当前运行的根目录 是否存在文件名小写的 `readme.md` 文件 */
@@ -72,4 +140,4 @@ interface AddChangelog2docOptions<T = Record<string, any>> {
72
140
  /** 将变更日志添加到指定的文档目录内 并提供参数 */
73
141
  declare function addChangelog2doc<T>(options: AddChangelog2docOptions<T>): void;
74
142
 
75
- export { type AddChangelog2docOptions, type PackageInfo, type WriteYaml2mdParams, addChangelog2doc, clean, copyChangelogMd, copyReadmeMd, defaultCleanTargets, getRuanCatPkgInfo, hasCapitalReadmeMd, hasChangelogMd, hasLowerCaseReadmeMd, hasReadmeMd, writeYaml2md };
143
+ export { type AddChangelog2docOptions, type CopyClaudeAgentsOptions, type PackageInfo, type WriteYaml2mdParams, addChangelog2doc, clean, copyChangelogMd, copyClaudeAgents, copyReadmeMd, defaultCleanTargets, getRuanCatPkgInfo, hasCapitalReadmeMd, hasChangelogMd, hasClaudeAgents, hasLowerCaseReadmeMd, hasReadmeMd, writeYaml2md };
@@ -137,23 +137,75 @@ function copyChangelogMd(target) {
137
137
  fs.copyFileSync(source, destination);
138
138
  }
139
139
 
140
- // src/node-esm/scripts/copy-readme.ts
140
+ // src/node-esm/scripts/copy-claude-agents.ts
141
141
  import fs2 from "fs";
142
142
  import path2 from "path";
143
143
  import consola4 from "consola";
144
+ function findMonorepoRoot() {
145
+ let currentDir = process.cwd();
146
+ const root = path2.parse(currentDir).root;
147
+ while (currentDir !== root) {
148
+ const workspaceFile2 = path2.join(currentDir, "pnpm-workspace.yaml");
149
+ if (fs2.existsSync(workspaceFile2)) {
150
+ return currentDir;
151
+ }
152
+ currentDir = path2.dirname(currentDir);
153
+ }
154
+ const workspaceFile = path2.join(root, "pnpm-workspace.yaml");
155
+ if (fs2.existsSync(workspaceFile)) {
156
+ return root;
157
+ }
158
+ return null;
159
+ }
160
+ function resolveRootDir(rootDir) {
161
+ if (rootDir) {
162
+ return path2.resolve(process.cwd(), rootDir);
163
+ }
164
+ const monorepoRoot = findMonorepoRoot();
165
+ if (monorepoRoot) {
166
+ return monorepoRoot;
167
+ }
168
+ return process.cwd();
169
+ }
170
+ function hasClaudeAgents(options) {
171
+ const root = resolveRootDir(options?.rootDir);
172
+ const claudeAgentsPath = path2.join(root, ".claude/agents");
173
+ const exists = fs2.existsSync(claudeAgentsPath);
174
+ if (!exists) {
175
+ consola4.log("\u68C0\u6D4B\u7684\u6839\u76EE\u5F55\u4E3A\uFF1A", root);
176
+ consola4.warn("\u8BE5\u6839\u76EE\u5F55\u4E0D\u5B58\u5728 .claude/agents \u6587\u4EF6\u5939");
177
+ }
178
+ return exists;
179
+ }
180
+ function copyClaudeAgents(options) {
181
+ if (!hasClaudeAgents({ rootDir: options.rootDir })) {
182
+ return;
183
+ }
184
+ const root = resolveRootDir(options.rootDir);
185
+ const source = path2.join(root, ".claude/agents");
186
+ const destination = path2.resolve(process.cwd(), options.target);
187
+ fs2.mkdirSync(path2.dirname(destination), { recursive: true });
188
+ fs2.cpSync(source, destination, { recursive: true });
189
+ consola4.success(`\u5DF2\u6210\u529F\u590D\u5236 .claude/agents \u5230 ${destination}`);
190
+ }
191
+
192
+ // src/node-esm/scripts/copy-readme.ts
193
+ import fs3 from "fs";
194
+ import path3 from "path";
195
+ import consola5 from "consola";
144
196
  var capitalReadmeMd = "README.md";
145
197
  var lowerCaseReadmeMd = "readme.md";
146
198
  function hasCapitalReadmeMd() {
147
- const res = fs2.existsSync(path2.resolve(process.cwd(), capitalReadmeMd));
199
+ const res = fs3.existsSync(path3.resolve(process.cwd(), capitalReadmeMd));
148
200
  if (!res) {
149
- consola4.warn(`\u5F53\u524D\u9879\u76EE\u6839\u76EE\u5F55\u4E0D\u5B58\u5728 ${capitalReadmeMd} \u6587\u4EF6`);
201
+ consola5.warn(`\u5F53\u524D\u9879\u76EE\u6839\u76EE\u5F55\u4E0D\u5B58\u5728 ${capitalReadmeMd} \u6587\u4EF6`);
150
202
  }
151
203
  return res;
152
204
  }
153
205
  function hasLowerCaseReadmeMd() {
154
- const res = fs2.existsSync(path2.resolve(process.cwd(), lowerCaseReadmeMd));
206
+ const res = fs3.existsSync(path3.resolve(process.cwd(), lowerCaseReadmeMd));
155
207
  if (!res) {
156
- consola4.log(`\u5F53\u524D\u9879\u76EE\u6839\u76EE\u5F55\u4E0D\u5B58\u5728 ${lowerCaseReadmeMd} \u6587\u4EF6`);
208
+ consola5.log(`\u5F53\u524D\u9879\u76EE\u6839\u76EE\u5F55\u4E0D\u5B58\u5728 ${lowerCaseReadmeMd} \u6587\u4EF6`);
157
209
  }
158
210
  return res;
159
211
  }
@@ -171,14 +223,14 @@ function copyReadmeMd(target) {
171
223
  } else if (hasLowerCaseReadmeMd()) {
172
224
  readmeFileName = lowerCaseReadmeMd;
173
225
  }
174
- const source = path2.resolve(process.cwd(), readmeFileName);
175
- const destination = path2.resolve(process.cwd(), target, "index.md");
176
- fs2.copyFileSync(source, destination);
226
+ const source = path3.resolve(process.cwd(), readmeFileName);
227
+ const destination = path3.resolve(process.cwd(), target, "index.md");
228
+ fs3.copyFileSync(source, destination);
177
229
  }
178
230
 
179
231
  // src/node-esm/scripts/yaml-to-md.ts
180
232
  import { readFileSync, writeFileSync } from "fs";
181
- import { consola as consola5 } from "consola";
233
+ import { consola as consola6 } from "consola";
182
234
  import { isUndefined } from "lodash-es";
183
235
 
184
236
  // ../../node_modules/.pnpm/js-yaml@4.1.0/node_modules/js-yaml/dist/js-yaml.mjs
@@ -2805,16 +2857,16 @@ var js_yaml_default = jsYaml;
2805
2857
 
2806
2858
  // src/node-esm/scripts/yaml-to-md.ts
2807
2859
  function writeYaml2md(params) {
2808
- consola5.info(` \u5F53\u524D\u8FD0\u884C\u7684\u5730\u5740\u4E3A\uFF1A ${process.cwd()} `);
2860
+ consola6.info(` \u5F53\u524D\u8FD0\u884C\u7684\u5730\u5740\u4E3A\uFF1A ${process.cwd()} `);
2809
2861
  const { mdPath, data } = params;
2810
2862
  if (isUndefined(mdPath)) {
2811
- consola5.error(" \u8BF7\u63D0\u4F9Bmd\u6587\u4EF6\u7684\u5730\u5740 ");
2863
+ consola6.error(" \u8BF7\u63D0\u4F9Bmd\u6587\u4EF6\u7684\u5730\u5740 ");
2812
2864
  process.exit(1);
2813
2865
  }
2814
2866
  try {
2815
2867
  readFileSync(mdPath, "utf-8");
2816
2868
  } catch (error) {
2817
- consola5.error(` \u6587\u4EF6 ${mdPath} \u4E0D\u5B58\u5728 `);
2869
+ consola6.error(` \u6587\u4EF6 ${mdPath} \u4E0D\u5B58\u5728 `);
2818
2870
  process.exit(1);
2819
2871
  }
2820
2872
  const mdContent = readFileSync(mdPath, "utf-8");
@@ -2824,18 +2876,18 @@ ${yamlContent}---
2824
2876
 
2825
2877
  ${mdContent}`;
2826
2878
  writeFileSync(mdPath, newContent, "utf-8");
2827
- consola5.success(` \u5DF2\u5C06YAML\u6570\u636E\u5199\u5165\u5230 ${mdPath} `);
2879
+ consola6.success(` \u5DF2\u5C06YAML\u6570\u636E\u5199\u5165\u5230 ${mdPath} `);
2828
2880
  }
2829
2881
 
2830
2882
  // src/node-esm/scripts/add-changelog-to-doc.ts
2831
- import path3 from "path";
2883
+ import path4 from "path";
2832
2884
  function addChangelog2doc(options) {
2833
2885
  const { data, target } = options;
2834
2886
  if (!hasChangelogMd()) {
2835
2887
  return;
2836
2888
  }
2837
2889
  copyChangelogMd(target);
2838
- const mdPath = path3.resolve(process.cwd(), target, "CHANGELOG.md");
2890
+ const mdPath = path4.resolve(process.cwd(), target, "CHANGELOG.md");
2839
2891
  writeYaml2md({
2840
2892
  mdPath,
2841
2893
  data
@@ -2845,11 +2897,13 @@ export {
2845
2897
  addChangelog2doc,
2846
2898
  clean,
2847
2899
  copyChangelogMd,
2900
+ copyClaudeAgents,
2848
2901
  copyReadmeMd,
2849
2902
  defaultCleanTargets,
2850
2903
  getRuanCatPkgInfo,
2851
2904
  hasCapitalReadmeMd,
2852
2905
  hasChangelogMd,
2906
+ hasClaudeAgents,
2853
2907
  hasLowerCaseReadmeMd,
2854
2908
  hasReadmeMd,
2855
2909
  writeYaml2md