@weapp-vite/mcp 1.1.0 → 1.1.2
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/README.md +17 -1
- package/dist/index.d.mts +31 -6
- package/dist/index.d.ts +31 -6
- package/dist/index.mjs +270 -31
- package/package.json +3 -2
package/README.md
CHANGED
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
- 文档/变更记录资源暴露
|
|
12
12
|
- 调试/改造提示词模板
|
|
13
13
|
|
|
14
|
-
默认通过 `stdio` 运行,适合接入任意 MCP Client
|
|
14
|
+
默认通过 `stdio` 运行,适合接入任意 MCP Client,也支持 `streamable-http`。
|
|
15
15
|
|
|
16
16
|
## 启动
|
|
17
17
|
|
|
@@ -19,6 +19,22 @@
|
|
|
19
19
|
pnpm --filter @weapp-vite/mcp start
|
|
20
20
|
```
|
|
21
21
|
|
|
22
|
+
也可以在 Node 脚本里直接调用:
|
|
23
|
+
|
|
24
|
+
```ts
|
|
25
|
+
import { startWeappViteMcpServer } from '@weapp-vite/mcp'
|
|
26
|
+
|
|
27
|
+
const handle = await startWeappViteMcpServer({
|
|
28
|
+
workspaceRoot: process.cwd(),
|
|
29
|
+
transport: 'streamable-http',
|
|
30
|
+
host: '127.0.0.1',
|
|
31
|
+
port: 3088,
|
|
32
|
+
endpoint: '/mcp',
|
|
33
|
+
})
|
|
34
|
+
|
|
35
|
+
await handle.close?.()
|
|
36
|
+
```
|
|
37
|
+
|
|
22
38
|
## 主要 Tools
|
|
23
39
|
|
|
24
40
|
- `workspace_catalog`: 输出 `weapp-vite / wevu / wevu-compiler` 目录、版本、脚本
|
package/dist/index.d.mts
CHANGED
|
@@ -6,16 +6,19 @@ declare const EXPOSED_PACKAGES: {
|
|
|
6
6
|
readonly 'weapp-vite': {
|
|
7
7
|
readonly id: "weapp-vite";
|
|
8
8
|
readonly label: "weapp-vite";
|
|
9
|
+
readonly packageName: "weapp-vite";
|
|
9
10
|
readonly relativePath: string;
|
|
10
11
|
};
|
|
11
12
|
readonly wevu: {
|
|
12
13
|
readonly id: "wevu";
|
|
13
14
|
readonly label: "wevu";
|
|
15
|
+
readonly packageName: "wevu";
|
|
14
16
|
readonly relativePath: string;
|
|
15
17
|
};
|
|
16
18
|
readonly 'wevu-compiler': {
|
|
17
19
|
readonly id: "wevu-compiler";
|
|
18
20
|
readonly label: "wevu-compiler";
|
|
21
|
+
readonly packageName: "@wevu/compiler";
|
|
19
22
|
readonly relativePath: string;
|
|
20
23
|
};
|
|
21
24
|
};
|
|
@@ -26,7 +29,7 @@ declare const DEFAULT_MAX_FILE_CHARS = 80000;
|
|
|
26
29
|
declare const DEFAULT_MAX_RESULTS = 200;
|
|
27
30
|
declare const SKIPPED_DIR_NAMES: Set<string>;
|
|
28
31
|
|
|
29
|
-
interface
|
|
32
|
+
interface ResolvedExposedPackage {
|
|
30
33
|
id: ExposedPackageId;
|
|
31
34
|
label: string;
|
|
32
35
|
packageName: string;
|
|
@@ -38,9 +41,14 @@ interface ExposedPackageSummary {
|
|
|
38
41
|
readme?: string;
|
|
39
42
|
changelog?: string;
|
|
40
43
|
};
|
|
44
|
+
sourceRoot?: string;
|
|
45
|
+
cliPath?: string;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
interface ExposedPackageSummary extends ResolvedExposedPackage {
|
|
41
49
|
}
|
|
42
50
|
declare function loadPackageSummary(workspaceRoot: string, id: ExposedPackageId): Promise<ExposedPackageSummary>;
|
|
43
|
-
declare function loadExposedCatalog(workspaceRoot: string): Promise<
|
|
51
|
+
declare function loadExposedCatalog(workspaceRoot: string): Promise<ResolvedExposedPackage[]>;
|
|
44
52
|
|
|
45
53
|
interface CommandResult {
|
|
46
54
|
command: string;
|
|
@@ -85,6 +93,25 @@ declare function createWeappViteMcpServer(options?: CreateServerOptions): Promis
|
|
|
85
93
|
workspaceRoot: string;
|
|
86
94
|
}>;
|
|
87
95
|
|
|
96
|
+
declare const DEFAULT_MCP_HOST = "127.0.0.1";
|
|
97
|
+
declare const DEFAULT_MCP_PORT = 3088;
|
|
98
|
+
declare const DEFAULT_MCP_ENDPOINT = "/mcp";
|
|
99
|
+
interface StartMcpServerOptions extends CreateServerOptions {
|
|
100
|
+
transport?: 'stdio' | 'streamable-http';
|
|
101
|
+
host?: string;
|
|
102
|
+
port?: number;
|
|
103
|
+
endpoint?: string;
|
|
104
|
+
unref?: boolean;
|
|
105
|
+
quiet?: boolean;
|
|
106
|
+
onReady?: (message: string) => void;
|
|
107
|
+
}
|
|
108
|
+
interface McpServerHandle {
|
|
109
|
+
transport: 'stdio' | 'streamable-http';
|
|
110
|
+
close?: () => Promise<void>;
|
|
111
|
+
}
|
|
112
|
+
declare function startStdioServer(options?: CreateServerOptions): Promise<void>;
|
|
113
|
+
declare function startWeappViteMcpServer(options?: StartMcpServerOptions): Promise<McpServerHandle>;
|
|
114
|
+
|
|
88
115
|
declare function formatJson(value: unknown): string;
|
|
89
116
|
declare function normalizeErrorMessage(error: unknown): string;
|
|
90
117
|
declare function toToolResult(data: unknown, text?: string): {
|
|
@@ -108,7 +135,5 @@ declare function resolveWorkspaceRoot(start?: string): string;
|
|
|
108
135
|
declare function assertInsideRoot(root: string, targetPath: string): string;
|
|
109
136
|
declare function resolveSubPath(root: string, relativePath: string): string;
|
|
110
137
|
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
export { DEFAULT_MAX_FILE_CHARS, DEFAULT_MAX_OUTPUT_CHARS, DEFAULT_MAX_RESULTS, DEFAULT_TIMEOUT_MS, EXPOSED_PACKAGES, MCP_SERVER_NAME, MCP_SERVER_VERSION, SKIPPED_DIR_NAMES, assertInsideRoot, createWeappViteMcpServer, formatJson, listFilesInDirectory, loadExposedCatalog, loadPackageSummary, normalizeErrorMessage, readFileContent, resolveSubPath, resolveWorkspaceRoot, runCommand, searchTextInDirectory, startStdioServer, toToolError, toToolResult };
|
|
114
|
-
export type { CommandResult, CreateServerOptions, ExposedPackageId, ExposedPackageSummary, SearchMatch };
|
|
138
|
+
export { DEFAULT_MAX_FILE_CHARS, DEFAULT_MAX_OUTPUT_CHARS, DEFAULT_MAX_RESULTS, DEFAULT_MCP_ENDPOINT, DEFAULT_MCP_HOST, DEFAULT_MCP_PORT, DEFAULT_TIMEOUT_MS, EXPOSED_PACKAGES, MCP_SERVER_NAME, MCP_SERVER_VERSION, SKIPPED_DIR_NAMES, assertInsideRoot, createWeappViteMcpServer, formatJson, listFilesInDirectory, loadExposedCatalog, loadPackageSummary, normalizeErrorMessage, readFileContent, resolveSubPath, resolveWorkspaceRoot, runCommand, searchTextInDirectory, startStdioServer, startWeappViteMcpServer, toToolError, toToolResult };
|
|
139
|
+
export type { CommandResult, CreateServerOptions, ExposedPackageId, ExposedPackageSummary, McpServerHandle, SearchMatch, StartMcpServerOptions };
|
package/dist/index.d.ts
CHANGED
|
@@ -6,16 +6,19 @@ declare const EXPOSED_PACKAGES: {
|
|
|
6
6
|
readonly 'weapp-vite': {
|
|
7
7
|
readonly id: "weapp-vite";
|
|
8
8
|
readonly label: "weapp-vite";
|
|
9
|
+
readonly packageName: "weapp-vite";
|
|
9
10
|
readonly relativePath: string;
|
|
10
11
|
};
|
|
11
12
|
readonly wevu: {
|
|
12
13
|
readonly id: "wevu";
|
|
13
14
|
readonly label: "wevu";
|
|
15
|
+
readonly packageName: "wevu";
|
|
14
16
|
readonly relativePath: string;
|
|
15
17
|
};
|
|
16
18
|
readonly 'wevu-compiler': {
|
|
17
19
|
readonly id: "wevu-compiler";
|
|
18
20
|
readonly label: "wevu-compiler";
|
|
21
|
+
readonly packageName: "@wevu/compiler";
|
|
19
22
|
readonly relativePath: string;
|
|
20
23
|
};
|
|
21
24
|
};
|
|
@@ -26,7 +29,7 @@ declare const DEFAULT_MAX_FILE_CHARS = 80000;
|
|
|
26
29
|
declare const DEFAULT_MAX_RESULTS = 200;
|
|
27
30
|
declare const SKIPPED_DIR_NAMES: Set<string>;
|
|
28
31
|
|
|
29
|
-
interface
|
|
32
|
+
interface ResolvedExposedPackage {
|
|
30
33
|
id: ExposedPackageId;
|
|
31
34
|
label: string;
|
|
32
35
|
packageName: string;
|
|
@@ -38,9 +41,14 @@ interface ExposedPackageSummary {
|
|
|
38
41
|
readme?: string;
|
|
39
42
|
changelog?: string;
|
|
40
43
|
};
|
|
44
|
+
sourceRoot?: string;
|
|
45
|
+
cliPath?: string;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
interface ExposedPackageSummary extends ResolvedExposedPackage {
|
|
41
49
|
}
|
|
42
50
|
declare function loadPackageSummary(workspaceRoot: string, id: ExposedPackageId): Promise<ExposedPackageSummary>;
|
|
43
|
-
declare function loadExposedCatalog(workspaceRoot: string): Promise<
|
|
51
|
+
declare function loadExposedCatalog(workspaceRoot: string): Promise<ResolvedExposedPackage[]>;
|
|
44
52
|
|
|
45
53
|
interface CommandResult {
|
|
46
54
|
command: string;
|
|
@@ -85,6 +93,25 @@ declare function createWeappViteMcpServer(options?: CreateServerOptions): Promis
|
|
|
85
93
|
workspaceRoot: string;
|
|
86
94
|
}>;
|
|
87
95
|
|
|
96
|
+
declare const DEFAULT_MCP_HOST = "127.0.0.1";
|
|
97
|
+
declare const DEFAULT_MCP_PORT = 3088;
|
|
98
|
+
declare const DEFAULT_MCP_ENDPOINT = "/mcp";
|
|
99
|
+
interface StartMcpServerOptions extends CreateServerOptions {
|
|
100
|
+
transport?: 'stdio' | 'streamable-http';
|
|
101
|
+
host?: string;
|
|
102
|
+
port?: number;
|
|
103
|
+
endpoint?: string;
|
|
104
|
+
unref?: boolean;
|
|
105
|
+
quiet?: boolean;
|
|
106
|
+
onReady?: (message: string) => void;
|
|
107
|
+
}
|
|
108
|
+
interface McpServerHandle {
|
|
109
|
+
transport: 'stdio' | 'streamable-http';
|
|
110
|
+
close?: () => Promise<void>;
|
|
111
|
+
}
|
|
112
|
+
declare function startStdioServer(options?: CreateServerOptions): Promise<void>;
|
|
113
|
+
declare function startWeappViteMcpServer(options?: StartMcpServerOptions): Promise<McpServerHandle>;
|
|
114
|
+
|
|
88
115
|
declare function formatJson(value: unknown): string;
|
|
89
116
|
declare function normalizeErrorMessage(error: unknown): string;
|
|
90
117
|
declare function toToolResult(data: unknown, text?: string): {
|
|
@@ -108,7 +135,5 @@ declare function resolveWorkspaceRoot(start?: string): string;
|
|
|
108
135
|
declare function assertInsideRoot(root: string, targetPath: string): string;
|
|
109
136
|
declare function resolveSubPath(root: string, relativePath: string): string;
|
|
110
137
|
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
export { DEFAULT_MAX_FILE_CHARS, DEFAULT_MAX_OUTPUT_CHARS, DEFAULT_MAX_RESULTS, DEFAULT_TIMEOUT_MS, EXPOSED_PACKAGES, MCP_SERVER_NAME, MCP_SERVER_VERSION, SKIPPED_DIR_NAMES, assertInsideRoot, createWeappViteMcpServer, formatJson, listFilesInDirectory, loadExposedCatalog, loadPackageSummary, normalizeErrorMessage, readFileContent, resolveSubPath, resolveWorkspaceRoot, runCommand, searchTextInDirectory, startStdioServer, toToolError, toToolResult };
|
|
114
|
-
export type { CommandResult, CreateServerOptions, ExposedPackageId, ExposedPackageSummary, SearchMatch };
|
|
138
|
+
export { DEFAULT_MAX_FILE_CHARS, DEFAULT_MAX_OUTPUT_CHARS, DEFAULT_MAX_RESULTS, DEFAULT_MCP_ENDPOINT, DEFAULT_MCP_HOST, DEFAULT_MCP_PORT, DEFAULT_TIMEOUT_MS, EXPOSED_PACKAGES, MCP_SERVER_NAME, MCP_SERVER_VERSION, SKIPPED_DIR_NAMES, assertInsideRoot, createWeappViteMcpServer, formatJson, listFilesInDirectory, loadExposedCatalog, loadPackageSummary, normalizeErrorMessage, readFileContent, resolveSubPath, resolveWorkspaceRoot, runCommand, searchTextInDirectory, startStdioServer, startWeappViteMcpServer, toToolError, toToolResult };
|
|
139
|
+
export type { CommandResult, CreateServerOptions, ExposedPackageId, ExposedPackageSummary, McpServerHandle, SearchMatch, StartMcpServerOptions };
|
package/dist/index.mjs
CHANGED
|
@@ -1,12 +1,16 @@
|
|
|
1
1
|
import process from 'node:process';
|
|
2
2
|
import { fileURLToPath } from 'node:url';
|
|
3
|
-
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
|
|
4
3
|
import fs$1 from 'node:fs/promises';
|
|
4
|
+
import { createRequire } from 'node:module';
|
|
5
5
|
import path from 'node:path';
|
|
6
|
-
import { McpServer, ResourceTemplate } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
7
|
-
import { z } from 'zod';
|
|
8
6
|
import fs from 'node:fs';
|
|
9
7
|
import { spawn } from 'node:child_process';
|
|
8
|
+
import { Buffer } from 'node:buffer';
|
|
9
|
+
import http from 'node:http';
|
|
10
|
+
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
|
|
11
|
+
import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/streamableHttp.js';
|
|
12
|
+
import { McpServer, ResourceTemplate } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
13
|
+
import { z } from 'zod';
|
|
10
14
|
|
|
11
15
|
const MCP_SERVER_NAME = "@weapp-vite/mcp";
|
|
12
16
|
const MCP_SERVER_VERSION = "2.0.0";
|
|
@@ -14,17 +18,20 @@ const EXPOSED_PACKAGES = {
|
|
|
14
18
|
"weapp-vite": {
|
|
15
19
|
id: "weapp-vite",
|
|
16
20
|
label: "weapp-vite",
|
|
21
|
+
packageName: "weapp-vite",
|
|
17
22
|
relativePath: path.join("packages", "weapp-vite")
|
|
18
23
|
},
|
|
19
24
|
"wevu": {
|
|
20
25
|
id: "wevu",
|
|
21
26
|
label: "wevu",
|
|
22
|
-
|
|
27
|
+
packageName: "wevu",
|
|
28
|
+
relativePath: path.join("packages-runtime", "wevu")
|
|
23
29
|
},
|
|
24
30
|
"wevu-compiler": {
|
|
25
31
|
id: "wevu-compiler",
|
|
26
32
|
label: "wevu-compiler",
|
|
27
|
-
|
|
33
|
+
packageName: "@wevu/compiler",
|
|
34
|
+
relativePath: path.join("packages-runtime", "wevu-compiler")
|
|
28
35
|
}
|
|
29
36
|
};
|
|
30
37
|
const DEFAULT_TIMEOUT_MS = 12e4;
|
|
@@ -77,10 +84,6 @@ function resolveSubPath(root, relativePath) {
|
|
|
77
84
|
return assertInsideRoot(root, path.resolve(root, relativePath));
|
|
78
85
|
}
|
|
79
86
|
|
|
80
|
-
async function readJsonFile(filePath) {
|
|
81
|
-
const content = await fs$1.readFile(filePath, "utf8");
|
|
82
|
-
return JSON.parse(content);
|
|
83
|
-
}
|
|
84
87
|
async function pathExists(filePath) {
|
|
85
88
|
try {
|
|
86
89
|
await fs$1.access(filePath);
|
|
@@ -89,17 +92,40 @@ async function pathExists(filePath) {
|
|
|
89
92
|
return false;
|
|
90
93
|
}
|
|
91
94
|
}
|
|
92
|
-
async function
|
|
95
|
+
async function toWorkspaceRelativePath(workspaceRoot, absolutePath) {
|
|
96
|
+
const [realWorkspaceRoot, realAbsolutePath] = await Promise.all([
|
|
97
|
+
fs$1.realpath(workspaceRoot),
|
|
98
|
+
fs$1.realpath(absolutePath)
|
|
99
|
+
]);
|
|
100
|
+
const relativePath = path.relative(realWorkspaceRoot, realAbsolutePath);
|
|
101
|
+
if (!relativePath || relativePath === ".") {
|
|
102
|
+
return ".";
|
|
103
|
+
}
|
|
104
|
+
return relativePath;
|
|
105
|
+
}
|
|
106
|
+
async function readPackageJson(filePath) {
|
|
107
|
+
const content = await fs$1.readFile(filePath, "utf8");
|
|
108
|
+
return JSON.parse(content);
|
|
109
|
+
}
|
|
110
|
+
function createWorkspaceRequire(workspaceRoot) {
|
|
111
|
+
return createRequire(path.join(workspaceRoot, "__weapp_vite_mcp__.cjs"));
|
|
112
|
+
}
|
|
113
|
+
async function resolveMonorepoPackage(workspaceRoot, id) {
|
|
93
114
|
const config = EXPOSED_PACKAGES[id];
|
|
94
115
|
const absolutePath = assertInsideRoot(workspaceRoot, path.join(workspaceRoot, config.relativePath));
|
|
95
116
|
const packageJsonPath = path.join(absolutePath, "package.json");
|
|
96
|
-
|
|
117
|
+
if (!await pathExists(packageJsonPath)) {
|
|
118
|
+
return void 0;
|
|
119
|
+
}
|
|
120
|
+
const packageJson = await readPackageJson(packageJsonPath);
|
|
97
121
|
const readmePath = path.join(absolutePath, "README.md");
|
|
98
122
|
const changelogPath = path.join(absolutePath, "CHANGELOG.md");
|
|
123
|
+
const sourceRoot = await pathExists(path.join(absolutePath, "src")) ? absolutePath : void 0;
|
|
124
|
+
const cliPath = id === "weapp-vite" ? await pathExists(path.join(absolutePath, "bin", "weapp-vite.js")) ? path.join(absolutePath, "bin", "weapp-vite.js") : void 0 : void 0;
|
|
99
125
|
return {
|
|
100
126
|
id,
|
|
101
127
|
label: config.label,
|
|
102
|
-
packageName: packageJson.name ?? config.
|
|
128
|
+
packageName: packageJson.name ?? config.packageName,
|
|
103
129
|
version: packageJson.version ?? "0.0.0",
|
|
104
130
|
absolutePath,
|
|
105
131
|
relativePath: config.relativePath,
|
|
@@ -107,14 +133,73 @@ async function loadPackageSummary(workspaceRoot, id) {
|
|
|
107
133
|
docs: {
|
|
108
134
|
readme: await pathExists(readmePath) ? readmePath : void 0,
|
|
109
135
|
changelog: await pathExists(changelogPath) ? changelogPath : void 0
|
|
136
|
+
},
|
|
137
|
+
sourceRoot,
|
|
138
|
+
cliPath
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
async function resolveInstalledPackage(workspaceRoot, id) {
|
|
142
|
+
const config = EXPOSED_PACKAGES[id];
|
|
143
|
+
const workspaceRequire = createWorkspaceRequire(workspaceRoot);
|
|
144
|
+
let packageJsonPath;
|
|
145
|
+
try {
|
|
146
|
+
packageJsonPath = workspaceRequire.resolve(`${config.packageName}/package.json`);
|
|
147
|
+
} catch {
|
|
148
|
+
return void 0;
|
|
149
|
+
}
|
|
150
|
+
const absolutePath = path.dirname(packageJsonPath);
|
|
151
|
+
const relativePath = await toWorkspaceRelativePath(workspaceRoot, absolutePath);
|
|
152
|
+
const packageJson = await readPackageJson(packageJsonPath);
|
|
153
|
+
const docsRoot = path.join(absolutePath, "dist", "docs");
|
|
154
|
+
const installedReadmePath = path.join(docsRoot, "README.md");
|
|
155
|
+
const installedChangelogPath = path.join(docsRoot, "CHANGELOG.md");
|
|
156
|
+
const sourceRoot = await pathExists(path.join(absolutePath, "src")) ? absolutePath : void 0;
|
|
157
|
+
let cliPath;
|
|
158
|
+
if (id === "weapp-vite") {
|
|
159
|
+
const binEntry = typeof packageJson.bin === "string" ? packageJson.bin : packageJson.bin?.["weapp-vite"];
|
|
160
|
+
if (typeof binEntry === "string" && binEntry.trim()) {
|
|
161
|
+
const resolvedCliPath = path.resolve(absolutePath, binEntry);
|
|
162
|
+
if (await pathExists(resolvedCliPath)) {
|
|
163
|
+
cliPath = resolvedCliPath;
|
|
164
|
+
}
|
|
110
165
|
}
|
|
166
|
+
}
|
|
167
|
+
return {
|
|
168
|
+
id,
|
|
169
|
+
label: config.label,
|
|
170
|
+
packageName: packageJson.name ?? config.packageName,
|
|
171
|
+
version: packageJson.version ?? "0.0.0",
|
|
172
|
+
absolutePath,
|
|
173
|
+
relativePath,
|
|
174
|
+
scripts: Object.keys(packageJson.scripts ?? {}),
|
|
175
|
+
docs: {
|
|
176
|
+
readme: await pathExists(installedReadmePath) ? installedReadmePath : void 0,
|
|
177
|
+
changelog: await pathExists(installedChangelogPath) ? installedChangelogPath : void 0
|
|
178
|
+
},
|
|
179
|
+
sourceRoot,
|
|
180
|
+
cliPath
|
|
111
181
|
};
|
|
112
182
|
}
|
|
113
|
-
async function
|
|
114
|
-
|
|
115
|
-
|
|
183
|
+
async function resolveExposedPackage(workspaceRoot, id) {
|
|
184
|
+
return await resolveMonorepoPackage(workspaceRoot, id) ?? await resolveInstalledPackage(workspaceRoot, id) ?? Promise.reject(new Error(`\u672A\u627E\u5230\u66B4\u9732\u5305\uFF1A${id}`));
|
|
185
|
+
}
|
|
186
|
+
async function resolveExposedPackages(workspaceRoot) {
|
|
187
|
+
const resolved = await Promise.allSettled(
|
|
188
|
+
Object.keys(EXPOSED_PACKAGES).map((id) => resolveExposedPackage(workspaceRoot, id))
|
|
116
189
|
);
|
|
117
|
-
return
|
|
190
|
+
return resolved.flatMap((result) => {
|
|
191
|
+
if (result.status === "fulfilled") {
|
|
192
|
+
return [result.value];
|
|
193
|
+
}
|
|
194
|
+
return [];
|
|
195
|
+
}).sort((a, b) => a.id.localeCompare(b.id));
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
async function loadPackageSummary(workspaceRoot, id) {
|
|
199
|
+
return resolveExposedPackage(workspaceRoot, id);
|
|
200
|
+
}
|
|
201
|
+
async function loadExposedCatalog(workspaceRoot) {
|
|
202
|
+
return resolveExposedPackages(workspaceRoot);
|
|
118
203
|
}
|
|
119
204
|
|
|
120
205
|
const ALLOWED_COMMANDS = /* @__PURE__ */ new Set([
|
|
@@ -315,8 +400,12 @@ function toToolError(error) {
|
|
|
315
400
|
|
|
316
401
|
const packageIds = Object.keys(EXPOSED_PACKAGES);
|
|
317
402
|
const packageIdSchema = z.enum(packageIds);
|
|
318
|
-
function resolvePackageRoot(workspaceRoot, packageId) {
|
|
319
|
-
|
|
403
|
+
async function resolvePackageRoot(workspaceRoot, packageId) {
|
|
404
|
+
const resolved = await resolveExposedPackage(workspaceRoot, packageId);
|
|
405
|
+
if (!resolved.sourceRoot) {
|
|
406
|
+
throw new Error(`\u5F53\u524D\u5DE5\u4F5C\u533A\u4E2D\u7684 ${packageId} \u4E0D\u5305\u542B\u6E90\u7801\u76EE\u5F55\uFF0C\u8BF7\u6539\u4E3A\u4F18\u5148\u8BFB\u53D6\u672C\u5730\u968F\u5305\u6587\u6863\u3002`);
|
|
407
|
+
}
|
|
408
|
+
return assertInsideRoot(workspaceRoot, resolved.sourceRoot);
|
|
320
409
|
}
|
|
321
410
|
function toDocsUri(packageId, fileName) {
|
|
322
411
|
return `weapp-vite://docs/${packageId}/${fileName}`;
|
|
@@ -354,7 +443,7 @@ async function createWeappViteMcpServer(options) {
|
|
|
354
443
|
}
|
|
355
444
|
}, async ({ packageId, directory, maxResults }) => {
|
|
356
445
|
try {
|
|
357
|
-
const packageRoot = resolvePackageRoot(workspaceRoot, packageId);
|
|
446
|
+
const packageRoot = await resolvePackageRoot(workspaceRoot, packageId);
|
|
358
447
|
const files = await listFilesInDirectory(packageRoot, directory ?? "src", maxResults ?? DEFAULT_MAX_RESULTS);
|
|
359
448
|
return toToolResult({
|
|
360
449
|
packageId,
|
|
@@ -378,7 +467,7 @@ async function createWeappViteMcpServer(options) {
|
|
|
378
467
|
}
|
|
379
468
|
}, async ({ packageId, filePath, startLine, endLine, maxChars }) => {
|
|
380
469
|
try {
|
|
381
|
-
const packageRoot = resolvePackageRoot(workspaceRoot, packageId);
|
|
470
|
+
const packageRoot = await resolvePackageRoot(workspaceRoot, packageId);
|
|
382
471
|
const { filePath: absolutePath, content } = await readFileContent(packageRoot, filePath, {
|
|
383
472
|
startLine,
|
|
384
473
|
endLine,
|
|
@@ -414,7 +503,7 @@ async function createWeappViteMcpServer(options) {
|
|
|
414
503
|
if (allMatches.length >= safeMax) {
|
|
415
504
|
break;
|
|
416
505
|
}
|
|
417
|
-
const packageRoot = resolvePackageRoot(workspaceRoot, id);
|
|
506
|
+
const packageRoot = await resolvePackageRoot(workspaceRoot, id);
|
|
418
507
|
const matches = await searchTextInDirectory(packageRoot, query, {
|
|
419
508
|
relativeDirectory: directory ?? "src",
|
|
420
509
|
maxResults: safeMax - allMatches.length
|
|
@@ -444,9 +533,9 @@ async function createWeappViteMcpServer(options) {
|
|
|
444
533
|
}
|
|
445
534
|
}, async ({ packageId, script, args, timeoutMs }) => {
|
|
446
535
|
try {
|
|
447
|
-
const
|
|
536
|
+
const resolvedPackage = await resolveExposedPackage(workspaceRoot, packageId);
|
|
448
537
|
const result = await runCommand(workspaceRoot, "pnpm", ["run", script, ...args ?? []], {
|
|
449
|
-
cwdRelative,
|
|
538
|
+
cwdRelative: resolvedPackage.relativePath,
|
|
450
539
|
timeoutMs: timeoutMs ?? DEFAULT_TIMEOUT_MS
|
|
451
540
|
});
|
|
452
541
|
return toToolResult(result);
|
|
@@ -466,7 +555,10 @@ async function createWeappViteMcpServer(options) {
|
|
|
466
555
|
}
|
|
467
556
|
}, async ({ subCommand, projectPath, platform, args, timeoutMs }) => {
|
|
468
557
|
try {
|
|
469
|
-
const cliPath =
|
|
558
|
+
const cliPath = (await resolveExposedPackage(workspaceRoot, "weapp-vite")).cliPath;
|
|
559
|
+
if (!cliPath) {
|
|
560
|
+
throw new Error("\u5F53\u524D\u5DE5\u4F5C\u533A\u4E2D\u7684 weapp-vite \u672A\u66B4\u9732 CLI \u5165\u53E3");
|
|
561
|
+
}
|
|
470
562
|
const finalArgs = [cliPath, subCommand];
|
|
471
563
|
if (projectPath) {
|
|
472
564
|
finalArgs.push(resolveSubPath(workspaceRoot, projectPath));
|
|
@@ -572,7 +664,7 @@ async function createWeappViteMcpServer(options) {
|
|
|
572
664
|
}]
|
|
573
665
|
};
|
|
574
666
|
});
|
|
575
|
-
const catalog = await
|
|
667
|
+
const catalog = await resolveExposedPackages(workspaceRoot);
|
|
576
668
|
for (const summary of catalog) {
|
|
577
669
|
if (summary.docs.readme) {
|
|
578
670
|
const uri = toDocsUri(summary.id, "README.md");
|
|
@@ -616,7 +708,7 @@ async function createWeappViteMcpServer(options) {
|
|
|
616
708
|
throw new Error(`\u672A\u77E5 package\uFF1A${packageId}`);
|
|
617
709
|
}
|
|
618
710
|
const relativePath = decodeURIComponent(String(variables.path ?? ""));
|
|
619
|
-
const packageRoot = resolvePackageRoot(workspaceRoot, packageId);
|
|
711
|
+
const packageRoot = await resolvePackageRoot(workspaceRoot, packageId);
|
|
620
712
|
const { content } = await readFileContent(packageRoot, relativePath, {
|
|
621
713
|
maxChars: DEFAULT_MAX_FILE_CHARS
|
|
622
714
|
});
|
|
@@ -643,11 +735,158 @@ async function createWeappViteMcpServer(options) {
|
|
|
643
735
|
};
|
|
644
736
|
}
|
|
645
737
|
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
738
|
+
const DEFAULT_MCP_HOST = "127.0.0.1";
|
|
739
|
+
const DEFAULT_MCP_PORT = 3088;
|
|
740
|
+
const DEFAULT_MCP_ENDPOINT = "/mcp";
|
|
741
|
+
function normalizeEndpoint(input) {
|
|
742
|
+
const value = typeof input === "string" ? input.trim() : "";
|
|
743
|
+
if (!value) {
|
|
744
|
+
return DEFAULT_MCP_ENDPOINT;
|
|
745
|
+
}
|
|
746
|
+
return value.startsWith("/") ? value : `/${value}`;
|
|
747
|
+
}
|
|
748
|
+
function normalizePort(input) {
|
|
749
|
+
if (typeof input === "number" && Number.isInteger(input) && input > 0 && input <= 65535) {
|
|
750
|
+
return input;
|
|
751
|
+
}
|
|
752
|
+
return DEFAULT_MCP_PORT;
|
|
753
|
+
}
|
|
754
|
+
async function parseJsonBody(req) {
|
|
755
|
+
if (req.method !== "POST") {
|
|
756
|
+
return void 0;
|
|
757
|
+
}
|
|
758
|
+
const chunks = [];
|
|
759
|
+
for await (const chunk of req) {
|
|
760
|
+
chunks.push(typeof chunk === "string" ? Buffer.from(chunk) : chunk);
|
|
761
|
+
}
|
|
762
|
+
if (chunks.length === 0) {
|
|
763
|
+
return void 0;
|
|
764
|
+
}
|
|
765
|
+
const raw = Buffer.concat(chunks).toString("utf8").trim();
|
|
766
|
+
if (!raw) {
|
|
767
|
+
return void 0;
|
|
768
|
+
}
|
|
769
|
+
return JSON.parse(raw);
|
|
770
|
+
}
|
|
771
|
+
function writeJson(res, statusCode, payload) {
|
|
772
|
+
if (res.headersSent) {
|
|
773
|
+
return;
|
|
774
|
+
}
|
|
775
|
+
res.statusCode = statusCode;
|
|
776
|
+
res.setHeader("content-type", "application/json");
|
|
777
|
+
res.end(JSON.stringify(payload));
|
|
778
|
+
}
|
|
779
|
+
async function startStdioServer$1(options) {
|
|
780
|
+
const previousCwd = process.cwd();
|
|
781
|
+
if (options?.workspaceRoot) {
|
|
782
|
+
process.chdir(options.workspaceRoot);
|
|
783
|
+
}
|
|
784
|
+
try {
|
|
785
|
+
const { server } = await createWeappViteMcpServer(options);
|
|
786
|
+
const transport = new StdioServerTransport();
|
|
787
|
+
await server.connect(transport);
|
|
788
|
+
} finally {
|
|
789
|
+
if (options?.workspaceRoot) {
|
|
790
|
+
process.chdir(previousCwd);
|
|
791
|
+
}
|
|
792
|
+
}
|
|
650
793
|
}
|
|
794
|
+
async function startStreamableHttpServer(options) {
|
|
795
|
+
const {
|
|
796
|
+
endpoint = DEFAULT_MCP_ENDPOINT,
|
|
797
|
+
host = DEFAULT_MCP_HOST,
|
|
798
|
+
port = DEFAULT_MCP_PORT,
|
|
799
|
+
workspaceRoot,
|
|
800
|
+
unref = false,
|
|
801
|
+
quiet = false,
|
|
802
|
+
onReady
|
|
803
|
+
} = options;
|
|
804
|
+
const normalizedEndpoint = normalizeEndpoint(endpoint);
|
|
805
|
+
const normalizedPort = normalizePort(port);
|
|
806
|
+
const { server: mcpServer } = await createWeappViteMcpServer({ workspaceRoot });
|
|
807
|
+
const transport = new StreamableHTTPServerTransport({
|
|
808
|
+
sessionIdGenerator: void 0
|
|
809
|
+
});
|
|
810
|
+
await mcpServer.connect(transport);
|
|
811
|
+
const httpServer = http.createServer(async (req, res) => {
|
|
812
|
+
try {
|
|
813
|
+
const hostHeader = req.headers.host ?? `${host}:${normalizedPort}`;
|
|
814
|
+
const url = new URL(req.url ?? "/", `http://${hostHeader}`);
|
|
815
|
+
if (url.pathname !== normalizedEndpoint) {
|
|
816
|
+
writeJson(res, 404, {
|
|
817
|
+
jsonrpc: "2.0",
|
|
818
|
+
error: {
|
|
819
|
+
code: -32004,
|
|
820
|
+
message: `Not Found: ${url.pathname}`
|
|
821
|
+
},
|
|
822
|
+
id: null
|
|
823
|
+
});
|
|
824
|
+
return;
|
|
825
|
+
}
|
|
826
|
+
const method = req.method ?? "GET";
|
|
827
|
+
if (!["GET", "POST", "DELETE"].includes(method)) {
|
|
828
|
+
writeJson(res, 405, {
|
|
829
|
+
jsonrpc: "2.0",
|
|
830
|
+
error: {
|
|
831
|
+
code: -32005,
|
|
832
|
+
message: `Method Not Allowed: ${method}`
|
|
833
|
+
},
|
|
834
|
+
id: null
|
|
835
|
+
});
|
|
836
|
+
return;
|
|
837
|
+
}
|
|
838
|
+
const body = await parseJsonBody(req);
|
|
839
|
+
await transport.handleRequest(req, res, body);
|
|
840
|
+
} catch (error) {
|
|
841
|
+
writeJson(res, 500, {
|
|
842
|
+
jsonrpc: "2.0",
|
|
843
|
+
error: {
|
|
844
|
+
code: -32603,
|
|
845
|
+
message: error instanceof Error ? error.message : String(error)
|
|
846
|
+
},
|
|
847
|
+
id: null
|
|
848
|
+
});
|
|
849
|
+
}
|
|
850
|
+
});
|
|
851
|
+
await new Promise((resolve, reject) => {
|
|
852
|
+
httpServer.once("error", reject);
|
|
853
|
+
httpServer.listen(normalizedPort, host, () => {
|
|
854
|
+
resolve();
|
|
855
|
+
});
|
|
856
|
+
});
|
|
857
|
+
if (unref) {
|
|
858
|
+
httpServer.unref();
|
|
859
|
+
}
|
|
860
|
+
if (!quiet) {
|
|
861
|
+
onReady?.(`[mcp] streamable-http ready at http://${host}:${normalizedPort}${normalizedEndpoint}`);
|
|
862
|
+
}
|
|
863
|
+
return {
|
|
864
|
+
transport: "streamable-http",
|
|
865
|
+
close: async () => {
|
|
866
|
+
await transport.close();
|
|
867
|
+
await new Promise((resolve, reject) => {
|
|
868
|
+
httpServer.close((error) => {
|
|
869
|
+
if (error) {
|
|
870
|
+
reject(error);
|
|
871
|
+
return;
|
|
872
|
+
}
|
|
873
|
+
resolve();
|
|
874
|
+
});
|
|
875
|
+
});
|
|
876
|
+
}
|
|
877
|
+
};
|
|
878
|
+
}
|
|
879
|
+
async function startWeappViteMcpServer(options) {
|
|
880
|
+
const transport = options?.transport ?? "stdio";
|
|
881
|
+
if (transport === "streamable-http") {
|
|
882
|
+
return startStreamableHttpServer(options ?? {});
|
|
883
|
+
}
|
|
884
|
+
await startStdioServer$1(options);
|
|
885
|
+
return {
|
|
886
|
+
transport: "stdio"
|
|
887
|
+
};
|
|
888
|
+
}
|
|
889
|
+
|
|
651
890
|
function isDirectExecution() {
|
|
652
891
|
const entry = process.argv[1];
|
|
653
892
|
if (!entry) {
|
|
@@ -665,4 +904,4 @@ ${message}
|
|
|
665
904
|
});
|
|
666
905
|
}
|
|
667
906
|
|
|
668
|
-
export { DEFAULT_MAX_FILE_CHARS, DEFAULT_MAX_OUTPUT_CHARS, DEFAULT_MAX_RESULTS, DEFAULT_TIMEOUT_MS, EXPOSED_PACKAGES, MCP_SERVER_NAME, MCP_SERVER_VERSION, SKIPPED_DIR_NAMES, assertInsideRoot, createWeappViteMcpServer, formatJson, listFilesInDirectory, loadExposedCatalog, loadPackageSummary, normalizeErrorMessage, readFileContent, resolveSubPath, resolveWorkspaceRoot, runCommand, searchTextInDirectory, startStdioServer, toToolError, toToolResult };
|
|
907
|
+
export { DEFAULT_MAX_FILE_CHARS, DEFAULT_MAX_OUTPUT_CHARS, DEFAULT_MAX_RESULTS, DEFAULT_MCP_ENDPOINT, DEFAULT_MCP_HOST, DEFAULT_MCP_PORT, DEFAULT_TIMEOUT_MS, EXPOSED_PACKAGES, MCP_SERVER_NAME, MCP_SERVER_VERSION, SKIPPED_DIR_NAMES, assertInsideRoot, createWeappViteMcpServer, formatJson, listFilesInDirectory, loadExposedCatalog, loadPackageSummary, normalizeErrorMessage, readFileContent, resolveSubPath, resolveWorkspaceRoot, runCommand, searchTextInDirectory, startStdioServer$1 as startStdioServer, startWeappViteMcpServer, toToolError, toToolResult };
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@weapp-vite/mcp",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "1.1.
|
|
4
|
+
"version": "1.1.2",
|
|
5
5
|
"description": "mcp",
|
|
6
6
|
"author": "ice breaker <1324318532@qq.com>",
|
|
7
7
|
"license": "ISC",
|
|
@@ -31,7 +31,7 @@
|
|
|
31
31
|
"node": "^20.19.0 || >=22.12.0"
|
|
32
32
|
},
|
|
33
33
|
"dependencies": {
|
|
34
|
-
"@modelcontextprotocol/sdk": "^1.
|
|
34
|
+
"@modelcontextprotocol/sdk": "^1.29.0",
|
|
35
35
|
"zod": "^4.3.6"
|
|
36
36
|
},
|
|
37
37
|
"scripts": {
|
|
@@ -40,6 +40,7 @@
|
|
|
40
40
|
"build": "unbuild",
|
|
41
41
|
"test": "vitest run",
|
|
42
42
|
"test:dev": "vitest",
|
|
43
|
+
"typecheck": "tsc --noEmit",
|
|
43
44
|
"release": "pnpm publish",
|
|
44
45
|
"lint": "eslint .",
|
|
45
46
|
"lint:fix": "eslint . --fix",
|