@arkstack/driver-express 0.14.22 → 0.15.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.js +31 -4
- package/dist/middlewares/index.d.ts +20 -1
- package/dist/middlewares/index.js +48 -1
- package/package.json +9 -5
package/dist/index.js
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import express from "express";
|
|
2
2
|
import { ArkstackKitDriver } from "@arkstack/contract";
|
|
3
|
-
import { ErrorHandler, Logger, RequestException, env, renderError, resolveRuntimeModule } from "@arkstack/common";
|
|
3
|
+
import { ErrorHandler, Logger, RequestException, devTlsCredentials, env, localNetworkAddress, renderError, resolveRuntimeModule } from "@arkstack/common";
|
|
4
|
+
import https from "node:https";
|
|
4
5
|
import { resolveMiddleware } from "@arkstack/http";
|
|
5
6
|
import ngrok from "@ngrok/ngrok";
|
|
6
7
|
import { Router as Router$2 } from "clear-router/express";
|
|
@@ -191,9 +192,11 @@ var ExpressDriver = class extends ArkstackKitDriver {
|
|
|
191
192
|
*/
|
|
192
193
|
async start(app, port) {
|
|
193
194
|
const host = env("APP_HOST", env("HOST", "0.0.0.0"));
|
|
195
|
+
const secure = env("APP_SECURE", false) === true;
|
|
194
196
|
const tunneled = env("TUNNEL", false);
|
|
195
|
-
|
|
196
|
-
|
|
197
|
+
const scheme = secure ? "https" : "http";
|
|
198
|
+
const onListen = async () => {
|
|
199
|
+
let log = startupLogLines(scheme, host, port);
|
|
197
200
|
if (tunneled === true) {
|
|
198
201
|
const url = (await ngrok.forward({
|
|
199
202
|
addr: port,
|
|
@@ -208,8 +211,32 @@ var ExpressDriver = class extends ArkstackKitDriver {
|
|
|
208
211
|
}
|
|
209
212
|
}
|
|
210
213
|
console.log(log.join("\n"));
|
|
211
|
-
}
|
|
214
|
+
};
|
|
215
|
+
if (secure) {
|
|
216
|
+
const credentials = await devTlsCredentials();
|
|
217
|
+
https.createServer({
|
|
218
|
+
key: credentials.key,
|
|
219
|
+
cert: credentials.cert
|
|
220
|
+
}, app).listen(port, host, onListen);
|
|
221
|
+
return;
|
|
222
|
+
}
|
|
223
|
+
app.listen(port, host, onListen);
|
|
224
|
+
}
|
|
225
|
+
};
|
|
226
|
+
/**
|
|
227
|
+
* Build the "Server is running" startup lines, adding a local-network URL when
|
|
228
|
+
* the server is bound to all interfaces (`0.0.0.0`/`::`) so it is reachable from
|
|
229
|
+
* other devices.
|
|
230
|
+
*/
|
|
231
|
+
const startupLogLines = (scheme, host, port) => {
|
|
232
|
+
const bindsAll = host === "0.0.0.0" || host === "::";
|
|
233
|
+
const localHost = bindsAll ? "localhost" : host;
|
|
234
|
+
const lines = [Logger.log([["Server is running on", "white"], [`${scheme}://${localHost}:${port}`, "cyan"]], " ", false)];
|
|
235
|
+
if (bindsAll) {
|
|
236
|
+
const address = localNetworkAddress();
|
|
237
|
+
if (address) lines.push(Logger.log([["Network access via", "white"], [`${scheme}://${address}:${port}`, "cyan"]], " ", false));
|
|
212
238
|
}
|
|
239
|
+
return lines;
|
|
213
240
|
};
|
|
214
241
|
//#endregion
|
|
215
242
|
export { ExpressDriver, Router, defaultErrorHandler };
|
|
@@ -22,6 +22,25 @@ declare class FormDataMiddleware {
|
|
|
22
22
|
handler(req: Request, res: Response, next: NextFunction): unknown;
|
|
23
23
|
}
|
|
24
24
|
//#endregion
|
|
25
|
+
//#region src/middlewares/inertia.d.ts
|
|
26
|
+
/**
|
|
27
|
+
* Bind the Inertia request context for Express.
|
|
28
|
+
*
|
|
29
|
+
* Normalizes the Express request into the adapter's driver-agnostic shape and
|
|
30
|
+
* runs the downstream handler inside Inertia's async-local context (mirroring the
|
|
31
|
+
* `resora` middleware), so `inertia()` / `Inertia.*` resolve the active request.
|
|
32
|
+
*
|
|
33
|
+
* It also upgrades `302` redirects to `303 See Other` for `PUT`/`PATCH`/`DELETE`
|
|
34
|
+
* Inertia visits, which the Inertia client requires to follow the redirect with
|
|
35
|
+
* a `GET`.
|
|
36
|
+
*
|
|
37
|
+
* `@arkstack/inertia` is imported dynamically so the package stays optional.
|
|
38
|
+
*/
|
|
39
|
+
declare const inertia: () => Handler;
|
|
40
|
+
declare class InertiaMiddleware {
|
|
41
|
+
handler(req: Request, res: Response, next: NextFunction): unknown;
|
|
42
|
+
}
|
|
43
|
+
//#endregion
|
|
25
44
|
//#region src/middlewares/limiter.d.ts
|
|
26
45
|
/**
|
|
27
46
|
* create a rate limiter middleware
|
|
@@ -66,4 +85,4 @@ declare class RequestLoggerMiddleware {
|
|
|
66
85
|
*/
|
|
67
86
|
declare const resora: () => Handler;
|
|
68
87
|
//#endregion
|
|
69
|
-
export { AuthMiddleware, FormDataMiddleware, RequestLoggerMiddleware, auth, formdata, limiter, requestLogger, resora };
|
|
88
|
+
export { AuthMiddleware, FormDataMiddleware, InertiaMiddleware, RequestLoggerMiddleware, auth, formdata, inertia, limiter, requestLogger, resora };
|
|
@@ -74,6 +74,53 @@ var FormDataMiddleware = class {
|
|
|
74
74
|
}
|
|
75
75
|
};
|
|
76
76
|
//#endregion
|
|
77
|
+
//#region src/middlewares/inertia.ts
|
|
78
|
+
/**
|
|
79
|
+
* Bind the Inertia request context for Express.
|
|
80
|
+
*
|
|
81
|
+
* Normalizes the Express request into the adapter's driver-agnostic shape and
|
|
82
|
+
* runs the downstream handler inside Inertia's async-local context (mirroring the
|
|
83
|
+
* `resora` middleware), so `inertia()` / `Inertia.*` resolve the active request.
|
|
84
|
+
*
|
|
85
|
+
* It also upgrades `302` redirects to `303 See Other` for `PUT`/`PATCH`/`DELETE`
|
|
86
|
+
* Inertia visits, which the Inertia client requires to follow the redirect with
|
|
87
|
+
* a `GET`.
|
|
88
|
+
*
|
|
89
|
+
* `@arkstack/inertia` is imported dynamically so the package stays optional.
|
|
90
|
+
*/
|
|
91
|
+
const inertia = () => {
|
|
92
|
+
return async (req, res, next) => {
|
|
93
|
+
try {
|
|
94
|
+
const { runInertia, shouldUpgradeRedirect } = await import("@arkstack/inertia");
|
|
95
|
+
const request = {
|
|
96
|
+
method: String(req.method ?? "GET").toUpperCase(),
|
|
97
|
+
url: req.originalUrl || req.url || "/",
|
|
98
|
+
header: (name) => {
|
|
99
|
+
const value = req.headers[name.toLowerCase()];
|
|
100
|
+
return Array.isArray(value) ? value[0] : value;
|
|
101
|
+
}
|
|
102
|
+
};
|
|
103
|
+
if (request.header("x-inertia") === "true") {
|
|
104
|
+
const original = res.redirect.bind(res);
|
|
105
|
+
res.redirect = ((...args) => {
|
|
106
|
+
let status = typeof args[0] === "number" ? args[0] : 302;
|
|
107
|
+
const url = typeof args[0] === "number" ? args[1] : args[0];
|
|
108
|
+
if (shouldUpgradeRedirect(request.method, status)) status = 303;
|
|
109
|
+
return original(status, url);
|
|
110
|
+
});
|
|
111
|
+
}
|
|
112
|
+
runInertia(request, () => next());
|
|
113
|
+
} catch (error) {
|
|
114
|
+
next(error);
|
|
115
|
+
}
|
|
116
|
+
};
|
|
117
|
+
};
|
|
118
|
+
var InertiaMiddleware = class {
|
|
119
|
+
handler(req, res, next) {
|
|
120
|
+
return inertia()(req, res, next);
|
|
121
|
+
}
|
|
122
|
+
};
|
|
123
|
+
//#endregion
|
|
77
124
|
//#region src/Exceptions/RateLimitExceededException.ts
|
|
78
125
|
var RateLimitExceededException = class extends Exception {
|
|
79
126
|
statusCode = 429;
|
|
@@ -180,4 +227,4 @@ const resora = () => {
|
|
|
180
227
|
};
|
|
181
228
|
};
|
|
182
229
|
//#endregion
|
|
183
|
-
export { AuthMiddleware, FormDataMiddleware, RequestLoggerMiddleware, auth, formdata, limiter, requestLogger, resora };
|
|
230
|
+
export { AuthMiddleware, FormDataMiddleware, InertiaMiddleware, RequestLoggerMiddleware, auth, formdata, inertia, limiter, requestLogger, resora };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@arkstack/driver-express",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.15.1",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Express driver for Arkstack, providing Express-based runtime integration for the framework.",
|
|
6
6
|
"homepage": "https://arkstack.toneflix.net",
|
|
@@ -43,17 +43,21 @@
|
|
|
43
43
|
"express-rate-limit": "^8.4.1",
|
|
44
44
|
"multer": "^2.1.1",
|
|
45
45
|
"resora": "^1.3.27",
|
|
46
|
-
"@arkstack/contract": "^0.
|
|
46
|
+
"@arkstack/contract": "^0.15.1"
|
|
47
47
|
},
|
|
48
48
|
"peerDependencies": {
|
|
49
49
|
"express": "^5.2.1",
|
|
50
|
-
"@arkstack/
|
|
51
|
-
"@arkstack/
|
|
52
|
-
"@arkstack/
|
|
50
|
+
"@arkstack/auth": "^0.15.1",
|
|
51
|
+
"@arkstack/common": "^0.15.1",
|
|
52
|
+
"@arkstack/foundry": "^0.15.1",
|
|
53
|
+
"@arkstack/inertia": "^0.15.1"
|
|
53
54
|
},
|
|
54
55
|
"peerDependenciesMeta": {
|
|
55
56
|
"@arkstack/auth": {
|
|
56
57
|
"optional": true
|
|
58
|
+
},
|
|
59
|
+
"@arkstack/inertia": {
|
|
60
|
+
"optional": true
|
|
57
61
|
}
|
|
58
62
|
},
|
|
59
63
|
"devDependencies": {
|