mn-ws 0.0.0-stage → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/assets/groups.json +10 -0
- package/assets/mn-ws/SKILL.md +55 -0
- package/assets/mn-ws/hooks.json +14 -0
- package/assets/mn-ws/install/inject-root.mjs +26 -0
- package/bin/ws.mjs +13 -0
- package/dist/core/auth.d.ts +194 -0
- package/dist/core/auth.d.ts.map +1 -0
- package/dist/core/auth.js +331 -0
- package/dist/core/auth.js.map +1 -0
- package/dist/core/brand.d.ts +11 -0
- package/dist/core/brand.d.ts.map +1 -0
- package/dist/core/brand.js +7 -0
- package/dist/core/brand.js.map +1 -0
- package/dist/core/bridge.d.ts +106 -0
- package/dist/core/bridge.d.ts.map +1 -0
- package/dist/core/bridge.js +308 -0
- package/dist/core/bridge.js.map +1 -0
- package/dist/core/config.d.ts +174 -0
- package/dist/core/config.d.ts.map +1 -0
- package/dist/core/config.js +417 -0
- package/dist/core/config.js.map +1 -0
- package/dist/core/controller.d.ts +64 -0
- package/dist/core/controller.d.ts.map +1 -0
- package/dist/core/controller.js +100 -0
- package/dist/core/controller.js.map +1 -0
- package/dist/core/errors/index.d.ts +30 -0
- package/dist/core/errors/index.d.ts.map +1 -0
- package/dist/core/errors/index.js +88 -0
- package/dist/core/errors/index.js.map +1 -0
- package/dist/core/open.d.ts +3 -0
- package/dist/core/open.d.ts.map +1 -0
- package/dist/core/open.js +27 -0
- package/dist/core/open.js.map +1 -0
- package/dist/core/paths.d.ts +15 -0
- package/dist/core/paths.d.ts.map +1 -0
- package/dist/core/paths.js +50 -0
- package/dist/core/paths.js.map +1 -0
- package/dist/core/serve-port.d.ts +73 -0
- package/dist/core/serve-port.d.ts.map +1 -0
- package/dist/core/serve-port.js +134 -0
- package/dist/core/serve-port.js.map +1 -0
- package/dist/core/session.d.ts +78 -0
- package/dist/core/session.d.ts.map +1 -0
- package/dist/core/session.js +124 -0
- package/dist/core/session.js.map +1 -0
- package/dist/core/skills/bus.d.ts +29 -0
- package/dist/core/skills/bus.d.ts.map +1 -0
- package/dist/core/skills/bus.js +114 -0
- package/dist/core/skills/bus.js.map +1 -0
- package/dist/core/skills/get.d.ts +17 -0
- package/dist/core/skills/get.d.ts.map +1 -0
- package/dist/core/skills/get.js +87 -0
- package/dist/core/skills/get.js.map +1 -0
- package/dist/core/skills/handlers.d.ts +22 -0
- package/dist/core/skills/handlers.d.ts.map +1 -0
- package/dist/core/skills/handlers.js +86 -0
- package/dist/core/skills/handlers.js.map +1 -0
- package/dist/core/skills/index.d.ts +47 -0
- package/dist/core/skills/index.d.ts.map +1 -0
- package/dist/core/skills/index.js +268 -0
- package/dist/core/skills/index.js.map +1 -0
- package/dist/core/skills/install.d.ts +18 -0
- package/dist/core/skills/install.d.ts.map +1 -0
- package/dist/core/skills/install.js +123 -0
- package/dist/core/skills/install.js.map +1 -0
- package/dist/core/skills/text-util.d.ts +2 -0
- package/dist/core/skills/text-util.d.ts.map +1 -0
- package/dist/core/skills/text-util.js +14 -0
- package/dist/core/skills/text-util.js.map +1 -0
- package/dist/core/store.d.ts +29 -0
- package/dist/core/store.d.ts.map +1 -0
- package/dist/core/store.js +100 -0
- package/dist/core/store.js.map +1 -0
- package/dist/core/views.d.ts +11 -0
- package/dist/core/views.d.ts.map +1 -0
- package/dist/core/views.js +20 -0
- package/dist/core/views.js.map +1 -0
- package/dist/index.d.ts +6 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +8 -0
- package/dist/index.js.map +1 -0
- package/dist/modules/auth/index.d.ts +73 -0
- package/dist/modules/auth/index.d.ts.map +1 -0
- package/dist/modules/auth/index.js +64 -0
- package/dist/modules/auth/index.js.map +1 -0
- package/dist/modules/auth/service.d.ts +98 -0
- package/dist/modules/auth/service.d.ts.map +1 -0
- package/dist/modules/auth/service.js +200 -0
- package/dist/modules/auth/service.js.map +1 -0
- package/dist/modules/bridge/index.d.ts +73 -0
- package/dist/modules/bridge/index.d.ts.map +1 -0
- package/dist/modules/bridge/index.js +89 -0
- package/dist/modules/bridge/index.js.map +1 -0
- package/dist/modules/bridge/service.d.ts +75 -0
- package/dist/modules/bridge/service.d.ts.map +1 -0
- package/dist/modules/bridge/service.js +134 -0
- package/dist/modules/bridge/service.js.map +1 -0
- package/dist/modules/home/index.d.ts +95 -0
- package/dist/modules/home/index.d.ts.map +1 -0
- package/dist/modules/home/index.js +123 -0
- package/dist/modules/home/index.js.map +1 -0
- package/dist/modules/home/service.d.ts +48 -0
- package/dist/modules/home/service.d.ts.map +1 -0
- package/dist/modules/home/service.js +195 -0
- package/dist/modules/home/service.js.map +1 -0
- package/dist/modules/skill/index.d.ts +78 -0
- package/dist/modules/skill/index.d.ts.map +1 -0
- package/dist/modules/skill/index.js +132 -0
- package/dist/modules/skill/index.js.map +1 -0
- package/dist/runtime/api.d.ts +24 -0
- package/dist/runtime/api.d.ts.map +1 -0
- package/dist/runtime/api.js +140 -0
- package/dist/runtime/api.js.map +1 -0
- package/dist/runtime/cli.d.ts +23 -0
- package/dist/runtime/cli.d.ts.map +1 -0
- package/dist/runtime/cli.js +410 -0
- package/dist/runtime/cli.js.map +1 -0
- package/dist/runtime/help.d.ts +29 -0
- package/dist/runtime/help.d.ts.map +1 -0
- package/dist/runtime/help.js +89 -0
- package/dist/runtime/help.js.map +1 -0
- package/dist/runtime/registry.d.ts +318 -0
- package/dist/runtime/registry.d.ts.map +1 -0
- package/dist/runtime/registry.js +75 -0
- package/dist/runtime/registry.js.map +1 -0
- package/dist/runtime/server.d.ts +10 -0
- package/dist/runtime/server.d.ts.map +1 -0
- package/dist/runtime/server.js +127 -0
- package/dist/runtime/server.js.map +1 -0
- package/dist/runtime/spec.d.ts +32 -0
- package/dist/runtime/spec.d.ts.map +1 -0
- package/dist/runtime/spec.js +180 -0
- package/dist/runtime/spec.js.map +1 -0
- package/dist/runtime/types/action.d.ts +101 -0
- package/dist/runtime/types/action.d.ts.map +1 -0
- package/dist/runtime/types/action.js +19 -0
- package/dist/runtime/types/action.js.map +1 -0
- package/dist/runtime/types/client.d.ts +39 -0
- package/dist/runtime/types/client.d.ts.map +1 -0
- package/dist/runtime/types/client.js +2 -0
- package/dist/runtime/types/client.js.map +1 -0
- package/dist/runtime/types/http.d.ts +22 -0
- package/dist/runtime/types/http.d.ts.map +1 -0
- package/dist/runtime/types/http.js +6 -0
- package/dist/runtime/types/http.js.map +1 -0
- package/dist/runtime/types/module.d.ts +72 -0
- package/dist/runtime/types/module.d.ts.map +1 -0
- package/dist/runtime/types/module.js +15 -0
- package/dist/runtime/types/module.js.map +1 -0
- package/dist/web/public/assets/CliHints-BOxU-Duc.js +1 -0
- package/dist/web/public/assets/index-BTRKdMIW.js +50 -0
- package/dist/web/public/assets/index-BjGe8ggI.css +1 -0
- package/dist/web/public/assets/view-CE4tnCuy.js +1 -0
- package/dist/web/public/assets/view-CEQ2uPxE.js +1 -0
- package/dist/web/public/favicon-16.png +0 -0
- package/dist/web/public/favicon-32.png +0 -0
- package/dist/web/public/favicon-48.png +0 -0
- package/dist/web/public/favicon.ico +0 -0
- package/dist/web/public/index.html +19 -0
- package/dist/web/public/logo-rounded.png +0 -0
- package/dist/web/public/logo-rounded.svg +6 -0
- package/dist/web/public/logo.png +0 -0
- package/dist/web/public/logo.svg +6 -0
- package/package.json +64 -4
- package/README.md +0 -3
|
@@ -0,0 +1,268 @@
|
|
|
1
|
+
// 随包 skill 的发现、分组、安装与导出。
|
|
2
|
+
//
|
|
3
|
+
// 与 templates/ 的关系:templates 是「生成器要物化的项目模板」;
|
|
4
|
+
// assets/ 是「随 nx-nx 包分发给 agent 的 skill 文档」。两者都是包内资产,互不依赖。
|
|
5
|
+
//
|
|
6
|
+
// 多 skill 约定(见脚手架 B04):
|
|
7
|
+
// - 主 skill 名 = package.json.name(nx-nx),默认 install 装它
|
|
8
|
+
// - groups.json 是便捷聚合而非第二事实源;缺失/损坏时降级为目录扫描
|
|
9
|
+
import fsp from 'node:fs/promises';
|
|
10
|
+
import { existsSync } from 'node:fs';
|
|
11
|
+
import { dirname, join } from 'node:path';
|
|
12
|
+
import { fileURLToPath } from 'node:url';
|
|
13
|
+
import { badInput, blocked, notFound, specError } from '../errors/index.js';
|
|
14
|
+
import { assertSafeName } from '../paths.js';
|
|
15
|
+
import { asAbsolutePath } from '../brand.js';
|
|
16
|
+
import { hasInstallHooks, runPreInstall, runPostInstall, diffRendered, copyRendered, } from './install.js';
|
|
17
|
+
import { emit, loadHookConfig } from './bus.js';
|
|
18
|
+
const HERE = dirname(fileURLToPath(import.meta.url));
|
|
19
|
+
export function assetsDir() {
|
|
20
|
+
// MN_WS_ASSETS 为测试/隔离入口(调用时读取):指向临时资产树以验证降级路径
|
|
21
|
+
const override = process.env.MN_WS_ASSETS;
|
|
22
|
+
const candidates = [
|
|
23
|
+
...(override ? [override] : []),
|
|
24
|
+
join(HERE, '..', '..', '..', 'assets'),
|
|
25
|
+
join(process.cwd(), 'assets'),
|
|
26
|
+
];
|
|
27
|
+
for (const dir of candidates) {
|
|
28
|
+
if (existsSync(dir))
|
|
29
|
+
return asAbsolutePath(dir);
|
|
30
|
+
}
|
|
31
|
+
throw specError('找不到 assets/ 目录(尝试过: ' + candidates.join(', ') + ')');
|
|
32
|
+
}
|
|
33
|
+
export const defaultSkillsDir = () => asAbsolutePath(join(process.env.HOME || process.env.USERPROFILE || '', '.claude', 'skills'));
|
|
34
|
+
// 读 groups.json;文件缺失或 JSON 损坏 → 降级为目录扫描(每个含 SKILL.md 的
|
|
35
|
+
// 目录自成一个 group)。schema 错误不降级——那是作者打包事故,必须显眼。
|
|
36
|
+
export async function loadGroups() {
|
|
37
|
+
const root = assetsDir();
|
|
38
|
+
const file = join(root, 'groups.json');
|
|
39
|
+
if (!existsSync(file)) {
|
|
40
|
+
return { groups: await scanGroups(root), defaultGroup: null, source: 'assets-dirs' };
|
|
41
|
+
}
|
|
42
|
+
let raw;
|
|
43
|
+
try {
|
|
44
|
+
raw = await fsp.readFile(file, 'utf8');
|
|
45
|
+
}
|
|
46
|
+
catch {
|
|
47
|
+
return { groups: await scanGroups(root), defaultGroup: null, source: 'assets-dirs' };
|
|
48
|
+
}
|
|
49
|
+
let parsed;
|
|
50
|
+
try {
|
|
51
|
+
parsed = JSON.parse(raw);
|
|
52
|
+
}
|
|
53
|
+
catch {
|
|
54
|
+
return {
|
|
55
|
+
groups: await scanGroups(root),
|
|
56
|
+
defaultGroup: null,
|
|
57
|
+
source: 'assets-dirs',
|
|
58
|
+
warning: 'groups.json 不是合法 JSON,已降级为目录扫描',
|
|
59
|
+
};
|
|
60
|
+
}
|
|
61
|
+
const groups = parsed.groups;
|
|
62
|
+
if (!groups || typeof groups !== 'object') {
|
|
63
|
+
throw specError('groups.json schema 错误:缺少 groups 对象');
|
|
64
|
+
}
|
|
65
|
+
for (const [key, g] of Object.entries(groups)) {
|
|
66
|
+
if (!g || !Array.isArray(g.skills) || !g.skills.length) {
|
|
67
|
+
throw specError(`groups.json 的 group "${key}" 缺少非空 skills 数组`);
|
|
68
|
+
}
|
|
69
|
+
for (const s of g.skills) {
|
|
70
|
+
if (typeof s !== 'string' || !/^[\w.-]+$/.test(s)) {
|
|
71
|
+
throw specError(`groups.json 的 group "${key}" 含非法 skill 名: ${String(s)}`);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
return { groups, defaultGroup: 'mn-ws' in groups ? 'mn-ws' : null, source: 'manifest' };
|
|
76
|
+
}
|
|
77
|
+
async function scanGroups(root) {
|
|
78
|
+
const out = {};
|
|
79
|
+
let entries;
|
|
80
|
+
try {
|
|
81
|
+
entries = await fsp.readdir(root, { withFileTypes: true });
|
|
82
|
+
}
|
|
83
|
+
catch {
|
|
84
|
+
return out;
|
|
85
|
+
}
|
|
86
|
+
for (const e of entries) {
|
|
87
|
+
if (e.isDirectory() && existsSync(join(root, e.name, 'SKILL.md'))) {
|
|
88
|
+
out[e.name] = { skills: [e.name] };
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
return out;
|
|
92
|
+
}
|
|
93
|
+
export async function bundledSkillNames() {
|
|
94
|
+
const root = assetsDir();
|
|
95
|
+
try {
|
|
96
|
+
const entries = await fsp.readdir(root, { withFileTypes: true });
|
|
97
|
+
return entries
|
|
98
|
+
.filter((e) => e.isDirectory() && existsSync(join(root, e.name, 'SKILL.md')))
|
|
99
|
+
.map((e) => e.name)
|
|
100
|
+
.sort();
|
|
101
|
+
}
|
|
102
|
+
catch {
|
|
103
|
+
return [];
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
// 无副作用地查看某个 skill 的安装状态:目标是否存在、有哪些差异文件。
|
|
107
|
+
// installOne 与 installGroup 的预检共用它——预检绝不能边查边装。
|
|
108
|
+
export async function inspectInstall(name, toRoot) {
|
|
109
|
+
const safe = assertSafeName(name, 'skill 名');
|
|
110
|
+
const src = join(assetsDir(), safe);
|
|
111
|
+
if (!existsSync(join(src, 'SKILL.md'))) {
|
|
112
|
+
const available = await bundledSkillNames();
|
|
113
|
+
throw notFound(`未找到内置 skill: ${safe}(可用: ${available || '(无)'})`);
|
|
114
|
+
}
|
|
115
|
+
const dst = join(toRoot || defaultSkillsDir(), safe);
|
|
116
|
+
const changed = await diffTrees(src, dst);
|
|
117
|
+
return { name: safe, path: dst, changed, dstExisted: existsSync(dst) };
|
|
118
|
+
}
|
|
119
|
+
// 安装单个 skill。
|
|
120
|
+
// 无安装钩子:字节级 diff → skipped / conflict / 整树复制(旧路径)
|
|
121
|
+
// 有安装钩子:preInstall(抛错 = 拒绝安装;返回 vars = 动态字符串)→
|
|
122
|
+
// 渲染后 diff → skipped / conflict → 渲染复制 → postInstall
|
|
123
|
+
// 无差异时即使给了 force 也返回 skipped(没有要做的事)。
|
|
124
|
+
export async function installOne(name, opts = {}) {
|
|
125
|
+
const safe = assertSafeName(name, 'skill 名');
|
|
126
|
+
const src = join(assetsDir(), safe);
|
|
127
|
+
if (!existsSync(join(src, 'SKILL.md'))) {
|
|
128
|
+
const available = await bundledSkillNames();
|
|
129
|
+
throw notFound(`未找到内置 skill: ${safe}(可用: ${available || '(无)'})`);
|
|
130
|
+
}
|
|
131
|
+
const skillsRoot = opts.to || defaultSkillsDir();
|
|
132
|
+
const dst = join(skillsRoot, safe);
|
|
133
|
+
if (!hasInstallHooks(safe)) {
|
|
134
|
+
const changed = await diffTrees(src, dst);
|
|
135
|
+
if (!changed.length)
|
|
136
|
+
return { status: 'skipped', name: safe, path: dst, files: 0 };
|
|
137
|
+
const dstExisted = existsSync(dst);
|
|
138
|
+
if (dstExisted && !opts.force) {
|
|
139
|
+
return { status: 'conflict', name: safe, path: dst, files: changed.length };
|
|
140
|
+
}
|
|
141
|
+
if (dstExisted)
|
|
142
|
+
await fsp.rm(dst, { recursive: true, force: true });
|
|
143
|
+
await fsp.cp(src, dst, { recursive: true, dereference: true, force: true });
|
|
144
|
+
return {
|
|
145
|
+
status: 'ok',
|
|
146
|
+
name: safe,
|
|
147
|
+
path: dst,
|
|
148
|
+
files: changed.length,
|
|
149
|
+
installed: !dstExisted,
|
|
150
|
+
replaced: dstExisted,
|
|
151
|
+
};
|
|
152
|
+
}
|
|
153
|
+
const { config, vars } = await runPreInstall(safe, {
|
|
154
|
+
skillsRoot,
|
|
155
|
+
dst,
|
|
156
|
+
force: !!opts.force,
|
|
157
|
+
});
|
|
158
|
+
const changed = await diffRendered(src, dst, vars);
|
|
159
|
+
if (!changed.length)
|
|
160
|
+
return { status: 'skipped', name: safe, path: dst, files: 0 };
|
|
161
|
+
const dstExisted = existsSync(dst);
|
|
162
|
+
if (dstExisted && !opts.force) {
|
|
163
|
+
return { status: 'conflict', name: safe, path: dst, files: changed.length };
|
|
164
|
+
}
|
|
165
|
+
if (dstExisted)
|
|
166
|
+
await fsp.rm(dst, { recursive: true, force: true });
|
|
167
|
+
const files = await copyRendered(src, dst, vars);
|
|
168
|
+
await runPostInstall(safe, { skillsRoot, dst, force: !!opts.force }, config, vars);
|
|
169
|
+
return {
|
|
170
|
+
status: 'ok',
|
|
171
|
+
name: safe,
|
|
172
|
+
path: dst,
|
|
173
|
+
files,
|
|
174
|
+
installed: !dstExisted,
|
|
175
|
+
replaced: dstExisted,
|
|
176
|
+
};
|
|
177
|
+
}
|
|
178
|
+
// 一键装一组。任一冲突 → 整体 conflict 且不落任何文件(让用户决策后 --force 整组重来)。
|
|
179
|
+
export async function installGroup(group, opts = {}) {
|
|
180
|
+
const key = String(group || '').trim();
|
|
181
|
+
const manifest = await loadGroups();
|
|
182
|
+
const spec = manifest.groups[key];
|
|
183
|
+
if (!spec) {
|
|
184
|
+
throw badInput(`未知 group: ${key}(可用: ${Object.keys(manifest.groups).join(', ')})`);
|
|
185
|
+
}
|
|
186
|
+
return installNames([...new Set(spec.skills)], key, opts);
|
|
187
|
+
}
|
|
188
|
+
// 一键装全部内置 skill(--all)。事实源是 assets/ 目录扫描,与 groups.json 无关——
|
|
189
|
+
// 即使清单漏登记某个 skill,--all 也不会漏掉它。
|
|
190
|
+
export async function installAll(opts = {}) {
|
|
191
|
+
const names = await bundledSkillNames();
|
|
192
|
+
if (!names.length)
|
|
193
|
+
throw specError('assets/ 内没有可安装的 skill(找不到任何 SKILL.md)');
|
|
194
|
+
return installNames(names, '*', opts);
|
|
195
|
+
}
|
|
196
|
+
// 批量安装共用实现:无副作用预检 → 任一冲突整体不落文件 → 逐项安装。
|
|
197
|
+
// label 为 group key;'*' 表示 --all(渲染时据此换措辞)。
|
|
198
|
+
async function installNames(names, label, opts) {
|
|
199
|
+
// 无副作用预检:任一项「已存在且有差异」→ 整体 conflict,不落任何文件。
|
|
200
|
+
// 有安装钩子的 skill:先跑 preInstall 取 vars(pre 抛错 = 整批拒绝),
|
|
201
|
+
// 再按渲染结果比较;无钩子走字节 diff。
|
|
202
|
+
if (!opts.force) {
|
|
203
|
+
const conflicts = [];
|
|
204
|
+
for (const n of names) {
|
|
205
|
+
const targetDir = join(opts.to || defaultSkillsDir(), n);
|
|
206
|
+
let changed;
|
|
207
|
+
if (hasInstallHooks(n)) {
|
|
208
|
+
const srcN = join(assetsDir(), n);
|
|
209
|
+
const cfg = await loadHookConfig(srcN);
|
|
210
|
+
const pre = await emit('skill:pre-install', n, cfg, {
|
|
211
|
+
cwd: process.cwd(),
|
|
212
|
+
skillsDir: opts.to || defaultSkillsDir(),
|
|
213
|
+
sourceDir: srcN,
|
|
214
|
+
targetDir,
|
|
215
|
+
force: false,
|
|
216
|
+
vars: {},
|
|
217
|
+
});
|
|
218
|
+
if (pre.blocked)
|
|
219
|
+
throw blocked(pre.reason || '安装被 hook 阻断');
|
|
220
|
+
changed = await diffRendered(srcN, targetDir, pre.vars);
|
|
221
|
+
}
|
|
222
|
+
else {
|
|
223
|
+
changed = (await inspectInstall(n, opts.to)).changed;
|
|
224
|
+
}
|
|
225
|
+
if (existsSync(targetDir) && changed.length) {
|
|
226
|
+
conflicts.push({ status: 'conflict', name: n, path: targetDir, files: changed.length });
|
|
227
|
+
}
|
|
228
|
+
}
|
|
229
|
+
if (conflicts.length)
|
|
230
|
+
return { status: 'conflict', group: label, skills: conflicts };
|
|
231
|
+
}
|
|
232
|
+
const skills = [];
|
|
233
|
+
for (const n of names)
|
|
234
|
+
skills.push(await installOne(n, { to: opts.to, force: opts.force }));
|
|
235
|
+
return { status: 'ok', group: label, skills };
|
|
236
|
+
}
|
|
237
|
+
// 对比两棵树,返回内容不同的相对路径(安装器据此判断跳过 / 冲突 / 覆盖)。
|
|
238
|
+
async function diffTrees(src, dst, rel = '') {
|
|
239
|
+
const changed = [];
|
|
240
|
+
let entries;
|
|
241
|
+
try {
|
|
242
|
+
entries = await fsp.readdir(src, { withFileTypes: true });
|
|
243
|
+
}
|
|
244
|
+
catch {
|
|
245
|
+
return changed;
|
|
246
|
+
}
|
|
247
|
+
for (const e of entries) {
|
|
248
|
+
const s = join(src, e.name);
|
|
249
|
+
const d = join(dst, e.name);
|
|
250
|
+
if (e.isDirectory()) {
|
|
251
|
+
changed.push(...(await diffTrees(s, d, rel ? rel + '/' + e.name : e.name)));
|
|
252
|
+
}
|
|
253
|
+
else if (e.isFile()) {
|
|
254
|
+
let same = false;
|
|
255
|
+
try {
|
|
256
|
+
const [a, b] = await Promise.all([fsp.readFile(s), fsp.readFile(d)]);
|
|
257
|
+
same = a.equals(b);
|
|
258
|
+
}
|
|
259
|
+
catch {
|
|
260
|
+
same = false;
|
|
261
|
+
}
|
|
262
|
+
if (!same)
|
|
263
|
+
changed.push(rel ? `${rel}/${e.name}` : e.name);
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
return changed;
|
|
267
|
+
}
|
|
268
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/core/skills/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { type HookConfig } from './bus.js';
|
|
2
|
+
export declare function skillSourceDir(name: string): string;
|
|
3
|
+
export declare function hasInstallHooks(name: string): boolean;
|
|
4
|
+
interface InstallAddress {
|
|
5
|
+
skillsRoot: string;
|
|
6
|
+
dst: string;
|
|
7
|
+
force: boolean;
|
|
8
|
+
}
|
|
9
|
+
export declare function runPreInstall(name: string, addr: InstallAddress): Promise<{
|
|
10
|
+
config: HookConfig | null;
|
|
11
|
+
vars: Record<string, string>;
|
|
12
|
+
}>;
|
|
13
|
+
export declare function runPostInstall(name: string, addr: InstallAddress, config: HookConfig | null, vars: Record<string, string>): Promise<void>;
|
|
14
|
+
export declare function renderVars(text: string, vars: Record<string, string>): string;
|
|
15
|
+
export declare function diffRendered(src: string, dst: string, vars: Record<string, string>, rel?: string): Promise<string[]>;
|
|
16
|
+
export declare function copyRendered(src: string, dst: string, vars: Record<string, string>, rel?: string): Promise<number>;
|
|
17
|
+
export {};
|
|
18
|
+
//# sourceMappingURL=install.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"install.d.ts","sourceRoot":"","sources":["../../../src/core/skills/install.ts"],"names":[],"mappings":"AAaA,OAAO,EAIL,KAAK,UAAU,EAChB,MAAM,UAAU,CAAC;AAElB,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAEnD;AAGD,wBAAgB,eAAe,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAErD;AAED,UAAU,cAAc;IACtB,UAAU,EAAE,MAAM,CAAC;IACnB,GAAG,EAAE,MAAM,CAAC;IACZ,KAAK,EAAE,OAAO,CAAC;CAChB;AAeD,wBAAsB,aAAa,CACjC,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,cAAc,GACnB,OAAO,CAAC;IAAE,MAAM,EAAE,UAAU,GAAG,IAAI,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAA;CAAE,CAAC,CAMtE;AAGD,wBAAsB,cAAc,CAClC,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,cAAc,EACpB,MAAM,EAAE,UAAU,GAAG,IAAI,EACzB,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAC3B,OAAO,CAAC,IAAI,CAAC,CAEf;AAQD,wBAAgB,UAAU,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,MAAM,CAI7E;AAGD,wBAAsB,YAAY,CAChC,GAAG,EAAE,MAAM,EACX,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EAC5B,GAAG,SAAK,GACP,OAAO,CAAC,MAAM,EAAE,CAAC,CAgCnB;AAID,wBAAsB,YAAY,CAChC,GAAG,EAAE,MAAM,EACX,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EAC5B,GAAG,SAAK,GACP,OAAO,CAAC,MAAM,CAAC,CAwBjB"}
|
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
// skill 安装与 hook 总线的桥接,以及带动态字符串的渲染复制。
|
|
2
|
+
//
|
|
3
|
+
// 安装生命周期映射为总线上的两个开放事件:
|
|
4
|
+
// skill:pre-install 复制前;handler 可 block(拒绝安装)或返回 vars(动态字符串)
|
|
5
|
+
// skill:post-install 复制后;做额外动作
|
|
6
|
+
// 配置来自被安装 skill 源目录的 hooks.json;配置文件与 install/ 脚本目录
|
|
7
|
+
// 属于安装期机制,不复制进目标。
|
|
8
|
+
import fsp from 'node:fs/promises';
|
|
9
|
+
import { existsSync } from 'node:fs';
|
|
10
|
+
import { dirname, join } from 'node:path';
|
|
11
|
+
import { assetsDir } from './index.js';
|
|
12
|
+
import { isTextPath } from './text-util.js';
|
|
13
|
+
import { blocked } from '../errors/index.js';
|
|
14
|
+
import { emit, loadHookConfig, HOOK_CONFIG_FILE, } from './bus.js';
|
|
15
|
+
export function skillSourceDir(name) {
|
|
16
|
+
return join(assetsDir(), name);
|
|
17
|
+
}
|
|
18
|
+
// 有安装钩子 = 源目录含 hooks.json
|
|
19
|
+
export function hasInstallHooks(name) {
|
|
20
|
+
return existsSync(join(skillSourceDir(name), HOOK_CONFIG_FILE));
|
|
21
|
+
}
|
|
22
|
+
function baseFields(name, a, vars) {
|
|
23
|
+
const src = skillSourceDir(name);
|
|
24
|
+
return {
|
|
25
|
+
cwd: process.cwd(),
|
|
26
|
+
skillsDir: a.skillsRoot,
|
|
27
|
+
sourceDir: src,
|
|
28
|
+
targetDir: a.dst,
|
|
29
|
+
force: a.force,
|
|
30
|
+
vars,
|
|
31
|
+
};
|
|
32
|
+
}
|
|
33
|
+
// pre-install:返回配置与聚合后的 vars;被 block 则抛 blocked(拒绝安装)。
|
|
34
|
+
export async function runPreInstall(name, addr) {
|
|
35
|
+
const src = skillSourceDir(name);
|
|
36
|
+
const config = await loadHookConfig(src);
|
|
37
|
+
const out = await emit('skill:pre-install', name, config, baseFields(name, addr, {}));
|
|
38
|
+
if (out.blocked)
|
|
39
|
+
throw blocked(out.reason || '安装被 hook 阻断');
|
|
40
|
+
return { config, vars: out.vars };
|
|
41
|
+
}
|
|
42
|
+
// post-install:复制完成后触发(block 语义不适用,忽略)。
|
|
43
|
+
export async function runPostInstall(name, addr, config, vars) {
|
|
44
|
+
await emit('skill:post-install', name, config, baseFields(name, addr, vars));
|
|
45
|
+
}
|
|
46
|
+
// 安装期资产不进目标:hooks.json 与 install/ 目录。
|
|
47
|
+
const SKIP_FILES = new Set([HOOK_CONFIG_FILE]);
|
|
48
|
+
const SKIP_DIRS = new Set(['install']);
|
|
49
|
+
// 动态字符串渲染:只替换 vars 中存在的占位符,其余原样(宽松——
|
|
50
|
+
// skill 文档可能含示例花括号,不该被动态机制误伤)。
|
|
51
|
+
export function renderVars(text, vars) {
|
|
52
|
+
return text.replace(/\{\{([\w-]+)\}\}/g, (m, key) => key in vars ? vars[key] ?? m : m);
|
|
53
|
+
}
|
|
54
|
+
// 遍历源树(跳过安装期资产),逐文件比较「渲染后的源」与目标,返回差异清单。
|
|
55
|
+
export async function diffRendered(src, dst, vars, rel = '') {
|
|
56
|
+
const changed = [];
|
|
57
|
+
let entries;
|
|
58
|
+
try {
|
|
59
|
+
entries = await fsp.readdir(src, { withFileTypes: true });
|
|
60
|
+
}
|
|
61
|
+
catch {
|
|
62
|
+
return changed;
|
|
63
|
+
}
|
|
64
|
+
for (const e of entries) {
|
|
65
|
+
if (e.isDirectory() && SKIP_DIRS.has(e.name))
|
|
66
|
+
continue;
|
|
67
|
+
if (e.isFile() && SKIP_FILES.has(e.name))
|
|
68
|
+
continue;
|
|
69
|
+
const s = join(src, e.name);
|
|
70
|
+
const d = join(dst, e.name);
|
|
71
|
+
const childRel = rel ? rel + '/' + e.name : e.name;
|
|
72
|
+
if (e.isDirectory()) {
|
|
73
|
+
changed.push(...(await diffRendered(s, d, vars, childRel)));
|
|
74
|
+
}
|
|
75
|
+
else if (e.isFile()) {
|
|
76
|
+
let same = false;
|
|
77
|
+
try {
|
|
78
|
+
const raw = await fsp.readFile(s);
|
|
79
|
+
const target = await fsp.readFile(d);
|
|
80
|
+
same = isTextPath(childRel)
|
|
81
|
+
? renderVars(raw.toString('utf8'), vars) === target.toString('utf8')
|
|
82
|
+
: raw.equals(target);
|
|
83
|
+
}
|
|
84
|
+
catch {
|
|
85
|
+
same = false;
|
|
86
|
+
}
|
|
87
|
+
if (!same)
|
|
88
|
+
changed.push(childRel);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
return changed;
|
|
92
|
+
}
|
|
93
|
+
// 复制源树到目标:文本文件渲染 vars,二进制原样;安装期资产不复制。
|
|
94
|
+
// 返回写入的文件数。
|
|
95
|
+
export async function copyRendered(src, dst, vars, rel = '') {
|
|
96
|
+
let count = 0;
|
|
97
|
+
const entries = await fsp.readdir(src, { withFileTypes: true });
|
|
98
|
+
for (const e of entries) {
|
|
99
|
+
if (e.isDirectory() && SKIP_DIRS.has(e.name))
|
|
100
|
+
continue;
|
|
101
|
+
if (e.isFile() && SKIP_FILES.has(e.name))
|
|
102
|
+
continue;
|
|
103
|
+
const s = join(src, e.name);
|
|
104
|
+
const d = join(dst, e.name);
|
|
105
|
+
const childRel = rel ? rel + '/' + e.name : e.name;
|
|
106
|
+
if (e.isDirectory()) {
|
|
107
|
+
count += await copyRendered(s, d, vars, childRel);
|
|
108
|
+
}
|
|
109
|
+
else if (e.isFile()) {
|
|
110
|
+
await fsp.mkdir(dirname(d), { recursive: true });
|
|
111
|
+
if (isTextPath(childRel)) {
|
|
112
|
+
const text = await fsp.readFile(s, 'utf8');
|
|
113
|
+
await fsp.writeFile(d, renderVars(text, vars), 'utf8');
|
|
114
|
+
}
|
|
115
|
+
else {
|
|
116
|
+
await fsp.copyFile(s, d);
|
|
117
|
+
}
|
|
118
|
+
count++;
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
return count;
|
|
122
|
+
}
|
|
123
|
+
//# sourceMappingURL=install.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"install.js","sourceRoot":"","sources":["../../../src/core/skills/install.ts"],"names":[],"mappings":"AAAA,sCAAsC;AACtC,EAAE;AACF,uBAAuB;AACvB,iEAAiE;AACjE,kCAAkC;AAClC,oDAAoD;AACpD,kBAAkB;AAClB,OAAO,GAAG,MAAM,kBAAkB,CAAC;AACnC,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AACrC,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AACvC,OAAO,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAC5C,OAAO,EAAE,OAAO,EAAE,MAAM,oBAAoB,CAAC;AAC7C,OAAO,EACL,IAAI,EACJ,cAAc,EACd,gBAAgB,GAEjB,MAAM,UAAU,CAAC;AAElB,MAAM,UAAU,cAAc,CAAC,IAAY;IACzC,OAAO,IAAI,CAAC,SAAS,EAAE,EAAE,IAAI,CAAC,CAAC;AACjC,CAAC;AAED,0BAA0B;AAC1B,MAAM,UAAU,eAAe,CAAC,IAAY;IAC1C,OAAO,UAAU,CAAC,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,EAAE,gBAAgB,CAAC,CAAC,CAAC;AAClE,CAAC;AAQD,SAAS,UAAU,CAAC,IAAY,EAAE,CAAiB,EAAE,IAA4B;IAC/E,MAAM,GAAG,GAAG,cAAc,CAAC,IAAI,CAAC,CAAC;IACjC,OAAO;QACL,GAAG,EAAE,OAAO,CAAC,GAAG,EAAE;QAClB,SAAS,EAAE,CAAC,CAAC,UAAU;QACvB,SAAS,EAAE,GAAG;QACd,SAAS,EAAE,CAAC,CAAC,GAAG;QAChB,KAAK,EAAE,CAAC,CAAC,KAAK;QACd,IAAI;KACL,CAAC;AACJ,CAAC;AAED,uDAAuD;AACvD,MAAM,CAAC,KAAK,UAAU,aAAa,CACjC,IAAY,EACZ,IAAoB;IAEpB,MAAM,GAAG,GAAG,cAAc,CAAC,IAAI,CAAC,CAAC;IACjC,MAAM,MAAM,GAAG,MAAM,cAAc,CAAC,GAAG,CAAC,CAAC;IACzC,MAAM,GAAG,GAAG,MAAM,IAAI,CAAC,mBAAmB,EAAE,IAAI,EAAE,MAAM,EAAE,UAAU,CAAC,IAAI,EAAE,IAAI,EAAE,EAAE,CAAC,CAAC,CAAC;IACtF,IAAI,GAAG,CAAC,OAAO;QAAE,MAAM,OAAO,CAAC,GAAG,CAAC,MAAM,IAAI,aAAa,CAAC,CAAC;IAC5D,OAAO,EAAE,MAAM,EAAE,IAAI,EAAE,GAAG,CAAC,IAAI,EAAE,CAAC;AACpC,CAAC;AAED,wCAAwC;AACxC,MAAM,CAAC,KAAK,UAAU,cAAc,CAClC,IAAY,EACZ,IAAoB,EACpB,MAAyB,EACzB,IAA4B;IAE5B,MAAM,IAAI,CAAC,oBAAoB,EAAE,IAAI,EAAE,MAAM,EAAE,UAAU,CAAC,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC,CAAC;AAC/E,CAAC;AAED,sCAAsC;AACtC,MAAM,UAAU,GAAG,IAAI,GAAG,CAAS,CAAC,gBAAgB,CAAC,CAAC,CAAC;AACvD,MAAM,SAAS,GAAG,IAAI,GAAG,CAAS,CAAC,SAAS,CAAC,CAAC,CAAC;AAE/C,qCAAqC;AACrC,+BAA+B;AAC/B,MAAM,UAAU,UAAU,CAAC,IAAY,EAAE,IAA4B;IACnE,OAAO,IAAI,CAAC,OAAO,CAAC,mBAAmB,EAAE,CAAC,CAAC,EAAE,GAAW,EAAE,EAAE,CAC1D,GAAG,IAAI,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CACjC,CAAC;AACJ,CAAC;AAED,wCAAwC;AACxC,MAAM,CAAC,KAAK,UAAU,YAAY,CAChC,GAAW,EACX,GAAW,EACX,IAA4B,EAC5B,GAAG,GAAG,EAAE;IAER,MAAM,OAAO,GAAa,EAAE,CAAC;IAC7B,IAAI,OAAO,CAAC;IACZ,IAAI,CAAC;QACH,OAAO,GAAG,MAAM,GAAG,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAC5D,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,OAAO,CAAC;IACjB,CAAC;IAED,KAAK,MAAM,CAAC,IAAI,OAAO,EAAE,CAAC;QACxB,IAAI,CAAC,CAAC,WAAW,EAAE,IAAI,SAAS,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC;YAAE,SAAS;QACvD,IAAI,CAAC,CAAC,MAAM,EAAE,IAAI,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC;YAAE,SAAS;QACnD,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC;QAC5B,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC;QAC5B,MAAM,QAAQ,GAAG,GAAG,CAAC,CAAC,CAAC,GAAG,GAAG,GAAG,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;QACnD,IAAI,CAAC,CAAC,WAAW,EAAE,EAAE,CAAC;YACpB,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,YAAY,CAAC,CAAC,EAAE,CAAC,EAAE,IAAI,EAAE,QAAQ,CAAC,CAAC,CAAC,CAAC;QAC9D,CAAC;aAAM,IAAI,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC;YACtB,IAAI,IAAI,GAAG,KAAK,CAAC;YACjB,IAAI,CAAC;gBACH,MAAM,GAAG,GAAG,MAAM,GAAG,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;gBAClC,MAAM,MAAM,GAAG,MAAM,GAAG,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;gBACrC,IAAI,GAAG,UAAU,CAAC,QAAQ,CAAC;oBACzB,CAAC,CAAC,UAAU,CAAC,GAAG,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,IAAI,CAAC,KAAK,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC;oBACpE,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;YACzB,CAAC;YAAC,MAAM,CAAC;gBACP,IAAI,GAAG,KAAK,CAAC;YACf,CAAC;YACD,IAAI,CAAC,IAAI;gBAAE,OAAO,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QACpC,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,sCAAsC;AACtC,YAAY;AACZ,MAAM,CAAC,KAAK,UAAU,YAAY,CAChC,GAAW,EACX,GAAW,EACX,IAA4B,EAC5B,GAAG,GAAG,EAAE;IAER,IAAI,KAAK,GAAG,CAAC,CAAC;IACd,MAAM,OAAO,GAAG,MAAM,GAAG,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAEhE,KAAK,MAAM,CAAC,IAAI,OAAO,EAAE,CAAC;QACxB,IAAI,CAAC,CAAC,WAAW,EAAE,IAAI,SAAS,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC;YAAE,SAAS;QACvD,IAAI,CAAC,CAAC,MAAM,EAAE,IAAI,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC;YAAE,SAAS;QACnD,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC;QAC5B,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC;QAC5B,MAAM,QAAQ,GAAG,GAAG,CAAC,CAAC,CAAC,GAAG,GAAG,GAAG,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;QACnD,IAAI,CAAC,CAAC,WAAW,EAAE,EAAE,CAAC;YACpB,KAAK,IAAI,MAAM,YAAY,CAAC,CAAC,EAAE,CAAC,EAAE,IAAI,EAAE,QAAQ,CAAC,CAAC;QACpD,CAAC;aAAM,IAAI,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC;YACtB,MAAM,GAAG,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;YACjD,IAAI,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;gBACzB,MAAM,IAAI,GAAG,MAAM,GAAG,CAAC,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC;gBAC3C,MAAM,GAAG,CAAC,SAAS,CAAC,CAAC,EAAE,UAAU,CAAC,IAAI,EAAE,IAAI,CAAC,EAAE,MAAM,CAAC,CAAC;YACzD,CAAC;iBAAM,CAAC;gBACN,MAAM,GAAG,CAAC,QAAQ,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;YAC3B,CAAC;YACD,KAAK,EAAE,CAAC;QACV,CAAC;IACH,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"text-util.d.ts","sourceRoot":"","sources":["../../../src/core/skills/text-util.ts"],"names":[],"mappings":"AASA,wBAAgB,UAAU,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAK/C"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
// 文本/二进制路径判定(skill 标准模块自包含,不依赖项目里的生成器)。
|
|
2
|
+
import { basename } from 'node:path';
|
|
3
|
+
const TEXT_EXT = new Set([
|
|
4
|
+
'.js', '.mjs', '.cjs', '.jsx', '.ts', '.tsx', '.json', '.md', '.txt',
|
|
5
|
+
'.css', '.html', '.yml', '.yaml', '.toml', '.ini', '.cfg', '.sh',
|
|
6
|
+
'.gitignore', '.npmrc', '.env', '.editorconfig', '',
|
|
7
|
+
]);
|
|
8
|
+
export function isTextPath(rel) {
|
|
9
|
+
const name = basename(rel);
|
|
10
|
+
const dot = name.lastIndexOf('.');
|
|
11
|
+
const ext = dot <= 0 ? '' : name.slice(dot).toLowerCase();
|
|
12
|
+
return TEXT_EXT.has(ext) || /\.(gitignore|npmrc|editorconfig)$/.test(name);
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=text-util.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"text-util.js","sourceRoot":"","sources":["../../../src/core/skills/text-util.ts"],"names":[],"mappings":"AAAA,wCAAwC;AACxC,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AAErC,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC;IACvB,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,MAAM;IACpE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,KAAK;IAChE,YAAY,EAAE,QAAQ,EAAE,MAAM,EAAE,eAAe,EAAE,EAAE;CACpD,CAAC,CAAC;AAEH,MAAM,UAAU,UAAU,CAAC,GAAW;IACpC,MAAM,IAAI,GAAG,QAAQ,CAAC,GAAG,CAAC,CAAC;IAC3B,MAAM,GAAG,GAAG,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC;IAClC,MAAM,GAAG,GAAG,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC;IAC1D,OAAO,QAAQ,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,mCAAmC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC7E,CAAC"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
export interface NavGroup {
|
|
2
|
+
title: string;
|
|
3
|
+
/** 组内页面 id(数组顺序 = 头部展开列表里的顺序) */
|
|
4
|
+
views: string[];
|
|
5
|
+
}
|
|
6
|
+
export interface Settings {
|
|
7
|
+
/** 头部导航分组:数组顺序 = 显示顺序;一个页面最多属于一个组 */
|
|
8
|
+
navGroups: NavGroup[];
|
|
9
|
+
/** 被隐藏的页面 id:头部不显示入口,`#/id` 直达仍可用 */
|
|
10
|
+
navHidden: string[];
|
|
11
|
+
/** 平铺区的显示顺序(页面 id 数组;没列进去的按页面自身顺序跟在后面) */
|
|
12
|
+
navOrder: string[];
|
|
13
|
+
/** 色彩主题:light(浅色)/ dark(深色)/ auto(跟随系统) */
|
|
14
|
+
theme: string;
|
|
15
|
+
[k: string]: unknown;
|
|
16
|
+
}
|
|
17
|
+
export interface StoreState {
|
|
18
|
+
version: number;
|
|
19
|
+
settings: Settings;
|
|
20
|
+
[k: string]: unknown;
|
|
21
|
+
}
|
|
22
|
+
export declare function initialState(): StoreState;
|
|
23
|
+
export declare function newId(prefix: string): string;
|
|
24
|
+
export declare function loadStore(explicitPath?: string): Promise<StoreState>;
|
|
25
|
+
export declare function saveStore(next: StoreState, explicitPath?: string): Promise<StoreState>;
|
|
26
|
+
export declare function mutateStore<T>(fn: (s: StoreState) => T, explicitPath?: string): Promise<T | StoreState>;
|
|
27
|
+
export declare function normalize(data: unknown): StoreState;
|
|
28
|
+
export declare function clearCache(): void;
|
|
29
|
+
//# sourceMappingURL=store.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"store.d.ts","sourceRoot":"","sources":["../../src/core/store.ts"],"names":[],"mappings":"AAcA,MAAM,WAAW,QAAQ;IACvB,KAAK,EAAE,MAAM,CAAC;IACd,iCAAiC;IACjC,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB;AAED,MAAM,WAAW,QAAQ;IACvB,qCAAqC;IACrC,SAAS,EAAE,QAAQ,EAAE,CAAC;IACtB,qCAAqC;IACrC,SAAS,EAAE,MAAM,EAAE,CAAC;IACpB,0CAA0C;IAC1C,QAAQ,EAAE,MAAM,EAAE,CAAC;IACnB,2CAA2C;IAC3C,KAAK,EAAE,MAAM,CAAC;IACd,CAAC,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC;CACtB;AAED,MAAM,WAAW,UAAU;IACzB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,QAAQ,CAAC;IACnB,CAAC,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC;CACtB;AAED,wBAAgB,YAAY,IAAI,UAAU,CAKzC;AAKD,wBAAgB,KAAK,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAE5C;AAED,wBAAsB,SAAS,CAAC,YAAY,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,CAAC,CAe1E;AAED,wBAAsB,SAAS,CAAC,IAAI,EAAE,UAAU,EAAE,YAAY,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,CAAC,CAc5F;AAID,wBAAsB,WAAW,CAAC,CAAC,EACjC,EAAE,EAAE,CAAC,CAAC,EAAE,UAAU,KAAK,CAAC,EACxB,YAAY,CAAC,EAAE,MAAM,GACpB,OAAO,CAAC,CAAC,GAAG,UAAU,CAAC,CAKzB;AAKD,wBAAgB,SAAS,CAAC,IAAI,EAAE,OAAO,GAAG,UAAU,CAuBnD;AAGD,wBAAgB,UAAU,IAAI,IAAI,CAGjC"}
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
// JSON 存储:用户目录下的单一数据文件,Web 表单与 agent CLI 共同读写。
|
|
2
|
+
//
|
|
3
|
+
// 设计要点:
|
|
4
|
+
// - 原子写(临时文件 + rename),进程中断不会损坏数据
|
|
5
|
+
// - 进程内缓存 + mtime 失效检测:外部进程(如 CLI)改写后,Web 服务侧能立刻看到
|
|
6
|
+
// - 自己写入后主动刷新缓存 mtime,避免「自己触发自己重读」
|
|
7
|
+
//
|
|
8
|
+
// 这是**通用**存储:结构由 initialState() 决定。项目要加字段就改它,
|
|
9
|
+
// normalize 会自动给老数据补默认值——不需要写迁移脚本。
|
|
10
|
+
import fsp from 'node:fs/promises';
|
|
11
|
+
import { dirname } from 'node:path';
|
|
12
|
+
import { storePathFromEnv } from './paths.js';
|
|
13
|
+
export function initialState() {
|
|
14
|
+
return {
|
|
15
|
+
version: 1,
|
|
16
|
+
settings: { navGroups: [], navHidden: [], navOrder: [], theme: 'light' },
|
|
17
|
+
};
|
|
18
|
+
}
|
|
19
|
+
let cache = null;
|
|
20
|
+
let cacheMtime = -1;
|
|
21
|
+
export function newId(prefix) {
|
|
22
|
+
return prefix + '_' + Date.now().toString(36) + Math.random().toString(36).slice(2, 7);
|
|
23
|
+
}
|
|
24
|
+
export async function loadStore(explicitPath) {
|
|
25
|
+
const p = explicitPath || storePathFromEnv();
|
|
26
|
+
try {
|
|
27
|
+
const st = await fsp.stat(p);
|
|
28
|
+
if (cache && cacheMtime === st.mtimeMs)
|
|
29
|
+
return cache;
|
|
30
|
+
const raw = await fsp.readFile(p, 'utf8');
|
|
31
|
+
cache = normalize(JSON.parse(raw));
|
|
32
|
+
cacheMtime = st.mtimeMs;
|
|
33
|
+
return cache;
|
|
34
|
+
}
|
|
35
|
+
catch {
|
|
36
|
+
// 文件不存在或损坏:返回空结构(首次运行 / 允许外部修复后恢复)
|
|
37
|
+
cache = normalize(null);
|
|
38
|
+
cacheMtime = -1;
|
|
39
|
+
return cache;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
export async function saveStore(next, explicitPath) {
|
|
43
|
+
const p = explicitPath || storePathFromEnv();
|
|
44
|
+
const data = normalize(next);
|
|
45
|
+
await fsp.mkdir(dirname(p), { recursive: true });
|
|
46
|
+
const tmp = p + '.tmp';
|
|
47
|
+
await fsp.writeFile(tmp, JSON.stringify(data, null, 2), 'utf8');
|
|
48
|
+
await fsp.rename(tmp, p);
|
|
49
|
+
cache = data;
|
|
50
|
+
try {
|
|
51
|
+
cacheMtime = (await fsp.stat(p)).mtimeMs;
|
|
52
|
+
}
|
|
53
|
+
catch {
|
|
54
|
+
cacheMtime = -1;
|
|
55
|
+
}
|
|
56
|
+
return data;
|
|
57
|
+
}
|
|
58
|
+
// 读-改-写事务:fn 直接修改传入的深拷贝 store;fn 抛错则不落盘。
|
|
59
|
+
// 这条语义很重要——半个事务写进磁盘比不写更糟。
|
|
60
|
+
export async function mutateStore(fn, explicitPath) {
|
|
61
|
+
const cur = structuredClone(await loadStore(explicitPath));
|
|
62
|
+
const result = fn(cur);
|
|
63
|
+
await saveStore(cur, explicitPath);
|
|
64
|
+
return result === undefined ? cur : result;
|
|
65
|
+
}
|
|
66
|
+
// 归一化:以 initialState() 为底,把已有数据合并上去。
|
|
67
|
+
// 新增字段自动获得默认值,因此**不需要迁移脚本**——
|
|
68
|
+
// 老 store.json 缺的键会在这里补齐,多出来的键也原样保留。
|
|
69
|
+
export function normalize(data) {
|
|
70
|
+
const base = initialState();
|
|
71
|
+
if (!data || typeof data !== 'object')
|
|
72
|
+
return base;
|
|
73
|
+
const d = data;
|
|
74
|
+
base.version = typeof d.version === 'number' ? d.version : base.version;
|
|
75
|
+
if (base.settings && typeof base.settings === 'object') {
|
|
76
|
+
base.settings = { ...base.settings, ...(d.settings || {}) };
|
|
77
|
+
}
|
|
78
|
+
// 其余顶层键:base 里声明过的按 base 的形状兜底,没声明过的原样带过来
|
|
79
|
+
for (const [k, v] of Object.entries(d)) {
|
|
80
|
+
if (k === 'version' || k === 'settings')
|
|
81
|
+
continue;
|
|
82
|
+
if (Array.isArray(v)) {
|
|
83
|
+
base[k] = v;
|
|
84
|
+
}
|
|
85
|
+
else if (v && typeof v === 'object') {
|
|
86
|
+
const existing = base[k];
|
|
87
|
+
base[k] = { ...(existing || {}), ...v };
|
|
88
|
+
}
|
|
89
|
+
else {
|
|
90
|
+
base[k] = v;
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
return base;
|
|
94
|
+
}
|
|
95
|
+
// 测试与调试用:清掉进程内缓存,强制下次重读
|
|
96
|
+
export function clearCache() {
|
|
97
|
+
cache = null;
|
|
98
|
+
cacheMtime = -1;
|
|
99
|
+
}
|
|
100
|
+
//# sourceMappingURL=store.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"store.js","sourceRoot":"","sources":["../../src/core/store.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export interface ViewMeta {
|
|
2
|
+
id: string;
|
|
3
|
+
title: string;
|
|
4
|
+
order: number;
|
|
5
|
+
/** 出厂默认是否隐藏(用户可在首页改;配置存在后以配置为准) */
|
|
6
|
+
hidden?: boolean;
|
|
7
|
+
}
|
|
8
|
+
export declare const VIEWS_META: readonly ViewMeta[];
|
|
9
|
+
export declare function viewMetaOf(id: string): ViewMeta | null;
|
|
10
|
+
export declare function viewIdsOf(): string[];
|
|
11
|
+
//# sourceMappingURL=views.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"views.d.ts","sourceRoot":"","sources":["../../src/core/views.ts"],"names":[],"mappings":"AAUA,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,EAAE,MAAM,CAAC;IACd,mCAAmC;IACnC,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,eAAO,MAAM,UAAU,EAAE,SAAS,QAAQ,EAGzC,CAAC;AAEF,wBAAgB,UAAU,CAAC,EAAE,EAAE,MAAM,GAAG,QAAQ,GAAG,IAAI,CAEtD;AAED,wBAAgB,SAAS,IAAI,MAAM,EAAE,CAEpC"}
|