1

所以,我正在构建一个小应用程序来学习如何使用 express.js。我有一个非常简单的表单,同时提交一个文本字段和一个文件。这是通过 FormData 提交的,所以我在后端使用 multer 来处理请求。我想做的是在对文件执行任何操作之前对表单的文本输入执行验证(即仅在验证成功时保存,如果不发送某种错误消息)。我曾经这样做过

<form id="form" method='POST' enctype='multipart/form-data'>
      <input type='file' id='file-upload' name='file-upload' />
      <input type='text' id='text-upload' name='text-upload' />
      <input type='submit' />
</form>

后端:router.js

//somewhere in the router file
import {importedController} from './controllers/importedController';
/* some other routes */
router.post('/upload', importedController.processfunction);

导入的Controller.js

exports.processfunction = (req, res, next) => {
var getFields = multer().any();
getFields(req, res, err => {
 if (err) {return next(err);}
 req.checkBody('text-upload','must not be empty!').notEmpty();
 //do the validation from here
 var errors = req.validationErrors();
 if (errors) { 
  //some logic
 } else {
  //some other stuff
  //in both, i can access req.body and req.file to do whatever i want
 }
});
}

但是,我注意到express validator似乎有一种新语法,因此我尝试遵循此语法并执行以下操作:

路由器.js

router.post('/upload', [ body('text-input', 'must be not empty').not().isEmpty()], importedController.processfunction);

但是然后在我的importedController.js 中,验证在我定义的multer getFields() 函数之外不起作用(似乎合乎逻辑,因为尚未处理请求)。但是,如果我尝试将其包含在 multer 函数中:

导入的Controller.js

exports.processfunction = (req, res, next) => {
 var getFields = multer().any();
 getFields(req, res, err => {
  if (err) {return next(err);}
  errors = validationResult(req);
  if (!errors.isEmpty()) {
   //actually always yields and error...
  } else { //stuff}
 });
}

然后它总是返回一个错误,尽管字段输入是正确的。就好像对“未处理”请求执行了验证,其中 req.body 为空。虽然代码现在可以工作所以不着急,但为了以后的项目,我想遵循新的语法。非常感谢任何帮助!

编辑:感谢@gustavohenke 在下面的回答,我找到了一个解决方案

意识到这一点,我的问题与 multer 模块的工作方式有关,因为它似乎在处理表单数据之前上传文件(必须在验证之前)——至少 multer 模块似乎给了你无法控制何时上传文件,使您无法在实际保存之前调用另一个中间件。

所以我最终做的是在客户端使用 ajax 首先只发送表单数据(保存文件以供以后使用)到multer().any()与表单验证器逻辑链接的中间件。根据第一次调用服务器给出的响应,然后我将它与另一个 ajax 链接起来,最终将文件上传到另一个路由,这次使用 amulter(storage: myStorage).single('myFileInputName')来上传文件。

仔细想想,这个解决方案似乎比我一开始想的要好:它不仅避免了在表单输入错误的情况下保存文件,它甚至避免使用任何带宽来发送文件(可能相当沉重)如果输入不正确。

4

1 回答 1

1

当您说验证发生在multer 处理身体之前发生时,您是正确的。

在这两种情况下,验证器都会尽快运行;但请注意以下差异:

  • 在您为遗留 API 提供的示例中,您在处理主体后在 multer 回调中定义验证。因此,它有效。
  • 但是,在您的检查 API 示例中,验证器是在 multer 有机会执行之前定义的,因此您总是会遇到错误 -req.body仍然是空的。
于 2017-09-06T14:36:26.497 回答