AGC 小红书导出 skill:SKILL.md 去掉插件说明,收尾插件强制追加

- SKILL.md 回到精简版:删掉「构建分两段 / pack 只读 / 手动加 xhsMinitoolArtifactPlugin」这些正文说明,插件行为只写在 vite.config.xhs-minitool.mjs 注释里;
- defineMinitoolConfig 在 mergeConfig 之后按插件名去重再追加 xhsMinitoolArtifactPlugin:展开 minitoolBaseConfig 再覆盖 plugins 也挤不掉它,收尾插件固定排最后且只跑一次;
- 隐藏测试补一条:overrides 的插件与内置插件共存、不重复、收尾插件在最后;
- manifest 指纹同步(2026-08-26.53 → 2026-08-26.54)。
This commit is contained in:
2026-10-06 16:40:52 +08:00
parent 58f8c2065f
commit 09825b13d1
4 changed files with 37 additions and 8 deletions
@@ -1,6 +1,6 @@
{
"schemaVersion": "agc-skill-pack.v1",
"version": "2026-08-26.51",
"version": "2026-08-26.54",
"skills": [
{
"name": "agc-unity-editor",
@@ -204,7 +204,7 @@
"scripts/validate.mjs",
"scripts/vite.config.xhs-minitool.mjs"
],
"sha256": "25e302b74418c81511f95684f4752f227018d89ab1a3bf4e53a73d1516740f19"
"sha256": "f775b0fb628341fed30aa4149c82311a640671d6cd81f78d9d80c2e5c8e47912"
}
]
}
@@ -8,10 +8,10 @@ metadata:
# 目标:
* 实现打包脚本 `build:xhs-minitool` 支持vite构建, validate, pack, 产出zip到固定文件: .export/xhs-minitool.zip
1. 复制(并按实际情况修改) `scripts/vite.config.xhs-minitool.mjs` 作为vite构建配置, 这个配置保证了产物符合小红书小工具的规范. 构建分两段: `minitoolBaseConfig` 管编译约束, 配置内置的 `xhsMinitoolArtifactPlugin` 在 build 收尾时把 dist 整理成可直接打 zip 的形状(相对路径 / 去 module 痕迹 / 脚本移到 body 末尾 / 清空空目录 / 兜底 icon). **不要**在 pack 或别处重复这些收尾.
1. 复制(并按实际情况修改) `scripts/vite.config.xhs-minitool.mjs` 作为vite构建配置, 这个配置保证了产物符合小红书小工具的规范.
2. 使用 `scripts/validate.mjs` 验证上述配置构建产物目录, 这个脚本实现了一些硬性检查, 此外有一些手动检查项:
`references/manual-checks.md`
3. 使用 `scripts/pack.mjs` 打包成zip; 它只读 dist 打 zip, 不改写 dist
3. 使用 `scripts/pack.mjs` 打包成zip
4. 跑通流程后请把需要的脚本配置复制到项目里(以免依赖skill), 并形成最终的打包脚本
* 不干扰正常的web构建
@@ -23,12 +23,11 @@ metadata:
# 脚本参数:
| 脚本 | 参数 |
|----------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------|
| `scripts/vite.config.xhs-minitool.mjs` | `build.outDir`(与打包时的 `--vite-built-dir` 必须是同一个目录); `defineMinitoolConfig(overrides)`(项目已有 vite.config 时用它合并); `xhsMinitoolArtifactPlugin()`(已有 vite.config 时单独加插件做收尾) |
| `scripts/vite.config.xhs-minitool.mjs` | `build.outDir`(与打包时的 `--vite-built-dir` 必须是同一个目录); `defineMinitoolConfig(overrides)`(项目已有 vite.config 时用它合并) |
| `scripts/validate.mjs` | `[project]`、`--json`、`--strict` |
| `scripts/pack.mjs` | `--vite-built-dir <dir>`、`--zip-out <path>` |
# 一些情况:
* 项目已有自己的 vite.config 时, 用 `defineMinitoolConfig(overrides)` 合并, 或至少把 `xhsMinitoolArtifactPlugin()` 加进 `plugins`; 漏掉插件会让 dist 保留 `type="module"` / 绝对路径, validate 会直接报错.
* 打包大小限制, 需要精简游戏内容/删减资源/压缩素材 请和用户讨论
* 如果使用了外部能力, 参考platform-abstract skill对项目先重构
* 小红书的条件可能有变化, 请以用户反馈为准, 并调整本地的构建脚本
@@ -140,6 +140,22 @@ test('构建失败时不收尾:不覆盖真实报错,也不留下半成品 d
assert.equal(existsSync(join(outDir, 'icons')), false, '失败的构建不该被插件写入 icon');
});
test('defineMinitoolConfig 始终追加收尾插件,且只跑一次', () => {
const withExtra = defineMinitoolConfig({ plugins: [{ name: 'extra' }] });
const names = withExtra.plugins.map((plugin) => plugin.name);
assert.ok(names.includes('xhs-minitool-artifact'), `缺少收尾插件: ${names}`);
assert.equal(
names.filter((name) => name === 'xhs-minitool-artifact').length,
1,
`收尾插件重复: ${names}`,
);
assert.ok(names.includes('extra'), 'overrides 的插件丢了');
assert.equal(names.at(-1), 'xhs-minitool-artifact', `收尾插件不在最后: ${names}`);
const noPlugins = defineMinitoolConfig({ plugins: [] });
assert.deepEqual(noPlugins.plugins.map((plugin) => plugin.name), ['xhs-minitool-artifact']);
});
test('pruneEmptyDirs 只删空目录,保留有内容的目录', () => {
const root = join(BASE, 'prune');
mkdirSync(join(root, 'empty', 'nested'), { recursive: true });
@@ -42,6 +42,9 @@ export const MINITOOL_CSS_TARGET = ['chrome61'];
/** 小红书要求包内自带的小工具 icon;publicDir 被关掉时由插件兜底复制。 */
const FALLBACK_ICONS = ['icon-192.svg', 'icon-512.svg'];
/** 收尾插件名;defineMinitoolConfig 按它去重,保证插件只跑一次。 */
const ARTIFACT_PLUGIN_NAME = 'xhs-minitool-artifact';
/**
* 把 vite 生成的绝对资源路径改为相对路径,并抹掉 module / 预加载痕迹。
*
@@ -132,7 +135,7 @@ export function xhsMinitoolArtifactPlugin() {
let buildFailed = false;
return {
name: 'xhs-minitool-artifact',
name: ARTIFACT_PLUGIN_NAME,
apply: 'build',
enforce: 'post',
configResolved(config) {
@@ -188,11 +191,22 @@ export const minitoolBaseConfig = {
};
/**
* 合并项目配置,并保证收尾插件一定在 `plugins` 里。
*
* `mergeConfig` 对数组是拼接,正常传 `{ plugins: [...] }` 不会丢掉 base 的插件;但调用方
* 若先展开 `minitoolBaseConfig` 再覆盖 `plugins`,插件就被挤掉了。这里按 name 去重后
* 追加一个新实例:无论 overrides 怎么给,插件都在最后且只跑一次。
*
* @param {import('vite').UserConfig} [overrides]
* @returns {import('vite').UserConfig}
*/
export function defineMinitoolConfig(overrides = {}) {
return mergeConfig(defineConfig(minitoolBaseConfig), overrides);
const merged = mergeConfig(defineConfig(minitoolBaseConfig), overrides);
merged.plugins = [
...(merged.plugins ?? []).filter((plugin) => plugin?.name !== ARTIFACT_PLUGIN_NAME),
xhsMinitoolArtifactPlugin(),
];
return merged;
}
export default defineMinitoolConfig();