reactjs - 通过下一个 js api 路由将文件上传到服务器

标签 reactjs typescript axios next.js multipartform-data

我在将请求传输到服务器之前使用 Next.js api 作为中间件,我正在尝试发送一个带有文件的 multipart/formdata 请求,如果我调用后端它会工作API 直接来自客户端的 FormData 对象,我编写了 Next API 来解析该表单数据,形成新的表单数据(这次是服务器端)并调用后端 API 但失败了。

代码如下:

import axios from "axios";
import formidable from "formidable";
import FormData from "form-data";
import type { NextApiRequest, NextApiResponse } from "next";
import { getSession } from "next-auth/react";
//
import BlogAPIs from "utils/apis/BlogAPIs";

export const config = {
  api: {
    bodyParser: false,
  },
};

export default async (req: NextApiRequest, res: NextApiResponse) => {
  try {
    const session = await getSession({ req });

    const formData = new FormData();

    const fs = require("fs");

    const data: { fields: any; files: any } = await new Promise(
      (resolve, reject) => {
        const form = new formidable.IncomingForm();

        form.parse(req, (err: any, fields: any, files: any) => {
          if (err) reject({ err });
          resolve({ fields, files });
        });
      }
    );

    ["title", "content", "description", "thumbnail"].map((key) => {
      data.fields[key] && formData.append(key, data.fields[key]);
      data.files[key] &&
        formData.append(key, fs.createReadStream(data.files[key].filepath));
    });

    let config = {
      method: "post",
      url: `${process.env.API_BASE_URL}/blogs/`,
      headers: {
        Authorization: `Bearer ${session?.backendToken as string}`,
        ...formData.getHeaders(),
      },
      data: formData,
    };

    await axios(config);

    res.status(200).json("Succesfully added blog");
  } catch (error: any) {
    res.status(700).json(error.message);
  }
};

我似乎无法弄清楚我在这里做错了什么......

最佳答案

我是这样实现的:

import axios from "axios";
import formidable from "formidable";
import type { NextApiRequest, NextApiResponse } from "next";
import { getSession } from "next-auth/react";
import { processError } from "utils/apis/processError";
//

export const config = {
  api: {
    bodyParser: false,
  },
};

export default async (req: NextApiRequest, res: NextApiResponse) => {
  try {
    const FormData = require("form-data");
    const concat = require("concat-stream");
    const fs = require("fs");

    const session = await getSession({ req });

    const data: { fields: any; files: any } = await new Promise(
      (resolve, reject) => {
        const form = new formidable.IncomingForm({
          keepExtensions: true,
        });

        form.parse(req, (err: any, fields: any, files: any) => {
          if (err) reject({ err });
          resolve({ fields, files });
        });
      }
    );

    const promise = new Promise<{ data: any; headers: any }>((resolve) => {
      const formData = new FormData();
      ["title", "content", "description", "tags"].map((key) => {
        data.fields[key] && formData.append(key, data.fields[key]);
      });

      data.files["thumbnail"] &&
        formData.append(
          "thumbnail",
          fs.createReadStream(data.files["thumbnail"].filepath),
          data.files["thumbnail"].originalFilename
        );

      formData.pipe(
        concat({ encoding: "buffer" }, (data: any) =>
          resolve({ data, headers: formData.getHeaders() })
        )
      );
    });

    promise
      .then(({ data, headers }) =>
        axios.post(`${process.env.API_BASE_URL}/blogs/`, data, {
          headers: {
            Authorization: `Bearer ${session?.backendToken as string}`,
            ...headers,
          },
        })
      )
      .catch((error) => {
        const errorMessage = processError(error);
        res.status(700).json(errorMessage);
      })
      .then((response) => {
        res.status(200).json({
          slug: response?.data.slug,
        });
      });
  } catch (error: any) {
    res.status(700).json(error.message);
  }
};

我用流数据创建了一个 promise ,然后将其发送到我的服务器。

关于reactjs - 通过下一个 js api 路由将文件上传到服务器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/72803910/

相关文章:

javascript - axios请求: promise error UnhandledPromiseRejectionWarning after catch anyway

javascript - 将 WebFontLoader 与 React Konva 一起使用会导致文本偏移吗?

javascript - Promise rejection 抛出警告,即使它稍后被捕获

typescript - 如何初始化{[ key : string]: string} to {} in TypeScript?

typescript - 您如何模拟 Apollo Server RESTDataSource 以使用 Jest 进行单元测试?

reactjs - Express/React 与 CORS - 为 React SPA 设置仅 HTTP 的安全 Cookie

reactjs - 如何为首次用户显示弹出窗口

javascript - React Context API - 获取更新的状态值

javascript - 如何在 react.js 中包含 pdf 链接

javascript - DELETE 后 GET 时 Firebase 返回空引用