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

React网页爬虫遇CORS跨域问题,如何配置通用代理解决?

React网页爬虫的CORS跨域与代理配置问题

我正在开发一款基于React的网页爬虫程序,支持用户输入URL后抓取页面的标题与作者信息,但目前遭遇了CORS跨域限制问题。

我曾针对特定URL配置过代理并生效,但该程序需要适配大量存在CORS限制的URL,例如tistory这类站点(域名前缀为博客名称,后缀为平台域名)。我尝试编写了如下代理配置,但并未生效:

const { createProxyMiddleware } = require('http-proxy-middleware');

module.exports = function(app){
  app.use(
    createProxyMiddleware('tistory/', {
      target: 'tistory.com/',
      pathRewrite: {
        'tistory/^':''
      },
      changeOrigin: true
    })
  )

};

直接请求目标URL的核心代码如下:

//let firstTestURL = "https://blog.naver.com/mayoha/223015532241";
//let testURLonProxy = "naver/siji5000/223015377877";

let testURL = "https://peursen.tistory.com/270";

axios.get(testURL)
.then((response) =>{
    let body = response.data;
    const $ = cheerio.load(body);

    let theURLtitle = $("title").text();
    console.log(theURLtitle);
})
.catch(err =>{
    console.log(err);
})

修正代理配置

原配置存在三个核心问题:target缺少协议头、匹配规则无法适配子域名场景、pathRewrite正则写法错误。以下是修正后的配置,支持tistory这类带动态子域名的站点:

const { createProxyMiddleware } = require('http-proxy-middleware');

module.exports = function(app){
  // 处理tistory类站点的代理
  app.use(
    createProxyMiddleware('/tistory/**', {
      target: 'https://tistory.com',
      pathRewrite: {
        '^/tistory/': '' // 移除路径开头的/tistory/前缀
      },
      changeOrigin: true,
      // 动态匹配子域名
      router: function(req) {
        // 从请求路径中提取子域名部分,比如peursen
        const subdomain = req.path.split('/')[2];
        return `https://${subdomain}.tistory.com`;
      }
    })
  );

  // 可扩展添加naver博客的代理规则
  app.use(
    createProxyMiddleware('/naver/**', {
      target: 'https://blog.naver.com',
      pathRewrite: {
        '^/naver/': ''
      },
      changeOrigin: true,
      router: function(req) {
        const blogId = req.path.split('/')[2];
        return `https://blog.naver.com/${blogId}`;
      }
    })
  );
};

修改后,前端请求需要调整为代理路径,比如原URL https://peursen.tistory.com/270 要改为 /tistory/peursen/270:

// 替换为代理路径
let proxyURL = "/tistory/peursen/270";

axios.get(proxyURL)
.then((response) =>{
    let body = response.data;
    const $ = cheerio.load(body);

    let theURLtitle = $("title").text();
    console.log(theURLtitle);
})
.catch(err =>{
    console.log(err);
})

其他可行的跨CORS解决方案

自建后端API中转(推荐生产环境使用)

浏览器的CORS限制仅针对前端请求,后端服务不受此限制。可以搭建一个简单的后端接口,由后端负责抓取目标页面内容,再返回给前端。示例代码如下:

后端(Express):

const express = require('express');
const axios = require('axios');
const cheerio = require('cheerio');
const cors = require('cors');
const app = express();

app.use(cors());
app.use(express.json());

app.get('/fetch-page', async (req, res) => {
  const targetURL = req.query.url;
  if (!targetURL) {
    return res.status(400).json({ error: '缺少目标URL参数' });
  }

  try {
    const response = await axios.get(targetURL);
    const $ = cheerio.load(response.data);
    const title = $("title").text();
    // 可扩展提取作者信息,需根据不同站点的DOM结构适配
    res.json({ title });
  } catch (err) {
    res.status(500).json({ error: `抓取失败:${err.message}` });
  }
});

app.listen(3001, () => console.log('后端服务运行在端口3001'));

前端请求:

let testURL = "https://peursen.tistory.com/270";

axios.get('http://localhost:3001/fetch-page', { params: { url: testURL } })
.then((response) =>{
    console.log('页面标题:', response.data.title);
})
.catch(err =>{
    console.log(err);
})

开发阶段临时方案:公开CORS代理

开发时可以使用公开的CORS代理服务,但存在数据安全风险,不适合生产环境。使用时只需在目标URL前添加代理前缀即可:

let proxyPrefix = "https://cors-anywhere.herokuapp.com/";
let testURL = proxyPrefix + "https://peursen.tistory.com/270";

axios.get(testURL)
// ...后续逻辑不变

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.31 20:25:16