Skip to content

Commit d2b9a7d

Browse files
committed
fix: support express version 5 and version 4
AdminForth/1781/image
1 parent 2c3e031 commit d2b9a7d

1 file changed

Lines changed: 44 additions & 3 deletions

File tree

adminforth/servers/express.ts

Lines changed: 44 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ import { createRequire } from 'module';
3232
// instead of a static JSON import (which would hard-link a peer dep at parse time).
3333
const require = createRequire(import.meta.url);
3434
const expressVersion: string = require('express/package.json').version;
35+
const expressMajor = Number(expressVersion.split('.')[0]);
3536

3637
function replaceAtStart(string, substring) {
3738
if (string.startsWith(substring)) {
@@ -195,8 +196,12 @@ class ExpressServer implements IExpressHttpServer {
195196
// Express 5 (path-to-regexp v8) requires named wildcards instead of a bare `*`.
196197
// `{*splat}` is an optional catch-all so the SPA route also matches the base path itself
197198
// (e.g. `/admin` as well as `/admin/...`; `/` as well as `/foo` when baseUrl is empty).
198-
const assetsRoute = `${slashedPrefix}assets/*splat`;
199-
const spaCatchAll = prefix ? `${prefix}{*splat}` : '/{*splat}';
199+
let assetsRoute = `${slashedPrefix}assets/*splat`;
200+
let spaCatchAll = prefix ? `${prefix}{*splat}` : '/{*splat}';
201+
if (expressMajor === 4) {
202+
assetsRoute = `${slashedPrefix}assets/*`;
203+
spaCatchAll = `${prefix}*`;
204+
}
200205

201206
if (this.adminforth.runningHotReload) {
202207
const handler = async (req, res) => {
@@ -727,7 +732,43 @@ class ExpressServer implements IExpressHttpServer {
727732
const input = { body, query, headers, cookies, adminUser, response, requestUrl, _raw_express_req: req, _raw_express_res: res, tr, abortSignal: abortController.signal};
728733

729734
let output;
730-
output = await handler(input);
735+
if (expressMajor === 5) {
736+
output = await handler(input);
737+
} else if (expressMajor === 4) {
738+
// Express 4 does not support async handlers, so we need to wrap it in a try/catch
739+
try {
740+
output = await handler(input);
741+
} catch (e) {
742+
afLogger.error(`Error in handler ${e}`);
743+
afLogger.error(e.stack);
744+
745+
const expressErrorCallback = this.adminforth.config.expressErrorCallback;
746+
747+
if (expressErrorCallback) {
748+
try {
749+
await expressErrorCallback({
750+
error: e,
751+
adminforth: this.adminforth,
752+
extra: {
753+
body,
754+
query,
755+
headers,
756+
cookies: cookies as any,
757+
requestUrl,
758+
meta: {},
759+
response,
760+
},
761+
});
762+
} catch (callbackError) {
763+
afLogger.error(`Error in expressErrorCallback ${callbackError}`);
764+
afLogger.error(callbackError?.stack);
765+
}
766+
}
767+
768+
res.status(500).send('Internal server error');
769+
return;
770+
}
771+
}
731772

732773
response.headers.forEach(([name, value]) => {
733774
res.setHeader(name, value);

0 commit comments

Comments
 (0)