You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用express-validator验证req.body数组对象值遇报错问题

问题:form-data发送对象数组时express-validator报错“Cannot convert object to primitive value”

我尝试通过Postman以form-data形式发送对象数组,使用express-validator对请求体数据进行验证,编写了如下addEvent验证函数:

// validate.js
import { check, body } from "express-validator";
import { validationResult } from "express-validator";
export const addEvent = () => {
  return [
    check("name", "Name is required").notEmpty(),
    check("pricing")
      .isArray()
      .notEmpty(),
    check("pricing.*.ticketType")
      .notEmpty()
      .withMessage("Price type is required"),
    check("pricing.*.price")
      .notEmpty()
      .withMessage("Price type is required"),
    (req, res, next) => {
      let errors = validationResult(req);
      if (!errors.isEmpty()) {
        return res.status(400).json({
          message: "Invalid parameters",
          stack: errors.array({ onlyFirstError: true }),
        });
      } else {
        next()
      }
    }
  ]
}

测试后返回错误:

"message": "Cannot convert object to primitive value"


问题原因

express-validator默认针对JSON格式请求体设计,form-data格式下嵌套对象数组的解析逻辑与JSON不同。check("pricing.*.ticketType")这类深层路径验证规则无法正确识别form-data中的嵌套结构,导致类型转换失败,抛出该错误。


解决方案

方案1:改用JSON格式发送请求

在Postman中切换为raw->JSON格式,按JSON结构构造请求体,示例:

{
  "name": "测试活动",
  "pricing": [
    {"ticketType": "普通票", "price": 99},
    {"ticketType": "VIP票", "price": 199}
  ]
}

此方式下原有验证逻辑可正常工作。

方案2:适配form-data调整验证逻辑

若必须使用form-data,需调整验证规则并确保应用正确解析form-data:

  1. 配置form-data解析器:使用multer解析form-data(无需存储文件)
    import multer from "multer";
    const upload = multer(); // 仅解析form-data,不处理文件上传
    // 在路由中使用
    app.post('/events', upload.none(), addEvent(), yourEventController);
    
  2. 修改验证函数:通过自定义验证遍历数组元素,检查字段完整性
    import { check, body } from "express-validator";
    import { validationResult } from "express-validator";
    
    export const addEvent = () => {
      return [
        check("name", "Name is required").notEmpty(),
        check("pricing").isArray().notEmpty().withMessage("Pricing must be an array"),
        // 自定义验证遍历每个pricing项
        body().custom((_, { req }) => {
          if (!req.body.pricing) return true;
          for (const item of req.body.pricing) {
            if (!item.ticketType) {
              throw new Error("每个定价项都需要填写票种");
            }
            if (!item.price) {
              throw new Error("每个定价项都需要填写价格");
            }
          }
          return true;
        }),
        (req, res, next) => {
          let errors = validationResult(req);
          if (!errors.isEmpty()) {
            return res.status(400).json({
              message: "Invalid parameters",
              stack: errors.array({ onlyFirstError: true }),
            });
          } else {
            next();
          }
        }
      ];
    };
    
    发送form-data时,需按pricing[0][ticketType]、pricing[0][price]、pricing[1][ticketType]这样的键名格式填写参数。

内容的提问来源于stack exchange,提问作者Lion Smith

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.13 23:25:11