如何配置Fastify的multipart formdata校验Schema?
解决Fastify Multipart FormData校验Schema问题
问题根源
attachFieldsToBody和addToBody配置冲突,导致表单字段解析异常- Schema中文件数组
attachments使用了非标准JSON Schema关键字isFile,引发验证逻辑混乱 - Fastify V4中
consumes已被弃用,需替换为contentType
修复步骤
1. 修正Multipart配置
移除冲突的addToBody配置,仅保留attachFieldsToBody: true即可将表单字段挂载到request.body:
limits: { fieldNameSize: 100, fieldSize: 10000, fields: 5, fileSize: 1000000, files: 5, headerPairs: 2000, parts: 10, }, attachFieldsToBody: true // 移除 addToBody: true
2. 更新Schema定义
调整schema.ts
替换consumes为Fastify V4支持的contentType:
export const createFeedbackSchema: FastifySchema = { summary: 'Feedback Creation', description: 'Feedback creation', operationId: 'createFeedback', tags: [_MODULES.Feedback.key], body: createFeedbackBodyRequest, contentType: 'multipart/form-data', // 替换原consumes字段 response: createFeedbackResponse, };
修正template.ts中的请求体Schema
移除非标准的isFile关键字,改用符合JSON Schema规范的定义(上传文件会被Fastify解析为Upload对象):
export const createFeedbackBodyRequest = { type: 'object', required: ['email_address', 'title'], properties: { email_address: { type: 'string', format: 'email', nullable: false, minLength: 1, description: 'Email address', }, title: { type: 'string', nullable: false, minLength: 1, description: 'Feedback title', }, custom_title: { type: 'string', nullable: true, minLength: 1, description: 'Feedback custom title', }, additional_details: { type: 'string', nullable: true, minLength: 1, description: 'Feedback additional details', }, attachments: { type: 'array', nullable: true, description: 'Feedback attachment files', items: { type: 'object', // Upload对象为object类型 additionalProperties: true // 允许Upload对象自带的属性与方法 }, }, }, };
3. 路由处理中的文件验证(可选)
如果需要严格验证文件类型、大小,可在路由逻辑中手动处理:
async function createFeedback(request: FastifyRequest) { const { attachments } = request.body as any; if (attachments) { for (const file of attachments) { // 验证文件类型 if (!file.mimetype.startsWith('image/')) { throw new Error('仅支持图片类型附件'); } // 二次验证文件大小(已在multipart limits中配置,此处为可选增强) const fileSize = await file.toBuffer().then(buf => buf.length); if (fileSize > 1000000) { throw new Error('文件大小不能超过1MB'); } } } // 执行后续业务逻辑 }
验证请求
发送请求时需确保:
email_address和title为form-data中的普通文本字段,且不为空attachments为form-data中的文件字段,支持多选(对应数组结构)
内容的提问来源于stack exchange,提问作者DISCO
相关产品推荐
相关产品推荐

