NestJS文件上传时如何从回调返回JSON消息而非触发错误
解决方法
Multer 的文件过滤器回调本身没有直接暴露响应对象,无法直接调用 res.send 返回结果,你可以通过以下两种方式实现自定义 JSON 响应的需求:
方案1:搭配 Nest 异常过滤器捕获 Multer 错误(符合 Nest 开发规范,推荐使用)
- 先修改你的文件过滤器,把错误提示改成指定内容即可:
export const FileFilter = (req, file, callback) => { if (!file.originalname.match(/\.(jpg|jpeg|png)$/)) { // 这里抛出的错误会被后续异常过滤器捕获 return callback(new Error('file type is not supported'), false); } callback(null, true); }
- 新建一个专门处理 Multer 错误的异常过滤器:
import { ExceptionFilter, Catch, ArgumentsHost } from '@nestjs/common'; @Catch(Error) export class MulterFileFilter implements ExceptionFilter { catch(exception: Error, host: ArgumentsHost) { const ctx = host.switchToHttp(); const response = ctx.getResponse(); // 匹配文件类型校验不通过的错误 if (exception.message === 'file type is not supported') { // 直接返回你需要的响应格式 return response.status(400).send({ status: "error", message: "file type is not supported" }); } // 其他错误可以在这里统一处理 return response.status(400).send({ status: "error", message: exception.message }); } }
- 在你的上传接口上绑定该异常过滤器:
import { Controller, Post, UseInterceptors, UploadedFile, UseFilters } from '@nestjs/common'; import { FileInterceptor } from '@nestjs/platform-express'; @Controller('upload') export class UploadController { @Post() // 绑定异常过滤器 @UseFilters(MulterFileFilter) @UseInterceptors(FileInterceptor('file', { fileFilter: FileFilter, // 你的其他Multer配置,比如存储路径、大小限制等 })) upload(@UploadedFile() file: Express.Multer.File) { // 正常上传后的业务逻辑 return { status: 'success', data: file }; } }
方案2:自定义拦截器校验文件类型(无需抛出错误)
如果你不想用异常过滤器,也可以自己封装拦截器直接校验文件后返回响应:
import { Injectable, NestInterceptor, ExecutionContext, CallHandler } from '@nestjs/common'; import { Observable } from 'rxjs'; @Injectable() export class FileValidateInterceptor implements NestInterceptor { intercept(context: ExecutionContext, next: CallHandler): Observable<any> { const ctx = context.switchToHttp(); const req = ctx.getRequest(); const res = ctx.getResponse(); const file = req.file; // 直接校验文件类型 if (!file?.originalname?.match(/\.(jpg|jpeg|png)$/)) { return res.send({ status: "error", message: "file type is not supported" }); } return next.handle(); } }
之后在上传接口上叠加使用该拦截器即可。
内容的提问来源于stack exchange,提问作者Nishad Ceroen
相关产品推荐
相关产品推荐

