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

React前端向Node.js后端传递businessImages数组为空问题

React前端上传图片后,Node后端接收的businessImages数组为空的问题

我用React做前端、Node.js做后端开发时遇到一个问题:把vendor对象发送到后端后,后端打印的businessImages数组是空的,但前端打印该对象时,businessImages明明已经填充了内容。相关代码如下:

前端React代码

const handleSubmit = async (e) => {
  e.preventDefault();
  if (businessImages.length > 15) {
    alert("You've selected too many images for your business");
    setBusinessImages([]);
  } else {
    const formDataBusinessImages = new FormData();
    const formDataProfilePicture = new FormData();
    vendor = {
      name: name.current.value,
      email: email.current.value,
      mobileNumber: mobileNumber.current.value,
      businessAddress: businessAddress.current.value,
      mainService: selectedService,
      subServive: selectedSubService,
      businessImages: [],
      aboutBusiness: aboutBusiness.current.value,
      minPrice: minPrice.current.value,
      maxPrice: maxPrice.current.value,
      featured: featured,
    };
    formDataProfilePicture.append("file", profilePicture);
    formDataProfilePicture.append(
      "upload_preset",
      process.env.REACT_APP_CLOUDINARY_KEY
    );
    try {
      await axios
        .post(
          "https://api.cloudinary.com/v1_1/devign/image/upload",
          formDataProfilePicture
        )
        .then((res) => {
          console.log("Profile pic uploaded");
          vendor.profilePicture = res.data.secure_url;
        });
    } catch (err) {
      console.log(err);
    }
    businessImages.map(async (image) => {
      formDataBusinessImages.append("file", image);
      formDataBusinessImages.append("upload_preset", process.env.REACT_APP_CLOUDINARY_KEY);
      try {
        await axios
          .post(
            "https://api.cloudinary.com/v1_1/devign/image/upload",
            formDataBusinessImages
          )
          .then((res) => {
            vendor.businessImages.push(res.data.secure_url);
          });
      } catch (err) {
        console.log(err);
      }
    });

    handleUpload(vendor);
  }
};
const handleUpload = async (uploadData) => {
  try {
    await axios.post("/auth/register", uploadData);
  } catch (err) {
    console.log(err);
  }
};

后端Node.js代码

router.post("/register", async (req, res) => {
  const newVendor = new Vendor({
    name: req.body.name,
    email: req.body.email,
    mobileNumber: req.body.mobileNumber,
    businessAddress: req.body.businessAddress,
    mainService: req.body.mainService,
    subService: req.body.subService,
    profilePicture: req.body.profilePicture,
    businessImages: [],
    minPrice: req.body.minPrice,
    maxPrice: req.body.maxPrice,
    featured: req.body.featured,
  });
  try {
    newVendor.businessImages.push(req.body.businessImages);
    console.log(req.body.businessImages, req.body.profilePicture);
    const vendor = await newVendor.save();
    res.status(200).json("Successfully registered");
  } catch (err) {
    console.log(err);
  }
});

问题原因

  1. 异步操作未等待完成:businessImages.map中的异步上传请求还没执行完,handleUpload(vendor)就已经被调用,此时vendor.businessImages还没被填充。map不会等待异步回调完成,直接继续执行后续代码。
  2. 后端赋值错误:newVendor.businessImages.push(req.body.businessImages)会把整个数组作为单个元素推入,即使前端传了正确数组,后端存储的也是嵌套数组。

修复方案

前端代码修改

用Promise.all等待所有图片上传完成后再发送请求,同时避免复用FormData导致的请求异常:

const handleSubmit = async (e) => {
  e.preventDefault();
  if (businessImages.length > 15) {
    alert("You've selected too many images for your business");
    setBusinessImages([]);
    return;
  }

  let vendor = {
    name: name.current.value,
    email: email.current.value,
    mobileNumber: mobileNumber.current.value,
    businessAddress: businessAddress.current.value,
    mainService: selectedService,
    subServive: selectedSubService,
    businessImages: [],
    aboutBusiness: aboutBusiness.current.value,
    minPrice: minPrice.current.value,
    maxPrice: maxPrice.current.value,
    featured: featured,
  };

  // 上传头像
  const formDataProfilePicture = new FormData();
  formDataProfilePicture.append("file", profilePicture);
  formDataProfilePicture.append("upload_preset", process.env.REACT_APP_CLOUDINARY_KEY);
  try {
    const profileRes = await axios.post(
      "https://api.cloudinary.com/v1_1/devign/image/upload",
      formDataProfilePicture
    );
    vendor.profilePicture = profileRes.data.secure_url;
  } catch (err) {
    console.log(err);
  }

  // 批量上传业务图片,用Promise.all等待全部完成
  const imageUploadTasks = businessImages.map(async (image) => {
    const formData = new FormData();
    formData.append("file", image);
    formData.append("upload_preset", process.env.REACT_APP_CLOUDINARY_KEY);
    try {
      const res = await axios.post(
        "https://api.cloudinary.com/v1_1/devign/image/upload",
        formData
      );
      return res.data.secure_url;
    } catch (err) {
      console.log(err);
      return null;
    }
  });

  // 收集所有上传成功的图片URL
  const uploadedUrls = await Promise.all(imageUploadTasks);
  vendor.businessImages = uploadedUrls.filter(url => url !== null);

  // 确保所有图片上传完成后,再发送到后端
  await handleUpload(vendor);
};

const handleUpload = async (uploadData) => {
  try {
    await axios.post("/auth/register", uploadData);
  } catch (err) {
    console.log(err);
  }
};

后端代码修改

直接赋值businessImages,避免错误的push操作:

router.post("/register", async (req, res) => {
  try {
    const newVendor = new Vendor({
      name: req.body.name,
      email: req.body.email,
      mobileNumber: req.body.mobileNumber,
      businessAddress: req.body.businessAddress,
      mainService: req.body.mainService,
      subService: req.body.subService,
      profilePicture: req.body.profilePicture,
      businessImages: req.body.businessImages || [],
      minPrice: req.body.minPrice,
      maxPrice: req.body.maxPrice,
      featured: req.body.featured,
    });

    console.log(req.body.businessImages, req.body.profilePicture);
    const vendor = await newVendor.save();
    res.status(200).json("Successfully registered");
  } catch (err) {
    console.log(err);
    res.status(500).json("Registration failed");
  }
});

内容的提问来源于stack exchange,提问作者Curran-C

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.25 15:27:19