Use formidable instead of multer
This commit is contained in:
parent
adf380c19d
commit
a15d496c53
@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "wms-core",
|
||||
"version": "0.7.12",
|
||||
"version": "0.8.2",
|
||||
"description": "Node web framework",
|
||||
"repository": "git@gitlab.com:ArisuOngaku/wms-core.git",
|
||||
"author": "Alice Gaudon <alice@gaudon.pro>",
|
||||
@ -22,6 +22,7 @@
|
||||
"@types/connect-redis": "^0.0.13",
|
||||
"@types/cookie": "^0.3.3",
|
||||
"@types/cookie-parser": "^1.4.2",
|
||||
"@types/formidable": "^1.0.31",
|
||||
"@types/geoip-lite": "^1.1.31",
|
||||
"@types/jest": "^25.2.1",
|
||||
"@types/mjml": "^4.0.4",
|
||||
@ -34,7 +35,6 @@
|
||||
"dependencies": {
|
||||
"@types/express": "^4.17.6",
|
||||
"@types/express-session": "^1.17.0",
|
||||
"@types/multer": "^1.4.3",
|
||||
"@types/mysql": "^2.15.10",
|
||||
"@types/nodemailer": "^6.4.0",
|
||||
"@types/nunjucks": "^3.1.3",
|
||||
@ -48,6 +48,7 @@
|
||||
"cookie-parser": "^1.4.5",
|
||||
"express": "^4.17.1",
|
||||
"express-session": "^1.17.1",
|
||||
"formidable": "^1.2.2",
|
||||
"geoip-lite": "^1.4.2",
|
||||
"mjml": "^4.6.2",
|
||||
"mysql": "^2.18.1",
|
||||
|
@ -170,12 +170,6 @@ export default abstract class Application {
|
||||
});
|
||||
}
|
||||
|
||||
public setupRequestParsingMiddlewares(router: Router) {
|
||||
for (const controller of this.controllers) {
|
||||
controller.setupRequestParsingMiddlewares(router);
|
||||
}
|
||||
}
|
||||
|
||||
public getWebSocketListeners(): { [p: string]: WebSocketListener } {
|
||||
return this.webSocketListeners;
|
||||
}
|
||||
|
@ -39,9 +39,6 @@ export default abstract class Controller {
|
||||
return [];
|
||||
}
|
||||
|
||||
public setupRequestParsingMiddlewares(router: Router): void {
|
||||
}
|
||||
|
||||
public hasGlobalHandlers(): boolean {
|
||||
return this.getGlobalHandlers().length > 0;
|
||||
}
|
||||
|
@ -24,6 +24,16 @@ export default class AuthComponent extends ApplicationComponent<void> {
|
||||
}
|
||||
}
|
||||
|
||||
export const REQUIRE_REQUEST_AUTH_MIDDLEWARE = async (req: Request, res: Response, next: NextFunction): Promise<void> => {
|
||||
if (!await req.authGuard.isAuthenticatedViaRequest(req)) {
|
||||
req.flash('error', `You must be logged in to access ${req.url}.`);
|
||||
res.redirect(Controller.route('auth') || '/');
|
||||
return;
|
||||
}
|
||||
|
||||
req.models.user = await req.authGuard.getUserForRequest(req);
|
||||
next();
|
||||
};
|
||||
|
||||
export const REQUIRE_AUTH_MIDDLEWARE = async (req: Request, res: Response, next: NextFunction): Promise<void> => {
|
||||
if (await req.authGuard.isAuthenticatedViaRequest(req)) {
|
||||
|
@ -17,7 +17,7 @@ export default class CsrfProtectionComponent extends ApplicationComponent<void>
|
||||
return req.session!.csrf;
|
||||
};
|
||||
|
||||
if (!['GET', 'HEAD', 'OPTIONS'].find(s => s === req.method)) {
|
||||
if (!['GET', 'HEAD', 'OPTIONS'].find(s => s === req.method) && !req.authGuard.isAuthenticatedViaRequest(req)) {
|
||||
if (req.session.csrf === undefined) {
|
||||
throw new InvalidCsrfTokenError(req.baseUrl, `You weren't assigned any CSRF token.`);
|
||||
} else if (req.body.csrf === undefined) {
|
||||
|
@ -1,8 +1,8 @@
|
||||
import ApplicationComponent from "../ApplicationComponent";
|
||||
import express, {Express, NextFunction, Request, Response, Router} from "express";
|
||||
import express, {Express, RequestHandler, Router} from "express";
|
||||
import Logger from "../Logger";
|
||||
import {Server} from "http";
|
||||
import {MulterError} from "multer";
|
||||
import {IncomingForm} from "formidable";
|
||||
import {FileError, ValidationBag} from "../db/Validator";
|
||||
|
||||
export default class ExpressAppComponent extends ApplicationComponent<void> {
|
||||
@ -19,22 +19,6 @@ export default class ExpressAppComponent extends ApplicationComponent<void> {
|
||||
Logger.info(`Web server running on localhost:${this.port}.`);
|
||||
});
|
||||
|
||||
this.app?.setupRequestParsingMiddlewares(router);
|
||||
|
||||
// Multer error handler
|
||||
router.use((err: any, req: Request, res: Response, next: NextFunction) => {
|
||||
if (err instanceof MulterError) {
|
||||
const bag = new ValidationBag();
|
||||
const validationError = new FileError(err.message);
|
||||
validationError.thingName = err.field;
|
||||
bag.addMessage(validationError);
|
||||
req.flash('validation', bag.getMessages());
|
||||
res.redirectBack();
|
||||
} else {
|
||||
next(err);
|
||||
}
|
||||
});
|
||||
|
||||
router.use(express.json());
|
||||
router.use(express.urlencoded({
|
||||
extended: true,
|
||||
@ -57,4 +41,31 @@ export default class ExpressAppComponent extends ApplicationComponent<void> {
|
||||
if (!this.server) throw 'Server was not initialized.';
|
||||
return this.server;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export const FILE_UPLOAD_MIDDLEWARE: (formFactory: () => IncomingForm, defaultField: string) => RequestHandler = (formFactory: () => IncomingForm, defaultField: string) => {
|
||||
return async (req, res, next) => {
|
||||
const form = formFactory();
|
||||
try {
|
||||
await new Promise<any>((resolve, reject) => {
|
||||
form.parse(req, (err, fields, files) => {
|
||||
if (err) {
|
||||
reject(err);
|
||||
return;
|
||||
}
|
||||
req.body = fields;
|
||||
req.files = files;
|
||||
resolve();
|
||||
});
|
||||
});
|
||||
} catch (e) {
|
||||
const bag = new ValidationBag();
|
||||
const fileError = new FileError(e);
|
||||
fileError.thingName = defaultField;
|
||||
bag.addMessage(fileError);
|
||||
next(bag);
|
||||
return;
|
||||
}
|
||||
next();
|
||||
};
|
||||
};
|
||||
|
@ -34,7 +34,6 @@ export default class LogRequestsComponent extends ApplicationComponent<void> {
|
||||
query: req.query,
|
||||
params: req.params,
|
||||
body: req.body,
|
||||
file: req.file,
|
||||
files: req.files,
|
||||
cookies: req.cookies,
|
||||
sessionId: req.sessionID,
|
||||
|
2
src/types/Express.d.ts
vendored
2
src/types/Express.d.ts
vendored
@ -1,6 +1,7 @@
|
||||
import {Environment} from "nunjucks";
|
||||
import Model from "../db/Model";
|
||||
import AuthGuard from "../auth/AuthGuard";
|
||||
import {Files} from "formidable";
|
||||
|
||||
declare global {
|
||||
namespace Express {
|
||||
@ -9,6 +10,7 @@ declare global {
|
||||
models: { [p: string]: Model | null };
|
||||
modelCollections: { [p: string]: Model[] | null };
|
||||
authGuard: AuthGuard<any>;
|
||||
files: Files;
|
||||
|
||||
flash(): { [key: string]: string[] };
|
||||
|
||||
|
25
yarn.lock
25
yarn.lock
@ -557,6 +557,11 @@
|
||||
resolved "https://registry.toot.party/@types%2fcookie/-/cookie-0.3.3.tgz#85bc74ba782fb7aa3a514d11767832b0e3bc6803"
|
||||
integrity sha512-LKVP3cgXBT9RYj+t+9FDKwS5tdI+rPBXaNSkma7hvqy35lc7mAokC2zsqWJH0LaqIt3B962nuYI77hsJoT1gow==
|
||||
|
||||
"@types/events@*":
|
||||
version "3.0.0"
|
||||
resolved "https://registry.toot.party/@types%2fevents/-/events-3.0.0.tgz#2862f3f58a9a7f7c3e78d79f130dd4d71c25c2a7"
|
||||
integrity sha512-EaObqwIvayI5a8dCzhFrjKzVwKLxjoG9T6Ppd5CEo07LRKfQ8Yokw54r5+Wq7FaBQ+yXRvQAYPrHwya1/UFt9g==
|
||||
|
||||
"@types/express-serve-static-core@*":
|
||||
version "4.17.7"
|
||||
resolved "https://registry.toot.party/@types%2fexpress-serve-static-core/-/express-serve-static-core-4.17.7.tgz#dfe61f870eb549dc6d7e12050901847c7d7e915b"
|
||||
@ -584,6 +589,14 @@
|
||||
"@types/qs" "*"
|
||||
"@types/serve-static" "*"
|
||||
|
||||
"@types/formidable@^1.0.31":
|
||||
version "1.0.31"
|
||||
resolved "https://registry.toot.party/@types%2fformidable/-/formidable-1.0.31.tgz#274f9dc2d0a1a9ce1feef48c24ca0859e7ec947b"
|
||||
integrity sha512-dIhM5t8lRP0oWe2HF8MuPvdd1TpPTjhDMAqemcq6oIZQCBQTovhBAdTQ5L5veJB4pdQChadmHuxtB0YzqvfU3Q==
|
||||
dependencies:
|
||||
"@types/events" "*"
|
||||
"@types/node" "*"
|
||||
|
||||
"@types/geoip-lite@^1.1.31":
|
||||
version "1.1.31"
|
||||
resolved "https://registry.toot.party/@types%2fgeoip-lite/-/geoip-lite-1.1.31.tgz#0063e47916ea982fa913a8c825f429e66b59ad10"
|
||||
@ -641,13 +654,6 @@
|
||||
resolved "https://registry.toot.party/@types%2fmjml/-/mjml-4.0.4.tgz#af6075d29f64d47186d76125504daf544dfb2b42"
|
||||
integrity sha512-4PhI6iZ1zGXZ9X9W0bbmI7mS2xdxITURueqSWJ/cTeS5+tbAtOUDG1ww/fPbfcffWwR4NeOjyNcZiczafH/yfw==
|
||||
|
||||
"@types/multer@^1.4.3":
|
||||
version "1.4.3"
|
||||
resolved "https://registry.toot.party/@types%2fmulter/-/multer-1.4.3.tgz#bdff74b334c38a8ee1de9fbedb5d1d3dbc377422"
|
||||
integrity sha512-tWsKbF5LYtXrJ7eOfI0aLBgEv9B7fnJe1JRXTj5+Z6EMfX0yHVsRFsNGnKyN8Bs0gtDv+JR37xAqsPnALyVTqg==
|
||||
dependencies:
|
||||
"@types/express" "*"
|
||||
|
||||
"@types/mysql@^2.15.10":
|
||||
version "2.15.13"
|
||||
resolved "https://registry.toot.party/@types%2fmysql/-/mysql-2.15.13.tgz#153dc2e2f8dffd39f7bba556c2679f14bdbecde1"
|
||||
@ -2115,6 +2121,11 @@ form-data@~2.3.2:
|
||||
combined-stream "^1.0.6"
|
||||
mime-types "^2.1.12"
|
||||
|
||||
formidable@^1.2.2:
|
||||
version "1.2.2"
|
||||
resolved "https://registry.toot.party/formidable/-/formidable-1.2.2.tgz#bf69aea2972982675f00865342b982986f6b8dd9"
|
||||
integrity sha512-V8gLm+41I/8kguQ4/o1D3RIHRmhYFG4pnNyonvua+40rqcEmT4+V71yaZ3B457xbbgCsCfjSPi65u/W6vK1U5Q==
|
||||
|
||||
forwarded@~0.1.2:
|
||||
version "0.1.2"
|
||||
resolved "https://registry.toot.party/forwarded/-/forwarded-0.1.2.tgz#98c23dab1175657b8c0573e8ceccd91b0ff18c84"
|
||||
|
Loading…
Reference in New Issue
Block a user