@forklaunch/express 0.5.34 → 0.6.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/lib/index.d.mts +142 -114
- package/lib/index.d.ts +142 -114
- package/lib/index.js +80 -7
- package/lib/index.mjs +81 -8
- package/package.json +13 -12
package/lib/index.js
CHANGED
@@ -39,6 +39,8 @@ module.exports = __toCommonJS(index_exports);
|
|
39
39
|
// src/expressApplication.ts
|
40
40
|
var import_common3 = require("@forklaunch/common");
|
41
41
|
var import_http3 = require("@forklaunch/core/http");
|
42
|
+
var import_zod = require("@forklaunch/validator/zod");
|
43
|
+
var import_streamableHttp = require("@modelcontextprotocol/sdk/server/streamableHttp.js");
|
42
44
|
var import_express_api_reference = require("@scalar/express-api-reference");
|
43
45
|
var import_crypto = __toESM(require("crypto"));
|
44
46
|
var import_express2 = __toESM(require("express"));
|
@@ -75,7 +77,15 @@ function contentParse(options2) {
|
|
75
77
|
case "text":
|
76
78
|
return textParser(req, res, next);
|
77
79
|
case "file":
|
78
|
-
return rawParser(req, res,
|
80
|
+
return rawParser(req, res, async (err) => {
|
81
|
+
if (err) {
|
82
|
+
return next(err);
|
83
|
+
}
|
84
|
+
if (req.body instanceof Buffer) {
|
85
|
+
req.body = req.body.toString("utf-8");
|
86
|
+
}
|
87
|
+
next();
|
88
|
+
});
|
79
89
|
case "multipart": {
|
80
90
|
const bb = (0, import_busboy.default)({
|
81
91
|
headers: req.headers,
|
@@ -88,8 +98,8 @@ function contentParse(options2) {
|
|
88
98
|
chunks.push(chunk);
|
89
99
|
});
|
90
100
|
file.on("end", () => {
|
91
|
-
const
|
92
|
-
body[fieldname] =
|
101
|
+
const fileString = chunks.map((chunk) => chunk.toString()).join("");
|
102
|
+
body[fieldname] = fileString;
|
93
103
|
});
|
94
104
|
});
|
95
105
|
bb.on("field", (fieldname, value) => {
|
@@ -175,11 +185,63 @@ var Application = class extends import_http3.ForklaunchExpressLikeApplication {
|
|
175
185
|
}
|
176
186
|
listen(...args) {
|
177
187
|
const port = typeof args[0] === "number" ? args[0] : Number(process.env.PORT);
|
188
|
+
const host = typeof args[1] === "string" ? args[1] : process.env.HOST ?? "localhost";
|
189
|
+
const protocol = process.env.PROTOCOL ?? "http";
|
178
190
|
const openApi = (0, import_http3.generateSwaggerDocument)(
|
179
191
|
this.schemaValidator,
|
192
|
+
protocol,
|
193
|
+
host,
|
180
194
|
port,
|
181
195
|
this.routers
|
182
196
|
);
|
197
|
+
if (this.schemaValidator instanceof import_zod.ZodSchemaValidator) {
|
198
|
+
const zodSchemaValidator = this.schemaValidator;
|
199
|
+
const routers = this.routers;
|
200
|
+
this.internal.get("/mcp", async (_req, res) => {
|
201
|
+
const server = (0, import_http3.generateMcpServer)(
|
202
|
+
zodSchemaValidator,
|
203
|
+
protocol,
|
204
|
+
host,
|
205
|
+
port,
|
206
|
+
"1.0.0",
|
207
|
+
routers
|
208
|
+
);
|
209
|
+
res.json(server);
|
210
|
+
});
|
211
|
+
this.internal.post("/mcp", async (req, res) => {
|
212
|
+
try {
|
213
|
+
const server = (0, import_http3.generateMcpServer)(
|
214
|
+
zodSchemaValidator,
|
215
|
+
protocol,
|
216
|
+
host,
|
217
|
+
port,
|
218
|
+
"1.0.0",
|
219
|
+
routers
|
220
|
+
);
|
221
|
+
const transport = new import_streamableHttp.StreamableHTTPServerTransport({
|
222
|
+
sessionIdGenerator: void 0
|
223
|
+
});
|
224
|
+
res.on("close", () => {
|
225
|
+
transport.close();
|
226
|
+
server.close();
|
227
|
+
});
|
228
|
+
await server.connect(transport);
|
229
|
+
await transport.handleRequest(req, res, req.body);
|
230
|
+
} catch (error) {
|
231
|
+
console.error("Error handling MCP request:", error);
|
232
|
+
if (!res.headersSent) {
|
233
|
+
res.status(500).json({
|
234
|
+
jsonrpc: "2.0",
|
235
|
+
error: {
|
236
|
+
code: -32603,
|
237
|
+
message: "Internal server error"
|
238
|
+
},
|
239
|
+
id: null
|
240
|
+
});
|
241
|
+
}
|
242
|
+
}
|
243
|
+
});
|
244
|
+
}
|
183
245
|
if (this.docsConfiguration == null || this.docsConfiguration.type === "scalar") {
|
184
246
|
this.internal.use(
|
185
247
|
`/api/${process.env.VERSION ?? "v1"}${process.env.DOCS_PATH ?? "/docs"}`,
|
@@ -218,14 +280,14 @@ var Application = class extends import_http3.ForklaunchExpressLikeApplication {
|
|
218
280
|
const errorHandler = (err, req, res, _next) => {
|
219
281
|
const statusCode = Number(res.statusCode);
|
220
282
|
res.locals.errorMessage = err.message;
|
221
|
-
console.
|
283
|
+
console.error(err);
|
222
284
|
res.type("text/plain");
|
223
285
|
res.status(statusCode >= 400 ? statusCode : 500).send(
|
224
286
|
`Internal server error:
|
225
287
|
|
226
288
|
Correlation id: ${(0, import_http3.isForklaunchRequest)(req) ? req.context.correlationId : "No correlation ID"}`
|
227
289
|
);
|
228
|
-
|
290
|
+
this.openTelemetryCollector.error(
|
229
291
|
err.stack ?? err.message,
|
230
292
|
(0, import_http3.meta)({
|
231
293
|
[import_http3.ATTR_HTTP_RESPONSE_STATUS_CODE]: statusCode
|
@@ -240,8 +302,7 @@ Correlation id: ${(0, import_http3.isForklaunchRequest)(req) ? req.context.corre
|
|
240
302
|
// src/expressRouter.ts
|
241
303
|
var import_http4 = require("@forklaunch/core/http");
|
242
304
|
var import_express3 = __toESM(require("express"));
|
243
|
-
var Router = class extends import_http4.ForklaunchExpressLikeRouter {
|
244
|
-
// implements ForklaunchRouter<SV>
|
305
|
+
var Router = class _Router extends import_http4.ForklaunchExpressLikeRouter {
|
245
306
|
/**
|
246
307
|
* Creates an instance of Router.
|
247
308
|
*
|
@@ -260,7 +321,9 @@ var Router = class extends import_http4.ForklaunchExpressLikeRouter {
|
|
260
321
|
openTelemetryCollector
|
261
322
|
);
|
262
323
|
this.basePath = basePath;
|
324
|
+
this.configOptions = options2;
|
263
325
|
}
|
326
|
+
configOptions;
|
264
327
|
route(path) {
|
265
328
|
this.internal.route(path);
|
266
329
|
return this;
|
@@ -429,6 +492,16 @@ var Router = class extends import_http4.ForklaunchExpressLikeRouter {
|
|
429
492
|
...middlewareOrMiddlewareWithTypedHandler
|
430
493
|
);
|
431
494
|
};
|
495
|
+
clone() {
|
496
|
+
const clone = new _Router(
|
497
|
+
this.basePath,
|
498
|
+
this.schemaValidator,
|
499
|
+
this.openTelemetryCollector,
|
500
|
+
this.configOptions
|
501
|
+
);
|
502
|
+
this.cloneInternals(clone);
|
503
|
+
return clone;
|
504
|
+
}
|
432
505
|
};
|
433
506
|
|
434
507
|
// src/handlers/checkout.ts
|
package/lib/index.mjs
CHANGED
@@ -3,11 +3,13 @@ import { safeStringify as safeStringify2 } from "@forklaunch/common";
|
|
3
3
|
import {
|
4
4
|
ATTR_HTTP_RESPONSE_STATUS_CODE,
|
5
5
|
ForklaunchExpressLikeApplication,
|
6
|
+
generateMcpServer,
|
6
7
|
generateSwaggerDocument,
|
7
8
|
isForklaunchRequest,
|
8
|
-
logger,
|
9
9
|
meta
|
10
10
|
} from "@forklaunch/core/http";
|
11
|
+
import { ZodSchemaValidator } from "@forklaunch/validator/zod";
|
12
|
+
import { StreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/streamableHttp.js";
|
11
13
|
import { apiReference } from "@scalar/express-api-reference";
|
12
14
|
import crypto from "crypto";
|
13
15
|
import express2 from "express";
|
@@ -44,7 +46,15 @@ function contentParse(options2) {
|
|
44
46
|
case "text":
|
45
47
|
return textParser(req, res, next);
|
46
48
|
case "file":
|
47
|
-
return rawParser(req, res,
|
49
|
+
return rawParser(req, res, async (err) => {
|
50
|
+
if (err) {
|
51
|
+
return next(err);
|
52
|
+
}
|
53
|
+
if (req.body instanceof Buffer) {
|
54
|
+
req.body = req.body.toString("utf-8");
|
55
|
+
}
|
56
|
+
next();
|
57
|
+
});
|
48
58
|
case "multipart": {
|
49
59
|
const bb = Busboy({
|
50
60
|
headers: req.headers,
|
@@ -57,8 +67,8 @@ function contentParse(options2) {
|
|
57
67
|
chunks.push(chunk);
|
58
68
|
});
|
59
69
|
file.on("end", () => {
|
60
|
-
const
|
61
|
-
body[fieldname] =
|
70
|
+
const fileString = chunks.map((chunk) => chunk.toString()).join("");
|
71
|
+
body[fieldname] = fileString;
|
62
72
|
});
|
63
73
|
});
|
64
74
|
bb.on("field", (fieldname, value) => {
|
@@ -146,11 +156,63 @@ var Application = class extends ForklaunchExpressLikeApplication {
|
|
146
156
|
}
|
147
157
|
listen(...args) {
|
148
158
|
const port = typeof args[0] === "number" ? args[0] : Number(process.env.PORT);
|
159
|
+
const host = typeof args[1] === "string" ? args[1] : process.env.HOST ?? "localhost";
|
160
|
+
const protocol = process.env.PROTOCOL ?? "http";
|
149
161
|
const openApi = generateSwaggerDocument(
|
150
162
|
this.schemaValidator,
|
163
|
+
protocol,
|
164
|
+
host,
|
151
165
|
port,
|
152
166
|
this.routers
|
153
167
|
);
|
168
|
+
if (this.schemaValidator instanceof ZodSchemaValidator) {
|
169
|
+
const zodSchemaValidator = this.schemaValidator;
|
170
|
+
const routers = this.routers;
|
171
|
+
this.internal.get("/mcp", async (_req, res) => {
|
172
|
+
const server = generateMcpServer(
|
173
|
+
zodSchemaValidator,
|
174
|
+
protocol,
|
175
|
+
host,
|
176
|
+
port,
|
177
|
+
"1.0.0",
|
178
|
+
routers
|
179
|
+
);
|
180
|
+
res.json(server);
|
181
|
+
});
|
182
|
+
this.internal.post("/mcp", async (req, res) => {
|
183
|
+
try {
|
184
|
+
const server = generateMcpServer(
|
185
|
+
zodSchemaValidator,
|
186
|
+
protocol,
|
187
|
+
host,
|
188
|
+
port,
|
189
|
+
"1.0.0",
|
190
|
+
routers
|
191
|
+
);
|
192
|
+
const transport = new StreamableHTTPServerTransport({
|
193
|
+
sessionIdGenerator: void 0
|
194
|
+
});
|
195
|
+
res.on("close", () => {
|
196
|
+
transport.close();
|
197
|
+
server.close();
|
198
|
+
});
|
199
|
+
await server.connect(transport);
|
200
|
+
await transport.handleRequest(req, res, req.body);
|
201
|
+
} catch (error) {
|
202
|
+
console.error("Error handling MCP request:", error);
|
203
|
+
if (!res.headersSent) {
|
204
|
+
res.status(500).json({
|
205
|
+
jsonrpc: "2.0",
|
206
|
+
error: {
|
207
|
+
code: -32603,
|
208
|
+
message: "Internal server error"
|
209
|
+
},
|
210
|
+
id: null
|
211
|
+
});
|
212
|
+
}
|
213
|
+
}
|
214
|
+
});
|
215
|
+
}
|
154
216
|
if (this.docsConfiguration == null || this.docsConfiguration.type === "scalar") {
|
155
217
|
this.internal.use(
|
156
218
|
`/api/${process.env.VERSION ?? "v1"}${process.env.DOCS_PATH ?? "/docs"}`,
|
@@ -189,14 +251,14 @@ var Application = class extends ForklaunchExpressLikeApplication {
|
|
189
251
|
const errorHandler = (err, req, res, _next) => {
|
190
252
|
const statusCode = Number(res.statusCode);
|
191
253
|
res.locals.errorMessage = err.message;
|
192
|
-
console.
|
254
|
+
console.error(err);
|
193
255
|
res.type("text/plain");
|
194
256
|
res.status(statusCode >= 400 ? statusCode : 500).send(
|
195
257
|
`Internal server error:
|
196
258
|
|
197
259
|
Correlation id: ${isForklaunchRequest(req) ? req.context.correlationId : "No correlation ID"}`
|
198
260
|
);
|
199
|
-
|
261
|
+
this.openTelemetryCollector.error(
|
200
262
|
err.stack ?? err.message,
|
201
263
|
meta({
|
202
264
|
[ATTR_HTTP_RESPONSE_STATUS_CODE]: statusCode
|
@@ -213,8 +275,7 @@ import {
|
|
213
275
|
ForklaunchExpressLikeRouter
|
214
276
|
} from "@forklaunch/core/http";
|
215
277
|
import express3 from "express";
|
216
|
-
var Router = class extends ForklaunchExpressLikeRouter {
|
217
|
-
// implements ForklaunchRouter<SV>
|
278
|
+
var Router = class _Router extends ForklaunchExpressLikeRouter {
|
218
279
|
/**
|
219
280
|
* Creates an instance of Router.
|
220
281
|
*
|
@@ -233,7 +294,9 @@ var Router = class extends ForklaunchExpressLikeRouter {
|
|
233
294
|
openTelemetryCollector
|
234
295
|
);
|
235
296
|
this.basePath = basePath;
|
297
|
+
this.configOptions = options2;
|
236
298
|
}
|
299
|
+
configOptions;
|
237
300
|
route(path) {
|
238
301
|
this.internal.route(path);
|
239
302
|
return this;
|
@@ -402,6 +465,16 @@ var Router = class extends ForklaunchExpressLikeRouter {
|
|
402
465
|
...middlewareOrMiddlewareWithTypedHandler
|
403
466
|
);
|
404
467
|
};
|
468
|
+
clone() {
|
469
|
+
const clone = new _Router(
|
470
|
+
this.basePath,
|
471
|
+
this.schemaValidator,
|
472
|
+
this.openTelemetryCollector,
|
473
|
+
this.configOptions
|
474
|
+
);
|
475
|
+
this.cloneInternals(clone);
|
476
|
+
return clone;
|
477
|
+
}
|
405
478
|
};
|
406
479
|
|
407
480
|
// src/handlers/checkout.ts
|
package/package.json
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
{
|
2
2
|
"name": "@forklaunch/express",
|
3
|
-
"version": "0.
|
3
|
+
"version": "0.6.1",
|
4
4
|
"description": "Forklaunch framework for express.",
|
5
5
|
"homepage": "https://github.com/forklaunch/forklaunch-js#readme",
|
6
6
|
"bugs": {
|
@@ -25,8 +25,9 @@
|
|
25
25
|
"lib/**"
|
26
26
|
],
|
27
27
|
"dependencies": {
|
28
|
-
"@
|
29
|
-
"@
|
28
|
+
"@modelcontextprotocol/sdk": "^1.13.3",
|
29
|
+
"@scalar/express-api-reference": "^0.8.7",
|
30
|
+
"@types/multer": "^2.0.0",
|
30
31
|
"body-parser": "^2.2.0",
|
31
32
|
"busboy": "^1.6.0",
|
32
33
|
"cors": "^2.8.5",
|
@@ -34,12 +35,12 @@
|
|
34
35
|
"multer": "2.0.1",
|
35
36
|
"qs": "^6.14.0",
|
36
37
|
"swagger-ui-express": "^5.0.1",
|
37
|
-
"@forklaunch/common": "0.
|
38
|
-
"@forklaunch/
|
39
|
-
"@forklaunch/
|
38
|
+
"@forklaunch/common": "0.4.1",
|
39
|
+
"@forklaunch/validator": "0.7.1",
|
40
|
+
"@forklaunch/core": "0.10.1"
|
40
41
|
},
|
41
42
|
"devDependencies": {
|
42
|
-
"@eslint/js": "^9.
|
43
|
+
"@eslint/js": "^9.30.1",
|
43
44
|
"@types/body-parser": "^1.19.6",
|
44
45
|
"@types/busboy": "^1.5.4",
|
45
46
|
"@types/cors": "^2.8.19",
|
@@ -48,16 +49,16 @@
|
|
48
49
|
"@types/jest": "^30.0.0",
|
49
50
|
"@types/qs": "^6.14.0",
|
50
51
|
"@types/swagger-ui-express": "^4.1.8",
|
51
|
-
"@typescript/native-preview": "7.0.0-dev.
|
52
|
-
"jest": "^30.0.
|
52
|
+
"@typescript/native-preview": "7.0.0-dev.20250702.1",
|
53
|
+
"jest": "^30.0.3",
|
53
54
|
"kill-port-process": "^3.2.1",
|
54
|
-
"prettier": "^3.
|
55
|
+
"prettier": "^3.6.2",
|
55
56
|
"ts-jest": "^29.4.0",
|
56
57
|
"ts-node": "^10.9.2",
|
57
58
|
"tsup": "^8.5.0",
|
58
|
-
"typedoc": "^0.28.
|
59
|
+
"typedoc": "^0.28.7",
|
59
60
|
"typescript": "^5.8.3",
|
60
|
-
"typescript-eslint": "^8.
|
61
|
+
"typescript-eslint": "^8.35.1"
|
61
62
|
},
|
62
63
|
"scripts": {
|
63
64
|
"build": "tsgo --noEmit && tsup index.ts --format cjs,esm --no-splitting --tsconfig tsconfig.json --outDir lib --dts --clean",
|