前端代理工具

前端最普遍的就是遇到跨域,这个问题一般都会用node框架例如egg,express工具编写

下面就开始看看项目架构

最主要的文件是proxy.js

const express = require('express');
const axios = require('axios');
const cors = require('cors');
const multer = require('multer');
const path = require('path');
const FormData = require('form-data'); // 引入 form-data
const iconv = require('iconv-lite');
const fs = require('fs');
const app = express();
//前端项目端口
const port = 3010;

// 设置 multer 存储引擎
const upload = multer(); // 默认使用内存存储

// 配置 CORS
app.use(
  cors({
    origin: 'http://localhost:9528', // 替换为你的前端地址
    credentials: true, // 允许携带 Cookie
  })
);

// 解析 JSON 请求体
app.use(express.json());

// 解析 multipart/form-data 请求体
app.use(upload.any()); // 解析 multipart 数据,任何字段都可以处理

// 中转路由
app.all('/proxy/*', async (req, res) => {
  try {
    // 构造目标 URL  这是你要请求的接口路径
    // const targetUrl = '';

    // 请求方法和数据
    const { method, body, query, headers } = req;
    // 判断请求是否包含文件
    if (req.files && req.files.length > 0) {
      // 处理文件上传的请求
      const form = new FormData();
      req.files.forEach(file => {
        const decodedName = iconv.decode(Buffer.from(file.originalname, 'binary'), 'utf-8');
        // 如果仍有乱码,可以直接设置默认文件名,避免后续问题
        file.originalname = decodedName || 'unknown_file';
        form.append(file.fieldname, file.buffer, {
          filename: file.originalname,
          contentType: file.mimetype,
        });
      });

      // 如果请求体中有其他字段,添加到 form-data
      Object.keys(body).forEach(key => {
        form.append(key, body[key]);
      });

      // 获取 form-data 请求头
      const formHeaders = form.getHeaders();
      // 转发请求
      const response = await axios({
        url: targetUrl,
        method,
        headers: {
          ...formHeaders, // 添加 form-data 的 headers
          host: new URL(targetUrl).host, // 替换 Host 为目标主机
          cookie: headers.cookie || '', // 转发客户端传递的 Cookie
        },
        params: query, // GET 参数
        data: form, // 请求体,包含表单数据
        timeout: 50000, // 可选:设置超时时间
      });

      // 设置目标接口的 Cookie 到响应头
      if (response.headers['set-cookie']) {
        res.setHeader('set-cookie', response.headers['set-cookie']);
      }
      // 转发响应
      res.status(response.status).send(response.data);

    } else {
      // 处理普通的 JSON 请求
      const response = await axios({
        url: targetUrl,
        method,
        headers: {
          ...headers,
          host: new URL(targetUrl).host, // 替换 Host 为目标主机
          cookie: headers.cookie || '', // 转发客户端传递的 Cookie
        },
        params: query, // GET 参数
        data: body, // JSON 请求体
        timeout: 5000, // 可选:设置超时时间
      });

      // 设置目标接口的 Cookie 到响应头
      if (response.headers['set-cookie']) {
        res.setHeader('set-cookie', response.headers['set-cookie']);
      }

      // 转发响应
      res.status(response.status).send(response.data);
    }
  } catch (error) {
    console.error('Proxy error:', error.message);

    // 处理错误
    if (error.response) {
      res.status(error.response.status).send(error.response.data);
    } else {
      res.status(500).send({ error: 'Internal Server Error' });
    }
  }
});

// 静态资源
app.use(express.static(path.join(__dirname, 'public')));

// 启动服务
app.listen(port, () => {
  console.log(`Proxy server running at http://localhost:${port}`);
});

这样你前端项目就可以用http://localhost:3010/proxy/打开 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值