@vetta-org/plugin-vite 0.0.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.
- package/dist/index.d.ts +18 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +105 -0
- package/dist/index.js.map +1 -0
- package/dist/pack.d.ts +16 -0
- package/dist/pack.d.ts.map +1 -0
- package/dist/pack.js +299 -0
- package/dist/pack.js.map +1 -0
- package/package.json +38 -0
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { type ModuleFederationOptions } from "@module-federation/vite";
|
|
2
|
+
import type { PluginOption } from "vite";
|
|
3
|
+
import { type CreateVettaPluginPackageOptions } from "./pack.js";
|
|
4
|
+
export interface VettaPluginPackageOptions extends Omit<CreateVettaPluginPackageOptions, "rootDir" | "distDir"> {
|
|
5
|
+
enabled?: boolean;
|
|
6
|
+
}
|
|
7
|
+
export interface VettaPluginFederationOptions {
|
|
8
|
+
name: string;
|
|
9
|
+
expose?: string;
|
|
10
|
+
entry?: string;
|
|
11
|
+
manifestFileName?: string;
|
|
12
|
+
remoteEntryFileName?: string;
|
|
13
|
+
shared?: ModuleFederationOptions["shared"];
|
|
14
|
+
package?: boolean | VettaPluginPackageOptions;
|
|
15
|
+
}
|
|
16
|
+
export declare function createVettaPluginFederationConfig(options: VettaPluginFederationOptions): ModuleFederationOptions;
|
|
17
|
+
export declare function vettaPluginFederation(options: VettaPluginFederationOptions): PluginOption[];
|
|
18
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAc,KAAK,uBAAuB,EAAE,MAAM,yBAAyB,CAAC;AACnF,OAAO,KAAK,EAAU,YAAY,EAAE,MAAM,MAAM,CAAC;AACjD,OAAO,EAAE,KAAK,+BAA+B,EAA4B,MAAM,WAAW,CAAC;AAE3F,MAAM,WAAW,yBAA0B,SAAQ,IAAI,CAAC,+BAA+B,EAAE,SAAS,GAAG,SAAS,CAAC;IAC9G,OAAO,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,WAAW,4BAA4B;IAC5C,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B,MAAM,CAAC,EAAE,uBAAuB,CAAC,QAAQ,CAAC,CAAC;IAC3C,OAAO,CAAC,EAAE,OAAO,GAAG,yBAAyB,CAAC;CAC9C;AAED,wBAAgB,iCAAiC,CAAC,OAAO,EAAE,4BAA4B,GAAG,uBAAuB,CAiChH;AA6DD,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,4BAA4B,GAAG,YAAY,EAAE,CAW3F","sourcesContent":["import { federation, type ModuleFederationOptions } from \"@module-federation/vite\";\nimport type { Plugin, PluginOption } from \"vite\";\nimport { type CreateVettaPluginPackageOptions, createVettaPluginPackage } from \"./pack.js\";\n\nexport interface VettaPluginPackageOptions extends Omit<CreateVettaPluginPackageOptions, \"rootDir\" | \"distDir\"> {\n\tenabled?: boolean;\n}\n\nexport interface VettaPluginFederationOptions {\n\tname: string;\n\texpose?: string;\n\tentry?: string;\n\tmanifestFileName?: string;\n\tremoteEntryFileName?: string;\n\tshared?: ModuleFederationOptions[\"shared\"];\n\tpackage?: boolean | VettaPluginPackageOptions;\n}\n\nexport function createVettaPluginFederationConfig(options: VettaPluginFederationOptions): ModuleFederationOptions {\n\tconst expose = options.expose ?? \"./plugin\";\n\tconst entry = options.entry ?? \"./src/index.tsx\";\n\treturn {\n\t\tname: options.name,\n\t\tfilename: options.remoteEntryFileName ?? \"remoteEntry.js\",\n\t\texposes: {\n\t\t\t[expose]: entry,\n\t\t},\n\t\tmanifest: {\n\t\t\tfileName: options.manifestFileName ?? \"mf-manifest.json\",\n\t\t},\n\t\tdts: false,\n\t\tshared: {\n\t\t\treact: {\n\t\t\t\tsingleton: true,\n\t\t\t\timport: false,\n\t\t\t\trequiredVersion: \"*\",\n\t\t\t},\n\t\t\t\"react-dom\": {\n\t\t\t\tsingleton: true,\n\t\t\t\timport: false,\n\t\t\t\trequiredVersion: \"*\",\n\t\t\t},\n\t\t\t// Match host plugin-shared-modules (tldraw remotes may require this subpath).\n\t\t\t\"react-dom/client\": {\n\t\t\t\tsingleton: true,\n\t\t\t\timport: false,\n\t\t\t\trequiredVersion: \"*\",\n\t\t\t},\n\t\t\t...options.shared,\n\t\t},\n\t};\n}\n\nfunction createBuildDefaultsPlugin(entry: string): Plugin {\n\treturn {\n\t\tname: \"vetta-plugin-build-defaults\",\n\t\tapply: \"build\",\n\t\tconfig() {\n\t\t\treturn {\n\t\t\t\tbuild: {\n\t\t\t\t\trollupOptions: {\n\t\t\t\t\t\tinput: entry,\n\t\t\t\t\t\texternal: [\"@vetta-org/plugin-sdk\"],\n\t\t\t\t\t\toutput: {\n\t\t\t\t\t\t\tassetFileNames(assetInfo) {\n\t\t\t\t\t\t\t\treturn assetInfo.names.some((name) => name.endsWith(\".css\"))\n\t\t\t\t\t\t\t\t\t? \"style.css\"\n\t\t\t\t\t\t\t\t\t: \"assets/[name]-[hash][extname]\";\n\t\t\t\t\t\t\t},\n\t\t\t\t\t\t\tpaths: {\n\t\t\t\t\t\t\t\t\"@vetta-org/plugin-sdk\": \"vetta-host://plugin-sdk\",\n\t\t\t\t\t\t\t},\n\t\t\t\t\t\t},\n\t\t\t\t\t},\n\t\t\t\t},\n\t\t\t};\n\t\t},\n\t};\n}\n\nfunction createPackagePlugin(options: VettaPluginPackageOptions): Plugin {\n\tlet rootDir = \"\";\n\tlet distDir = \"\";\n\tlet buildFailed = false;\n\n\treturn {\n\t\tname: \"vetta-plugin-package\",\n\t\tapply: \"build\",\n\t\tbuildStart() {\n\t\t\tbuildFailed = false;\n\t\t},\n\t\tbuildEnd(error) {\n\t\t\tbuildFailed = error !== undefined;\n\t\t},\n\t\tconfigResolved(config) {\n\t\t\trootDir = config.root;\n\t\t\tdistDir = config.build.outDir;\n\t\t},\n\t\tasync closeBundle() {\n\t\t\tif (options.enabled === false || buildFailed) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tconst result = await createVettaPluginPackage({\n\t\t\t\t...options,\n\t\t\t\trootDir,\n\t\t\t\tdistDir,\n\t\t\t});\n\t\t\tconsole.log(`[vetta-plugin-vite] Wrote ${result.outputPath} with ${result.files.length} runtime files`);\n\t\t},\n\t};\n}\n\nexport function vettaPluginFederation(options: VettaPluginFederationOptions): PluginOption[] {\n\tconst packageOptions = typeof options.package === \"object\" ? options.package : {};\n\tconst entry = options.entry ?? \"./src/index.tsx\";\n\tconst plugins: PluginOption[] = [\n\t\tcreateBuildDefaultsPlugin(entry),\n\t\t...federation(createVettaPluginFederationConfig(options)),\n\t];\n\tif (options.package !== false) {\n\t\tplugins.push(createPackagePlugin(packageOptions));\n\t}\n\treturn plugins;\n}\n"]}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
import { federation } from "@module-federation/vite";
|
|
2
|
+
import { createVettaPluginPackage } from "./pack.js";
|
|
3
|
+
export function createVettaPluginFederationConfig(options) {
|
|
4
|
+
const expose = options.expose ?? "./plugin";
|
|
5
|
+
const entry = options.entry ?? "./src/index.tsx";
|
|
6
|
+
return {
|
|
7
|
+
name: options.name,
|
|
8
|
+
filename: options.remoteEntryFileName ?? "remoteEntry.js",
|
|
9
|
+
exposes: {
|
|
10
|
+
[expose]: entry,
|
|
11
|
+
},
|
|
12
|
+
manifest: {
|
|
13
|
+
fileName: options.manifestFileName ?? "mf-manifest.json",
|
|
14
|
+
},
|
|
15
|
+
dts: false,
|
|
16
|
+
shared: {
|
|
17
|
+
react: {
|
|
18
|
+
singleton: true,
|
|
19
|
+
import: false,
|
|
20
|
+
requiredVersion: "*",
|
|
21
|
+
},
|
|
22
|
+
"react-dom": {
|
|
23
|
+
singleton: true,
|
|
24
|
+
import: false,
|
|
25
|
+
requiredVersion: "*",
|
|
26
|
+
},
|
|
27
|
+
// Match host plugin-shared-modules (tldraw remotes may require this subpath).
|
|
28
|
+
"react-dom/client": {
|
|
29
|
+
singleton: true,
|
|
30
|
+
import: false,
|
|
31
|
+
requiredVersion: "*",
|
|
32
|
+
},
|
|
33
|
+
...options.shared,
|
|
34
|
+
},
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
function createBuildDefaultsPlugin(entry) {
|
|
38
|
+
return {
|
|
39
|
+
name: "vetta-plugin-build-defaults",
|
|
40
|
+
apply: "build",
|
|
41
|
+
config() {
|
|
42
|
+
return {
|
|
43
|
+
build: {
|
|
44
|
+
rollupOptions: {
|
|
45
|
+
input: entry,
|
|
46
|
+
external: ["@vetta-org/plugin-sdk"],
|
|
47
|
+
output: {
|
|
48
|
+
assetFileNames(assetInfo) {
|
|
49
|
+
return assetInfo.names.some((name) => name.endsWith(".css"))
|
|
50
|
+
? "style.css"
|
|
51
|
+
: "assets/[name]-[hash][extname]";
|
|
52
|
+
},
|
|
53
|
+
paths: {
|
|
54
|
+
"@vetta-org/plugin-sdk": "vetta-host://plugin-sdk",
|
|
55
|
+
},
|
|
56
|
+
},
|
|
57
|
+
},
|
|
58
|
+
},
|
|
59
|
+
};
|
|
60
|
+
},
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
function createPackagePlugin(options) {
|
|
64
|
+
let rootDir = "";
|
|
65
|
+
let distDir = "";
|
|
66
|
+
let buildFailed = false;
|
|
67
|
+
return {
|
|
68
|
+
name: "vetta-plugin-package",
|
|
69
|
+
apply: "build",
|
|
70
|
+
buildStart() {
|
|
71
|
+
buildFailed = false;
|
|
72
|
+
},
|
|
73
|
+
buildEnd(error) {
|
|
74
|
+
buildFailed = error !== undefined;
|
|
75
|
+
},
|
|
76
|
+
configResolved(config) {
|
|
77
|
+
rootDir = config.root;
|
|
78
|
+
distDir = config.build.outDir;
|
|
79
|
+
},
|
|
80
|
+
async closeBundle() {
|
|
81
|
+
if (options.enabled === false || buildFailed) {
|
|
82
|
+
return;
|
|
83
|
+
}
|
|
84
|
+
const result = await createVettaPluginPackage({
|
|
85
|
+
...options,
|
|
86
|
+
rootDir,
|
|
87
|
+
distDir,
|
|
88
|
+
});
|
|
89
|
+
console.log(`[vetta-plugin-vite] Wrote ${result.outputPath} with ${result.files.length} runtime files`);
|
|
90
|
+
},
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
export function vettaPluginFederation(options) {
|
|
94
|
+
const packageOptions = typeof options.package === "object" ? options.package : {};
|
|
95
|
+
const entry = options.entry ?? "./src/index.tsx";
|
|
96
|
+
const plugins = [
|
|
97
|
+
createBuildDefaultsPlugin(entry),
|
|
98
|
+
...federation(createVettaPluginFederationConfig(options)),
|
|
99
|
+
];
|
|
100
|
+
if (options.package !== false) {
|
|
101
|
+
plugins.push(createPackagePlugin(packageOptions));
|
|
102
|
+
}
|
|
103
|
+
return plugins;
|
|
104
|
+
}
|
|
105
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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","sourcesContent":["import { federation, type ModuleFederationOptions } from \"@module-federation/vite\";\nimport type { Plugin, PluginOption } from \"vite\";\nimport { type CreateVettaPluginPackageOptions, createVettaPluginPackage } from \"./pack.js\";\n\nexport interface VettaPluginPackageOptions extends Omit<CreateVettaPluginPackageOptions, \"rootDir\" | \"distDir\"> {\n\tenabled?: boolean;\n}\n\nexport interface VettaPluginFederationOptions {\n\tname: string;\n\texpose?: string;\n\tentry?: string;\n\tmanifestFileName?: string;\n\tremoteEntryFileName?: string;\n\tshared?: ModuleFederationOptions[\"shared\"];\n\tpackage?: boolean | VettaPluginPackageOptions;\n}\n\nexport function createVettaPluginFederationConfig(options: VettaPluginFederationOptions): ModuleFederationOptions {\n\tconst expose = options.expose ?? \"./plugin\";\n\tconst entry = options.entry ?? \"./src/index.tsx\";\n\treturn {\n\t\tname: options.name,\n\t\tfilename: options.remoteEntryFileName ?? \"remoteEntry.js\",\n\t\texposes: {\n\t\t\t[expose]: entry,\n\t\t},\n\t\tmanifest: {\n\t\t\tfileName: options.manifestFileName ?? \"mf-manifest.json\",\n\t\t},\n\t\tdts: false,\n\t\tshared: {\n\t\t\treact: {\n\t\t\t\tsingleton: true,\n\t\t\t\timport: false,\n\t\t\t\trequiredVersion: \"*\",\n\t\t\t},\n\t\t\t\"react-dom\": {\n\t\t\t\tsingleton: true,\n\t\t\t\timport: false,\n\t\t\t\trequiredVersion: \"*\",\n\t\t\t},\n\t\t\t// Match host plugin-shared-modules (tldraw remotes may require this subpath).\n\t\t\t\"react-dom/client\": {\n\t\t\t\tsingleton: true,\n\t\t\t\timport: false,\n\t\t\t\trequiredVersion: \"*\",\n\t\t\t},\n\t\t\t...options.shared,\n\t\t},\n\t};\n}\n\nfunction createBuildDefaultsPlugin(entry: string): Plugin {\n\treturn {\n\t\tname: \"vetta-plugin-build-defaults\",\n\t\tapply: \"build\",\n\t\tconfig() {\n\t\t\treturn {\n\t\t\t\tbuild: {\n\t\t\t\t\trollupOptions: {\n\t\t\t\t\t\tinput: entry,\n\t\t\t\t\t\texternal: [\"@vetta-org/plugin-sdk\"],\n\t\t\t\t\t\toutput: {\n\t\t\t\t\t\t\tassetFileNames(assetInfo) {\n\t\t\t\t\t\t\t\treturn assetInfo.names.some((name) => name.endsWith(\".css\"))\n\t\t\t\t\t\t\t\t\t? \"style.css\"\n\t\t\t\t\t\t\t\t\t: \"assets/[name]-[hash][extname]\";\n\t\t\t\t\t\t\t},\n\t\t\t\t\t\t\tpaths: {\n\t\t\t\t\t\t\t\t\"@vetta-org/plugin-sdk\": \"vetta-host://plugin-sdk\",\n\t\t\t\t\t\t\t},\n\t\t\t\t\t\t},\n\t\t\t\t\t},\n\t\t\t\t},\n\t\t\t};\n\t\t},\n\t};\n}\n\nfunction createPackagePlugin(options: VettaPluginPackageOptions): Plugin {\n\tlet rootDir = \"\";\n\tlet distDir = \"\";\n\tlet buildFailed = false;\n\n\treturn {\n\t\tname: \"vetta-plugin-package\",\n\t\tapply: \"build\",\n\t\tbuildStart() {\n\t\t\tbuildFailed = false;\n\t\t},\n\t\tbuildEnd(error) {\n\t\t\tbuildFailed = error !== undefined;\n\t\t},\n\t\tconfigResolved(config) {\n\t\t\trootDir = config.root;\n\t\t\tdistDir = config.build.outDir;\n\t\t},\n\t\tasync closeBundle() {\n\t\t\tif (options.enabled === false || buildFailed) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tconst result = await createVettaPluginPackage({\n\t\t\t\t...options,\n\t\t\t\trootDir,\n\t\t\t\tdistDir,\n\t\t\t});\n\t\t\tconsole.log(`[vetta-plugin-vite] Wrote ${result.outputPath} with ${result.files.length} runtime files`);\n\t\t},\n\t};\n}\n\nexport function vettaPluginFederation(options: VettaPluginFederationOptions): PluginOption[] {\n\tconst packageOptions = typeof options.package === \"object\" ? options.package : {};\n\tconst entry = options.entry ?? \"./src/index.tsx\";\n\tconst plugins: PluginOption[] = [\n\t\tcreateBuildDefaultsPlugin(entry),\n\t\t...federation(createVettaPluginFederationConfig(options)),\n\t];\n\tif (options.package !== false) {\n\t\tplugins.push(createPackagePlugin(packageOptions));\n\t}\n\treturn plugins;\n}\n"]}
|
package/dist/pack.d.ts
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export interface VettaPluginPackageFile {
|
|
2
|
+
fullPath: string;
|
|
3
|
+
archivePath: string;
|
|
4
|
+
}
|
|
5
|
+
export interface VettaPluginPackageResult {
|
|
6
|
+
outputPath: string;
|
|
7
|
+
files: VettaPluginPackageFile[];
|
|
8
|
+
}
|
|
9
|
+
export interface CreateVettaPluginPackageOptions {
|
|
10
|
+
rootDir?: string;
|
|
11
|
+
manifestPath?: string;
|
|
12
|
+
releaseDir?: string;
|
|
13
|
+
distDir?: string;
|
|
14
|
+
}
|
|
15
|
+
export declare function createVettaPluginPackage(options?: CreateVettaPluginPackageOptions): Promise<VettaPluginPackageResult>;
|
|
16
|
+
//# sourceMappingURL=pack.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pack.d.ts","sourceRoot":"","sources":["../src/pack.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,sBAAsB;IACtC,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,wBAAwB;IACxC,UAAU,EAAE,MAAM,CAAC;IACnB,KAAK,EAAE,sBAAsB,EAAE,CAAC;CAChC;AAED,MAAM,WAAW,+BAA+B;IAC/C,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,OAAO,CAAC,EAAE,MAAM,CAAC;CACjB;AAgVD,wBAAsB,wBAAwB,CAC7C,OAAO,GAAE,+BAAoC,GAC3C,OAAO,CAAC,wBAAwB,CAAC,CAcnC","sourcesContent":["import { mkdir, readdir, readFile, rm, stat, writeFile } from \"node:fs/promises\";\nimport { basename, dirname, join, relative, resolve, sep } from \"node:path\";\n\nexport interface VettaPluginPackageFile {\n\tfullPath: string;\n\tarchivePath: string;\n}\n\nexport interface VettaPluginPackageResult {\n\toutputPath: string;\n\tfiles: VettaPluginPackageFile[];\n}\n\nexport interface CreateVettaPluginPackageOptions {\n\trootDir?: string;\n\tmanifestPath?: string;\n\treleaseDir?: string;\n\tdistDir?: string;\n}\n\ninterface PluginManifest {\n\tid: string;\n\tversion: string;\n\tentry: string;\n\tstyles?: string[];\n\tagent?: {\n\t\tsystemPrompt?: {\n\t\t\tpromptPaths?: string[];\n\t\t};\n\t\tskillPaths?: string[];\n\t\t/** Relative path to `.mcp.json` or present as object (inline). */\n\t\tmcpServers?: string | Record<string, unknown>;\n\t};\n}\n\nconst crcTable = new Uint32Array(256);\nfor (let i = 0; i < 256; i += 1) {\n\tlet value = i;\n\tfor (let bit = 0; bit < 8; bit += 1) {\n\t\tvalue = value & 1 ? 0xedb88320 ^ (value >>> 1) : value >>> 1;\n\t}\n\tcrcTable[i] = value >>> 0;\n}\n\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n\treturn typeof value === \"object\" && value !== null && !Array.isArray(value);\n}\n\nfunction readString(record: Record<string, unknown>, key: string): string | undefined {\n\tconst value = record[key];\n\treturn typeof value === \"string\" ? value : undefined;\n}\n\nfunction readStringArray(record: Record<string, unknown>, key: string): string[] | undefined {\n\tconst value = record[key];\n\tif (!Array.isArray(value)) {\n\t\treturn undefined;\n\t}\n\tconst strings = value.filter((entry): entry is string => typeof entry === \"string\");\n\treturn strings.length === value.length ? strings : undefined;\n}\n\nfunction readAgentManifest(record: Record<string, unknown>): PluginManifest[\"agent\"] {\n\tconst agent = record.agent;\n\tif (!isRecord(agent)) {\n\t\treturn undefined;\n\t}\n\tconst systemPrompt = isRecord(agent.systemPrompt)\n\t\t? {\n\t\t\t\tpromptPaths: readStringArray(agent.systemPrompt, \"promptPaths\"),\n\t\t\t}\n\t\t: undefined;\n\tconst mcpServersRaw = agent.mcpServers;\n\tconst mcpServers =\n\t\ttypeof mcpServersRaw === \"string\"\n\t\t\t? mcpServersRaw\n\t\t\t: isRecord(mcpServersRaw)\n\t\t\t\t? mcpServersRaw\n\t\t\t\t: undefined;\n\treturn {\n\t\tsystemPrompt,\n\t\tskillPaths: readStringArray(agent, \"skillPaths\"),\n\t\tmcpServers,\n\t};\n}\n\nfunction parsePluginManifest(value: unknown): PluginManifest {\n\tif (!isRecord(value)) {\n\t\tthrow new Error(\"plugin.json must contain an object.\");\n\t}\n\n\tconst id = readString(value, \"id\");\n\tconst version = readString(value, \"version\");\n\tconst entry = readString(value, \"entry\");\n\tif (!id || !version || !entry) {\n\t\tthrow new Error(\"plugin.json must define string id, version, and entry fields.\");\n\t}\n\n\treturn {\n\t\tid,\n\t\tversion,\n\t\tentry,\n\t\tagent: readAgentManifest(value),\n\t\tstyles: readStringArray(value, \"styles\"),\n\t};\n}\n\nfunction parseJsonObject(buffer: Buffer, fileName: string): Record<string, unknown> {\n\tconst parsed = JSON.parse(buffer.toString(\"utf-8\")) as unknown;\n\tif (!isRecord(parsed)) {\n\t\tthrow new Error(`${fileName} must contain an object.`);\n\t}\n\treturn parsed;\n}\n\nfunction crc32(buffer: Buffer): number {\n\tlet value = 0xffffffff;\n\tfor (const byte of buffer) {\n\t\tvalue = crcTable[(value ^ byte) & 0xff] ^ (value >>> 8);\n\t}\n\treturn (value ^ 0xffffffff) >>> 0;\n}\n\nfunction writeUInt16(value: number): Buffer {\n\tconst buffer = Buffer.allocUnsafe(2);\n\tbuffer.writeUInt16LE(value, 0);\n\treturn buffer;\n}\n\nfunction writeUInt32(value: number): Buffer {\n\tconst buffer = Buffer.allocUnsafe(4);\n\tbuffer.writeUInt32LE(value >>> 0, 0);\n\treturn buffer;\n}\n\nfunction archivePathFromRoot(rootDir: string, fullPath: string): string {\n\tconst archivePath = relative(rootDir, fullPath).replace(/\\\\/g, \"/\");\n\tif (!archivePath || archivePath.startsWith(\"..\") || archivePath.includes(`${sep}..${sep}`)) {\n\t\tthrow new Error(`File is outside plugin root: ${fullPath}`);\n\t}\n\treturn archivePath;\n}\n\nasync function collectFiles(dir: string): Promise<VettaPluginPackageFile[]> {\n\tconst entries = await readdir(dir, { withFileTypes: true });\n\tconst files: VettaPluginPackageFile[] = [];\n\tfor (const entry of entries) {\n\t\tconst fullPath = join(dir, entry.name);\n\t\tif (entry.isDirectory()) {\n\t\t\tfiles.push(...(await collectFiles(fullPath)));\n\t\t} else if (entry.isFile()) {\n\t\t\tfiles.push({ fullPath, archivePath: \"\" });\n\t\t}\n\t}\n\treturn files;\n}\n\nasync function collectPath(path: string): Promise<VettaPluginPackageFile[]> {\n\tconst info = await stat(path);\n\tif (info.isDirectory()) {\n\t\treturn collectFiles(path);\n\t}\n\tif (info.isFile()) {\n\t\treturn [{ fullPath: path, archivePath: \"\" }];\n\t}\n\treturn [];\n}\n\nasync function createZip(files: VettaPluginPackageFile[]): Promise<Buffer> {\n\tconst localParts: Buffer[] = [];\n\tconst centralParts: Buffer[] = [];\n\tlet offset = 0;\n\n\tfor (const file of files) {\n\t\tconst data = await readFile(file.fullPath);\n\t\tconst name = Buffer.from(file.archivePath.replace(/\\\\/g, \"/\"));\n\t\tconst checksum = crc32(data);\n\t\tconst localHeader = Buffer.concat([\n\t\t\twriteUInt32(0x04034b50),\n\t\t\twriteUInt16(20),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt32(checksum),\n\t\t\twriteUInt32(data.length),\n\t\t\twriteUInt32(data.length),\n\t\t\twriteUInt16(name.length),\n\t\t\twriteUInt16(0),\n\t\t\tname,\n\t\t]);\n\t\tlocalParts.push(localHeader, data);\n\n\t\tcentralParts.push(\n\t\t\tBuffer.concat([\n\t\t\t\twriteUInt32(0x02014b50),\n\t\t\t\twriteUInt16(20),\n\t\t\t\twriteUInt16(20),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt32(checksum),\n\t\t\t\twriteUInt32(data.length),\n\t\t\t\twriteUInt32(data.length),\n\t\t\t\twriteUInt16(name.length),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt32(0),\n\t\t\t\twriteUInt32(offset),\n\t\t\t\tname,\n\t\t\t]),\n\t\t);\n\t\toffset += localHeader.length + data.length;\n\t}\n\n\tconst centralDirectory = Buffer.concat(centralParts);\n\tconst endOfCentralDirectory = Buffer.concat([\n\t\twriteUInt32(0x06054b50),\n\t\twriteUInt16(0),\n\t\twriteUInt16(0),\n\t\twriteUInt16(files.length),\n\t\twriteUInt16(files.length),\n\t\twriteUInt32(centralDirectory.length),\n\t\twriteUInt32(offset),\n\t\twriteUInt16(0),\n\t]);\n\n\treturn Buffer.concat([...localParts, centralDirectory, endOfCentralDirectory]);\n}\n\nfunction readManifestRemoteEntry(manifest: Record<string, unknown>): string | undefined {\n\tconst metaData = manifest.metaData;\n\tif (!isRecord(metaData)) {\n\t\treturn undefined;\n\t}\n\tconst remoteEntry = metaData.remoteEntry;\n\tif (!isRecord(remoteEntry)) {\n\t\treturn undefined;\n\t}\n\tconst name = readString(remoteEntry, \"name\");\n\tif (!name) {\n\t\treturn undefined;\n\t}\n\tconst path = readString(remoteEntry, \"path\") ?? \"\";\n\treturn path ? `${path.replace(/\\/$/, \"\")}/${name}` : name;\n}\n\nasync function collectRuntimeFiles(\n\trootDir: string,\n\tmanifestPath: string,\n\tdistDir: string,\n): Promise<VettaPluginPackageFile[]> {\n\tconst pluginManifest = parsePluginManifest(parseJsonObject(await readFile(manifestPath), basename(manifestPath)));\n\tconst packageFiles = new Map<string, VettaPluginPackageFile>();\n\tconst addFile = (fullPath: string) => {\n\t\tconst resolved = resolve(fullPath);\n\t\tconst archivePath = archivePathFromRoot(rootDir, resolved);\n\t\tpackageFiles.set(archivePath, { fullPath: resolved, archivePath });\n\t};\n\n\taddFile(manifestPath);\n\n\tconst federationManifestPath = resolve(rootDir, pluginManifest.entry);\n\taddFile(federationManifestPath);\n\n\tconst federationManifest = parseJsonObject(await readFile(federationManifestPath), basename(federationManifestPath));\n\tconst remoteEntry = readManifestRemoteEntry(federationManifest);\n\tif (remoteEntry) {\n\t\taddFile(resolve(dirname(federationManifestPath), remoteEntry));\n\t}\n\n\tconst assetsDir = join(distDir, \"assets\");\n\tfor (const file of await collectFiles(assetsDir)) {\n\t\taddFile(file.fullPath);\n\t}\n\n\t// Vite cssCodeSplit emits extra files like dist/style2.css for async chunks;\n\t// include all dist-root CSS so preload-helper can fetch them (not only styles[]).\n\ttry {\n\t\tfor (const file of await collectFiles(distDir)) {\n\t\t\tconst rel = relative(distDir, file.fullPath).replace(/\\\\/g, \"/\");\n\t\t\tif (rel.endsWith(\".css\") && !rel.includes(\"/\")) {\n\t\t\t\taddFile(file.fullPath);\n\t\t\t}\n\t\t}\n\t} catch {\n\t\t// dist missing\n\t}\n\n\tfor (const style of pluginManifest.styles ?? []) {\n\t\taddFile(resolve(rootDir, style));\n\t}\n\n\tfor (const promptPath of pluginManifest.agent?.systemPrompt?.promptPaths ?? []) {\n\t\tfor (const file of await collectPath(resolve(rootDir, promptPath))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t}\n\n\tfor (const skillPath of pluginManifest.agent?.skillPaths ?? []) {\n\t\tfor (const file of await collectPath(resolve(rootDir, skillPath))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t}\n\n\t// Plugin-scoped MCP: include config file and conventional companion dirs when declared.\n\tconst mcpServers = pluginManifest.agent?.mcpServers;\n\tif (mcpServers !== undefined) {\n\t\tif (typeof mcpServers === \"string\") {\n\t\t\taddFile(resolve(rootDir, mcpServers));\n\t\t}\n\t\ttry {\n\t\t\tfor (const file of await collectFiles(resolve(rootDir, \"mcp\"))) {\n\t\t\t\taddFile(file.fullPath);\n\t\t\t}\n\t\t} catch {\n\t\t\t// optional mcp/ directory\n\t\t}\n\t}\n\n\t// Helper scripts (plugin workbench etc.): always pack scripts/ when present.\n\ttry {\n\t\tfor (const file of await collectFiles(resolve(rootDir, \"scripts\"))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t} catch {\n\t\t// optional scripts/ directory\n\t}\n\n\t// Handbook / agent docs beside skills (not always listed in skillPaths).\n\ttry {\n\t\tfor (const file of await collectFiles(resolve(rootDir, \"agent/docs\"))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t} catch {\n\t\t// optional agent/docs\n\t}\n\n\t// Plugin i18n catalogs (ADR-0033): bundle locales/<lang>.json so the host can\n\t// load them alongside the manifest. Optional — absent for single-language plugins.\n\ttry {\n\t\tfor (const file of await collectFiles(resolve(rootDir, \"locales\"))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t} catch {\n\t\t// no locales/ directory — nothing to bundle\n\t}\n\n\treturn [...packageFiles.values()].sort((a, b) => a.archivePath.localeCompare(b.archivePath));\n}\n\nexport async function createVettaPluginPackage(\n\toptions: CreateVettaPluginPackageOptions = {},\n): Promise<VettaPluginPackageResult> {\n\tconst rootDir = resolve(options.rootDir ?? process.cwd());\n\tconst manifestPath = resolve(rootDir, options.manifestPath ?? \"plugin.json\");\n\tconst releaseDir = resolve(rootDir, options.releaseDir ?? \"release\");\n\tconst distDir = resolve(rootDir, options.distDir ?? \"dist\");\n\tconst pluginManifest = parsePluginManifest(parseJsonObject(await readFile(manifestPath), basename(manifestPath)));\n\tconst outputPath = join(releaseDir, `${pluginManifest.id}-${pluginManifest.version}.zip`);\n\tconst files = await collectRuntimeFiles(rootDir, manifestPath, distDir);\n\n\tawait rm(releaseDir, { recursive: true, force: true });\n\tawait mkdir(releaseDir, { recursive: true });\n\tawait writeFile(outputPath, await createZip(files));\n\n\treturn { outputPath, files };\n}\n"]}
|
package/dist/pack.js
ADDED
|
@@ -0,0 +1,299 @@
|
|
|
1
|
+
import { mkdir, readdir, readFile, rm, stat, writeFile } from "node:fs/promises";
|
|
2
|
+
import { basename, dirname, join, relative, resolve, sep } from "node:path";
|
|
3
|
+
const crcTable = new Uint32Array(256);
|
|
4
|
+
for (let i = 0; i < 256; i += 1) {
|
|
5
|
+
let value = i;
|
|
6
|
+
for (let bit = 0; bit < 8; bit += 1) {
|
|
7
|
+
value = value & 1 ? 0xedb88320 ^ (value >>> 1) : value >>> 1;
|
|
8
|
+
}
|
|
9
|
+
crcTable[i] = value >>> 0;
|
|
10
|
+
}
|
|
11
|
+
function isRecord(value) {
|
|
12
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
13
|
+
}
|
|
14
|
+
function readString(record, key) {
|
|
15
|
+
const value = record[key];
|
|
16
|
+
return typeof value === "string" ? value : undefined;
|
|
17
|
+
}
|
|
18
|
+
function readStringArray(record, key) {
|
|
19
|
+
const value = record[key];
|
|
20
|
+
if (!Array.isArray(value)) {
|
|
21
|
+
return undefined;
|
|
22
|
+
}
|
|
23
|
+
const strings = value.filter((entry) => typeof entry === "string");
|
|
24
|
+
return strings.length === value.length ? strings : undefined;
|
|
25
|
+
}
|
|
26
|
+
function readAgentManifest(record) {
|
|
27
|
+
const agent = record.agent;
|
|
28
|
+
if (!isRecord(agent)) {
|
|
29
|
+
return undefined;
|
|
30
|
+
}
|
|
31
|
+
const systemPrompt = isRecord(agent.systemPrompt)
|
|
32
|
+
? {
|
|
33
|
+
promptPaths: readStringArray(agent.systemPrompt, "promptPaths"),
|
|
34
|
+
}
|
|
35
|
+
: undefined;
|
|
36
|
+
const mcpServersRaw = agent.mcpServers;
|
|
37
|
+
const mcpServers = typeof mcpServersRaw === "string"
|
|
38
|
+
? mcpServersRaw
|
|
39
|
+
: isRecord(mcpServersRaw)
|
|
40
|
+
? mcpServersRaw
|
|
41
|
+
: undefined;
|
|
42
|
+
return {
|
|
43
|
+
systemPrompt,
|
|
44
|
+
skillPaths: readStringArray(agent, "skillPaths"),
|
|
45
|
+
mcpServers,
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
function parsePluginManifest(value) {
|
|
49
|
+
if (!isRecord(value)) {
|
|
50
|
+
throw new Error("plugin.json must contain an object.");
|
|
51
|
+
}
|
|
52
|
+
const id = readString(value, "id");
|
|
53
|
+
const version = readString(value, "version");
|
|
54
|
+
const entry = readString(value, "entry");
|
|
55
|
+
if (!id || !version || !entry) {
|
|
56
|
+
throw new Error("plugin.json must define string id, version, and entry fields.");
|
|
57
|
+
}
|
|
58
|
+
return {
|
|
59
|
+
id,
|
|
60
|
+
version,
|
|
61
|
+
entry,
|
|
62
|
+
agent: readAgentManifest(value),
|
|
63
|
+
styles: readStringArray(value, "styles"),
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
function parseJsonObject(buffer, fileName) {
|
|
67
|
+
const parsed = JSON.parse(buffer.toString("utf-8"));
|
|
68
|
+
if (!isRecord(parsed)) {
|
|
69
|
+
throw new Error(`${fileName} must contain an object.`);
|
|
70
|
+
}
|
|
71
|
+
return parsed;
|
|
72
|
+
}
|
|
73
|
+
function crc32(buffer) {
|
|
74
|
+
let value = 0xffffffff;
|
|
75
|
+
for (const byte of buffer) {
|
|
76
|
+
value = crcTable[(value ^ byte) & 0xff] ^ (value >>> 8);
|
|
77
|
+
}
|
|
78
|
+
return (value ^ 0xffffffff) >>> 0;
|
|
79
|
+
}
|
|
80
|
+
function writeUInt16(value) {
|
|
81
|
+
const buffer = Buffer.allocUnsafe(2);
|
|
82
|
+
buffer.writeUInt16LE(value, 0);
|
|
83
|
+
return buffer;
|
|
84
|
+
}
|
|
85
|
+
function writeUInt32(value) {
|
|
86
|
+
const buffer = Buffer.allocUnsafe(4);
|
|
87
|
+
buffer.writeUInt32LE(value >>> 0, 0);
|
|
88
|
+
return buffer;
|
|
89
|
+
}
|
|
90
|
+
function archivePathFromRoot(rootDir, fullPath) {
|
|
91
|
+
const archivePath = relative(rootDir, fullPath).replace(/\\/g, "/");
|
|
92
|
+
if (!archivePath || archivePath.startsWith("..") || archivePath.includes(`${sep}..${sep}`)) {
|
|
93
|
+
throw new Error(`File is outside plugin root: ${fullPath}`);
|
|
94
|
+
}
|
|
95
|
+
return archivePath;
|
|
96
|
+
}
|
|
97
|
+
async function collectFiles(dir) {
|
|
98
|
+
const entries = await readdir(dir, { withFileTypes: true });
|
|
99
|
+
const files = [];
|
|
100
|
+
for (const entry of entries) {
|
|
101
|
+
const fullPath = join(dir, entry.name);
|
|
102
|
+
if (entry.isDirectory()) {
|
|
103
|
+
files.push(...(await collectFiles(fullPath)));
|
|
104
|
+
}
|
|
105
|
+
else if (entry.isFile()) {
|
|
106
|
+
files.push({ fullPath, archivePath: "" });
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
return files;
|
|
110
|
+
}
|
|
111
|
+
async function collectPath(path) {
|
|
112
|
+
const info = await stat(path);
|
|
113
|
+
if (info.isDirectory()) {
|
|
114
|
+
return collectFiles(path);
|
|
115
|
+
}
|
|
116
|
+
if (info.isFile()) {
|
|
117
|
+
return [{ fullPath: path, archivePath: "" }];
|
|
118
|
+
}
|
|
119
|
+
return [];
|
|
120
|
+
}
|
|
121
|
+
async function createZip(files) {
|
|
122
|
+
const localParts = [];
|
|
123
|
+
const centralParts = [];
|
|
124
|
+
let offset = 0;
|
|
125
|
+
for (const file of files) {
|
|
126
|
+
const data = await readFile(file.fullPath);
|
|
127
|
+
const name = Buffer.from(file.archivePath.replace(/\\/g, "/"));
|
|
128
|
+
const checksum = crc32(data);
|
|
129
|
+
const localHeader = Buffer.concat([
|
|
130
|
+
writeUInt32(0x04034b50),
|
|
131
|
+
writeUInt16(20),
|
|
132
|
+
writeUInt16(0),
|
|
133
|
+
writeUInt16(0),
|
|
134
|
+
writeUInt16(0),
|
|
135
|
+
writeUInt16(0),
|
|
136
|
+
writeUInt32(checksum),
|
|
137
|
+
writeUInt32(data.length),
|
|
138
|
+
writeUInt32(data.length),
|
|
139
|
+
writeUInt16(name.length),
|
|
140
|
+
writeUInt16(0),
|
|
141
|
+
name,
|
|
142
|
+
]);
|
|
143
|
+
localParts.push(localHeader, data);
|
|
144
|
+
centralParts.push(Buffer.concat([
|
|
145
|
+
writeUInt32(0x02014b50),
|
|
146
|
+
writeUInt16(20),
|
|
147
|
+
writeUInt16(20),
|
|
148
|
+
writeUInt16(0),
|
|
149
|
+
writeUInt16(0),
|
|
150
|
+
writeUInt16(0),
|
|
151
|
+
writeUInt16(0),
|
|
152
|
+
writeUInt32(checksum),
|
|
153
|
+
writeUInt32(data.length),
|
|
154
|
+
writeUInt32(data.length),
|
|
155
|
+
writeUInt16(name.length),
|
|
156
|
+
writeUInt16(0),
|
|
157
|
+
writeUInt16(0),
|
|
158
|
+
writeUInt16(0),
|
|
159
|
+
writeUInt16(0),
|
|
160
|
+
writeUInt32(0),
|
|
161
|
+
writeUInt32(offset),
|
|
162
|
+
name,
|
|
163
|
+
]));
|
|
164
|
+
offset += localHeader.length + data.length;
|
|
165
|
+
}
|
|
166
|
+
const centralDirectory = Buffer.concat(centralParts);
|
|
167
|
+
const endOfCentralDirectory = Buffer.concat([
|
|
168
|
+
writeUInt32(0x06054b50),
|
|
169
|
+
writeUInt16(0),
|
|
170
|
+
writeUInt16(0),
|
|
171
|
+
writeUInt16(files.length),
|
|
172
|
+
writeUInt16(files.length),
|
|
173
|
+
writeUInt32(centralDirectory.length),
|
|
174
|
+
writeUInt32(offset),
|
|
175
|
+
writeUInt16(0),
|
|
176
|
+
]);
|
|
177
|
+
return Buffer.concat([...localParts, centralDirectory, endOfCentralDirectory]);
|
|
178
|
+
}
|
|
179
|
+
function readManifestRemoteEntry(manifest) {
|
|
180
|
+
const metaData = manifest.metaData;
|
|
181
|
+
if (!isRecord(metaData)) {
|
|
182
|
+
return undefined;
|
|
183
|
+
}
|
|
184
|
+
const remoteEntry = metaData.remoteEntry;
|
|
185
|
+
if (!isRecord(remoteEntry)) {
|
|
186
|
+
return undefined;
|
|
187
|
+
}
|
|
188
|
+
const name = readString(remoteEntry, "name");
|
|
189
|
+
if (!name) {
|
|
190
|
+
return undefined;
|
|
191
|
+
}
|
|
192
|
+
const path = readString(remoteEntry, "path") ?? "";
|
|
193
|
+
return path ? `${path.replace(/\/$/, "")}/${name}` : name;
|
|
194
|
+
}
|
|
195
|
+
async function collectRuntimeFiles(rootDir, manifestPath, distDir) {
|
|
196
|
+
const pluginManifest = parsePluginManifest(parseJsonObject(await readFile(manifestPath), basename(manifestPath)));
|
|
197
|
+
const packageFiles = new Map();
|
|
198
|
+
const addFile = (fullPath) => {
|
|
199
|
+
const resolved = resolve(fullPath);
|
|
200
|
+
const archivePath = archivePathFromRoot(rootDir, resolved);
|
|
201
|
+
packageFiles.set(archivePath, { fullPath: resolved, archivePath });
|
|
202
|
+
};
|
|
203
|
+
addFile(manifestPath);
|
|
204
|
+
const federationManifestPath = resolve(rootDir, pluginManifest.entry);
|
|
205
|
+
addFile(federationManifestPath);
|
|
206
|
+
const federationManifest = parseJsonObject(await readFile(federationManifestPath), basename(federationManifestPath));
|
|
207
|
+
const remoteEntry = readManifestRemoteEntry(federationManifest);
|
|
208
|
+
if (remoteEntry) {
|
|
209
|
+
addFile(resolve(dirname(federationManifestPath), remoteEntry));
|
|
210
|
+
}
|
|
211
|
+
const assetsDir = join(distDir, "assets");
|
|
212
|
+
for (const file of await collectFiles(assetsDir)) {
|
|
213
|
+
addFile(file.fullPath);
|
|
214
|
+
}
|
|
215
|
+
// Vite cssCodeSplit emits extra files like dist/style2.css for async chunks;
|
|
216
|
+
// include all dist-root CSS so preload-helper can fetch them (not only styles[]).
|
|
217
|
+
try {
|
|
218
|
+
for (const file of await collectFiles(distDir)) {
|
|
219
|
+
const rel = relative(distDir, file.fullPath).replace(/\\/g, "/");
|
|
220
|
+
if (rel.endsWith(".css") && !rel.includes("/")) {
|
|
221
|
+
addFile(file.fullPath);
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
catch {
|
|
226
|
+
// dist missing
|
|
227
|
+
}
|
|
228
|
+
for (const style of pluginManifest.styles ?? []) {
|
|
229
|
+
addFile(resolve(rootDir, style));
|
|
230
|
+
}
|
|
231
|
+
for (const promptPath of pluginManifest.agent?.systemPrompt?.promptPaths ?? []) {
|
|
232
|
+
for (const file of await collectPath(resolve(rootDir, promptPath))) {
|
|
233
|
+
addFile(file.fullPath);
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
for (const skillPath of pluginManifest.agent?.skillPaths ?? []) {
|
|
237
|
+
for (const file of await collectPath(resolve(rootDir, skillPath))) {
|
|
238
|
+
addFile(file.fullPath);
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
// Plugin-scoped MCP: include config file and conventional companion dirs when declared.
|
|
242
|
+
const mcpServers = pluginManifest.agent?.mcpServers;
|
|
243
|
+
if (mcpServers !== undefined) {
|
|
244
|
+
if (typeof mcpServers === "string") {
|
|
245
|
+
addFile(resolve(rootDir, mcpServers));
|
|
246
|
+
}
|
|
247
|
+
try {
|
|
248
|
+
for (const file of await collectFiles(resolve(rootDir, "mcp"))) {
|
|
249
|
+
addFile(file.fullPath);
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
catch {
|
|
253
|
+
// optional mcp/ directory
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
// Helper scripts (plugin workbench etc.): always pack scripts/ when present.
|
|
257
|
+
try {
|
|
258
|
+
for (const file of await collectFiles(resolve(rootDir, "scripts"))) {
|
|
259
|
+
addFile(file.fullPath);
|
|
260
|
+
}
|
|
261
|
+
}
|
|
262
|
+
catch {
|
|
263
|
+
// optional scripts/ directory
|
|
264
|
+
}
|
|
265
|
+
// Handbook / agent docs beside skills (not always listed in skillPaths).
|
|
266
|
+
try {
|
|
267
|
+
for (const file of await collectFiles(resolve(rootDir, "agent/docs"))) {
|
|
268
|
+
addFile(file.fullPath);
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
catch {
|
|
272
|
+
// optional agent/docs
|
|
273
|
+
}
|
|
274
|
+
// Plugin i18n catalogs (ADR-0033): bundle locales/<lang>.json so the host can
|
|
275
|
+
// load them alongside the manifest. Optional — absent for single-language plugins.
|
|
276
|
+
try {
|
|
277
|
+
for (const file of await collectFiles(resolve(rootDir, "locales"))) {
|
|
278
|
+
addFile(file.fullPath);
|
|
279
|
+
}
|
|
280
|
+
}
|
|
281
|
+
catch {
|
|
282
|
+
// no locales/ directory — nothing to bundle
|
|
283
|
+
}
|
|
284
|
+
return [...packageFiles.values()].sort((a, b) => a.archivePath.localeCompare(b.archivePath));
|
|
285
|
+
}
|
|
286
|
+
export async function createVettaPluginPackage(options = {}) {
|
|
287
|
+
const rootDir = resolve(options.rootDir ?? process.cwd());
|
|
288
|
+
const manifestPath = resolve(rootDir, options.manifestPath ?? "plugin.json");
|
|
289
|
+
const releaseDir = resolve(rootDir, options.releaseDir ?? "release");
|
|
290
|
+
const distDir = resolve(rootDir, options.distDir ?? "dist");
|
|
291
|
+
const pluginManifest = parsePluginManifest(parseJsonObject(await readFile(manifestPath), basename(manifestPath)));
|
|
292
|
+
const outputPath = join(releaseDir, `${pluginManifest.id}-${pluginManifest.version}.zip`);
|
|
293
|
+
const files = await collectRuntimeFiles(rootDir, manifestPath, distDir);
|
|
294
|
+
await rm(releaseDir, { recursive: true, force: true });
|
|
295
|
+
await mkdir(releaseDir, { recursive: true });
|
|
296
|
+
await writeFile(outputPath, await createZip(files));
|
|
297
|
+
return { outputPath, files };
|
|
298
|
+
}
|
|
299
|
+
//# sourceMappingURL=pack.js.map
|
package/dist/pack.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pack.js","sourceRoot":"","sources":["../src/pack.ts"],"names":[],"mappings":"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","sourcesContent":["import { mkdir, readdir, readFile, rm, stat, writeFile } from \"node:fs/promises\";\nimport { basename, dirname, join, relative, resolve, sep } from \"node:path\";\n\nexport interface VettaPluginPackageFile {\n\tfullPath: string;\n\tarchivePath: string;\n}\n\nexport interface VettaPluginPackageResult {\n\toutputPath: string;\n\tfiles: VettaPluginPackageFile[];\n}\n\nexport interface CreateVettaPluginPackageOptions {\n\trootDir?: string;\n\tmanifestPath?: string;\n\treleaseDir?: string;\n\tdistDir?: string;\n}\n\ninterface PluginManifest {\n\tid: string;\n\tversion: string;\n\tentry: string;\n\tstyles?: string[];\n\tagent?: {\n\t\tsystemPrompt?: {\n\t\t\tpromptPaths?: string[];\n\t\t};\n\t\tskillPaths?: string[];\n\t\t/** Relative path to `.mcp.json` or present as object (inline). */\n\t\tmcpServers?: string | Record<string, unknown>;\n\t};\n}\n\nconst crcTable = new Uint32Array(256);\nfor (let i = 0; i < 256; i += 1) {\n\tlet value = i;\n\tfor (let bit = 0; bit < 8; bit += 1) {\n\t\tvalue = value & 1 ? 0xedb88320 ^ (value >>> 1) : value >>> 1;\n\t}\n\tcrcTable[i] = value >>> 0;\n}\n\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n\treturn typeof value === \"object\" && value !== null && !Array.isArray(value);\n}\n\nfunction readString(record: Record<string, unknown>, key: string): string | undefined {\n\tconst value = record[key];\n\treturn typeof value === \"string\" ? value : undefined;\n}\n\nfunction readStringArray(record: Record<string, unknown>, key: string): string[] | undefined {\n\tconst value = record[key];\n\tif (!Array.isArray(value)) {\n\t\treturn undefined;\n\t}\n\tconst strings = value.filter((entry): entry is string => typeof entry === \"string\");\n\treturn strings.length === value.length ? strings : undefined;\n}\n\nfunction readAgentManifest(record: Record<string, unknown>): PluginManifest[\"agent\"] {\n\tconst agent = record.agent;\n\tif (!isRecord(agent)) {\n\t\treturn undefined;\n\t}\n\tconst systemPrompt = isRecord(agent.systemPrompt)\n\t\t? {\n\t\t\t\tpromptPaths: readStringArray(agent.systemPrompt, \"promptPaths\"),\n\t\t\t}\n\t\t: undefined;\n\tconst mcpServersRaw = agent.mcpServers;\n\tconst mcpServers =\n\t\ttypeof mcpServersRaw === \"string\"\n\t\t\t? mcpServersRaw\n\t\t\t: isRecord(mcpServersRaw)\n\t\t\t\t? mcpServersRaw\n\t\t\t\t: undefined;\n\treturn {\n\t\tsystemPrompt,\n\t\tskillPaths: readStringArray(agent, \"skillPaths\"),\n\t\tmcpServers,\n\t};\n}\n\nfunction parsePluginManifest(value: unknown): PluginManifest {\n\tif (!isRecord(value)) {\n\t\tthrow new Error(\"plugin.json must contain an object.\");\n\t}\n\n\tconst id = readString(value, \"id\");\n\tconst version = readString(value, \"version\");\n\tconst entry = readString(value, \"entry\");\n\tif (!id || !version || !entry) {\n\t\tthrow new Error(\"plugin.json must define string id, version, and entry fields.\");\n\t}\n\n\treturn {\n\t\tid,\n\t\tversion,\n\t\tentry,\n\t\tagent: readAgentManifest(value),\n\t\tstyles: readStringArray(value, \"styles\"),\n\t};\n}\n\nfunction parseJsonObject(buffer: Buffer, fileName: string): Record<string, unknown> {\n\tconst parsed = JSON.parse(buffer.toString(\"utf-8\")) as unknown;\n\tif (!isRecord(parsed)) {\n\t\tthrow new Error(`${fileName} must contain an object.`);\n\t}\n\treturn parsed;\n}\n\nfunction crc32(buffer: Buffer): number {\n\tlet value = 0xffffffff;\n\tfor (const byte of buffer) {\n\t\tvalue = crcTable[(value ^ byte) & 0xff] ^ (value >>> 8);\n\t}\n\treturn (value ^ 0xffffffff) >>> 0;\n}\n\nfunction writeUInt16(value: number): Buffer {\n\tconst buffer = Buffer.allocUnsafe(2);\n\tbuffer.writeUInt16LE(value, 0);\n\treturn buffer;\n}\n\nfunction writeUInt32(value: number): Buffer {\n\tconst buffer = Buffer.allocUnsafe(4);\n\tbuffer.writeUInt32LE(value >>> 0, 0);\n\treturn buffer;\n}\n\nfunction archivePathFromRoot(rootDir: string, fullPath: string): string {\n\tconst archivePath = relative(rootDir, fullPath).replace(/\\\\/g, \"/\");\n\tif (!archivePath || archivePath.startsWith(\"..\") || archivePath.includes(`${sep}..${sep}`)) {\n\t\tthrow new Error(`File is outside plugin root: ${fullPath}`);\n\t}\n\treturn archivePath;\n}\n\nasync function collectFiles(dir: string): Promise<VettaPluginPackageFile[]> {\n\tconst entries = await readdir(dir, { withFileTypes: true });\n\tconst files: VettaPluginPackageFile[] = [];\n\tfor (const entry of entries) {\n\t\tconst fullPath = join(dir, entry.name);\n\t\tif (entry.isDirectory()) {\n\t\t\tfiles.push(...(await collectFiles(fullPath)));\n\t\t} else if (entry.isFile()) {\n\t\t\tfiles.push({ fullPath, archivePath: \"\" });\n\t\t}\n\t}\n\treturn files;\n}\n\nasync function collectPath(path: string): Promise<VettaPluginPackageFile[]> {\n\tconst info = await stat(path);\n\tif (info.isDirectory()) {\n\t\treturn collectFiles(path);\n\t}\n\tif (info.isFile()) {\n\t\treturn [{ fullPath: path, archivePath: \"\" }];\n\t}\n\treturn [];\n}\n\nasync function createZip(files: VettaPluginPackageFile[]): Promise<Buffer> {\n\tconst localParts: Buffer[] = [];\n\tconst centralParts: Buffer[] = [];\n\tlet offset = 0;\n\n\tfor (const file of files) {\n\t\tconst data = await readFile(file.fullPath);\n\t\tconst name = Buffer.from(file.archivePath.replace(/\\\\/g, \"/\"));\n\t\tconst checksum = crc32(data);\n\t\tconst localHeader = Buffer.concat([\n\t\t\twriteUInt32(0x04034b50),\n\t\t\twriteUInt16(20),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt16(0),\n\t\t\twriteUInt32(checksum),\n\t\t\twriteUInt32(data.length),\n\t\t\twriteUInt32(data.length),\n\t\t\twriteUInt16(name.length),\n\t\t\twriteUInt16(0),\n\t\t\tname,\n\t\t]);\n\t\tlocalParts.push(localHeader, data);\n\n\t\tcentralParts.push(\n\t\t\tBuffer.concat([\n\t\t\t\twriteUInt32(0x02014b50),\n\t\t\t\twriteUInt16(20),\n\t\t\t\twriteUInt16(20),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt32(checksum),\n\t\t\t\twriteUInt32(data.length),\n\t\t\t\twriteUInt32(data.length),\n\t\t\t\twriteUInt16(name.length),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt16(0),\n\t\t\t\twriteUInt32(0),\n\t\t\t\twriteUInt32(offset),\n\t\t\t\tname,\n\t\t\t]),\n\t\t);\n\t\toffset += localHeader.length + data.length;\n\t}\n\n\tconst centralDirectory = Buffer.concat(centralParts);\n\tconst endOfCentralDirectory = Buffer.concat([\n\t\twriteUInt32(0x06054b50),\n\t\twriteUInt16(0),\n\t\twriteUInt16(0),\n\t\twriteUInt16(files.length),\n\t\twriteUInt16(files.length),\n\t\twriteUInt32(centralDirectory.length),\n\t\twriteUInt32(offset),\n\t\twriteUInt16(0),\n\t]);\n\n\treturn Buffer.concat([...localParts, centralDirectory, endOfCentralDirectory]);\n}\n\nfunction readManifestRemoteEntry(manifest: Record<string, unknown>): string | undefined {\n\tconst metaData = manifest.metaData;\n\tif (!isRecord(metaData)) {\n\t\treturn undefined;\n\t}\n\tconst remoteEntry = metaData.remoteEntry;\n\tif (!isRecord(remoteEntry)) {\n\t\treturn undefined;\n\t}\n\tconst name = readString(remoteEntry, \"name\");\n\tif (!name) {\n\t\treturn undefined;\n\t}\n\tconst path = readString(remoteEntry, \"path\") ?? \"\";\n\treturn path ? `${path.replace(/\\/$/, \"\")}/${name}` : name;\n}\n\nasync function collectRuntimeFiles(\n\trootDir: string,\n\tmanifestPath: string,\n\tdistDir: string,\n): Promise<VettaPluginPackageFile[]> {\n\tconst pluginManifest = parsePluginManifest(parseJsonObject(await readFile(manifestPath), basename(manifestPath)));\n\tconst packageFiles = new Map<string, VettaPluginPackageFile>();\n\tconst addFile = (fullPath: string) => {\n\t\tconst resolved = resolve(fullPath);\n\t\tconst archivePath = archivePathFromRoot(rootDir, resolved);\n\t\tpackageFiles.set(archivePath, { fullPath: resolved, archivePath });\n\t};\n\n\taddFile(manifestPath);\n\n\tconst federationManifestPath = resolve(rootDir, pluginManifest.entry);\n\taddFile(federationManifestPath);\n\n\tconst federationManifest = parseJsonObject(await readFile(federationManifestPath), basename(federationManifestPath));\n\tconst remoteEntry = readManifestRemoteEntry(federationManifest);\n\tif (remoteEntry) {\n\t\taddFile(resolve(dirname(federationManifestPath), remoteEntry));\n\t}\n\n\tconst assetsDir = join(distDir, \"assets\");\n\tfor (const file of await collectFiles(assetsDir)) {\n\t\taddFile(file.fullPath);\n\t}\n\n\t// Vite cssCodeSplit emits extra files like dist/style2.css for async chunks;\n\t// include all dist-root CSS so preload-helper can fetch them (not only styles[]).\n\ttry {\n\t\tfor (const file of await collectFiles(distDir)) {\n\t\t\tconst rel = relative(distDir, file.fullPath).replace(/\\\\/g, \"/\");\n\t\t\tif (rel.endsWith(\".css\") && !rel.includes(\"/\")) {\n\t\t\t\taddFile(file.fullPath);\n\t\t\t}\n\t\t}\n\t} catch {\n\t\t// dist missing\n\t}\n\n\tfor (const style of pluginManifest.styles ?? []) {\n\t\taddFile(resolve(rootDir, style));\n\t}\n\n\tfor (const promptPath of pluginManifest.agent?.systemPrompt?.promptPaths ?? []) {\n\t\tfor (const file of await collectPath(resolve(rootDir, promptPath))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t}\n\n\tfor (const skillPath of pluginManifest.agent?.skillPaths ?? []) {\n\t\tfor (const file of await collectPath(resolve(rootDir, skillPath))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t}\n\n\t// Plugin-scoped MCP: include config file and conventional companion dirs when declared.\n\tconst mcpServers = pluginManifest.agent?.mcpServers;\n\tif (mcpServers !== undefined) {\n\t\tif (typeof mcpServers === \"string\") {\n\t\t\taddFile(resolve(rootDir, mcpServers));\n\t\t}\n\t\ttry {\n\t\t\tfor (const file of await collectFiles(resolve(rootDir, \"mcp\"))) {\n\t\t\t\taddFile(file.fullPath);\n\t\t\t}\n\t\t} catch {\n\t\t\t// optional mcp/ directory\n\t\t}\n\t}\n\n\t// Helper scripts (plugin workbench etc.): always pack scripts/ when present.\n\ttry {\n\t\tfor (const file of await collectFiles(resolve(rootDir, \"scripts\"))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t} catch {\n\t\t// optional scripts/ directory\n\t}\n\n\t// Handbook / agent docs beside skills (not always listed in skillPaths).\n\ttry {\n\t\tfor (const file of await collectFiles(resolve(rootDir, \"agent/docs\"))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t} catch {\n\t\t// optional agent/docs\n\t}\n\n\t// Plugin i18n catalogs (ADR-0033): bundle locales/<lang>.json so the host can\n\t// load them alongside the manifest. Optional — absent for single-language plugins.\n\ttry {\n\t\tfor (const file of await collectFiles(resolve(rootDir, \"locales\"))) {\n\t\t\taddFile(file.fullPath);\n\t\t}\n\t} catch {\n\t\t// no locales/ directory — nothing to bundle\n\t}\n\n\treturn [...packageFiles.values()].sort((a, b) => a.archivePath.localeCompare(b.archivePath));\n}\n\nexport async function createVettaPluginPackage(\n\toptions: CreateVettaPluginPackageOptions = {},\n): Promise<VettaPluginPackageResult> {\n\tconst rootDir = resolve(options.rootDir ?? process.cwd());\n\tconst manifestPath = resolve(rootDir, options.manifestPath ?? \"plugin.json\");\n\tconst releaseDir = resolve(rootDir, options.releaseDir ?? \"release\");\n\tconst distDir = resolve(rootDir, options.distDir ?? \"dist\");\n\tconst pluginManifest = parsePluginManifest(parseJsonObject(await readFile(manifestPath), basename(manifestPath)));\n\tconst outputPath = join(releaseDir, `${pluginManifest.id}-${pluginManifest.version}.zip`);\n\tconst files = await collectRuntimeFiles(rootDir, manifestPath, distDir);\n\n\tawait rm(releaseDir, { recursive: true, force: true });\n\tawait mkdir(releaseDir, { recursive: true });\n\tawait writeFile(outputPath, await createZip(files));\n\n\treturn { outputPath, files };\n}\n"]}
|
package/package.json
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@vetta-org/plugin-vite",
|
|
3
|
+
"version": "0.0.1",
|
|
4
|
+
"type": "module",
|
|
5
|
+
"main": "./dist/index.js",
|
|
6
|
+
"types": "./dist/index.d.ts",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": {
|
|
9
|
+
"types": "./dist/index.d.ts",
|
|
10
|
+
"import": "./dist/index.js"
|
|
11
|
+
},
|
|
12
|
+
"./pack": {
|
|
13
|
+
"types": "./dist/pack.d.ts",
|
|
14
|
+
"import": "./dist/pack.js"
|
|
15
|
+
}
|
|
16
|
+
},
|
|
17
|
+
"files": [
|
|
18
|
+
"dist"
|
|
19
|
+
],
|
|
20
|
+
"scripts": {
|
|
21
|
+
"clean": "rm -rf dist",
|
|
22
|
+
"build": "tsgo -p tsconfig.build.json"
|
|
23
|
+
},
|
|
24
|
+
"dependencies": {
|
|
25
|
+
"@module-federation/vite": "^1.16.6"
|
|
26
|
+
},
|
|
27
|
+
"peerDependencies": {
|
|
28
|
+
"vite": "^7.0.0"
|
|
29
|
+
},
|
|
30
|
+
"devDependencies": {
|
|
31
|
+
"typescript": "^5.9.2",
|
|
32
|
+
"vite": "^7.1.7"
|
|
33
|
+
},
|
|
34
|
+
"publishConfig": {
|
|
35
|
+
"access": "public",
|
|
36
|
+
"registry": "https://registry.npmjs.org/"
|
|
37
|
+
}
|
|
38
|
+
}
|