ReactJS中Fetch请求遭CORS拦截问题求助(附代码)
React + Node.js 跨域(CORS)问题排查与解决
问题概述
开发ReactJS(运行在3001端口)+ NodeJS(运行在3000端口)应用,数据库连接正常,直接访问后端/infos接口可返回数据,但前端请求该接口时触发CORS拦截错误。已配置cors中间件指定origin为http://localhost:3001,但问题未解决。
错误信息
Access to fetch at 'http://localhost:3000/infos' from origin 'http://localhost:3001' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.
现有代码
服务端 server.js
const express = require("express"); const bodyParser = require("body-parser"); const cors = require("cors"); const { connectToDB, closeDB } = require("./db_connect"); const app = express(); const port = 3000; app.use(bodyParser.json()); app.use(cors({ origin: "http://localhost:3001", })); app.get("/infos", async (req, res) => { try { const pool = await connectToDB(); const result = await pool.request().query("SELECT * FROM Information"); res.json(result.recordset); } catch (err) { console.error("Error fetching information:", err); res.status(500).json({ error: "Server error" }); } }); process.on("SIGINT", async () => { try { await closeDB(); process.exit(0); } catch (err) { console.error("Error closing the database connection:", err); process.exit(1); } }); app.listen(port, () => { console.log(`Server listening on port ${port}`); });
前端 App.js
import logo from './logo.svg'; import './App.css'; import React, { useState, useEffect } from "react"; function App() { const [info, setInfos] = useState([]); useEffect(() => { fetch("http://localhost:3000/infos") .then((response) => response.json()) .then((data) => setInfos(data)) .catch((error) => console.error("Error fetching data:", error)); }, []); return ( <div> <h1>Information</h1> <ul> {infos.map((info) => ( <li key={info.id}> {info.firstName} {info.lastName} - No.: {info.Number} </li> ))} </ul> </div> ); } export default App;
解决步骤
1. 先修复前端状态变量笔误
前端代码中状态变量定义为const [info, setInfos] = useState([]),但渲染时使用的是infos.map,变量名不匹配会导致数据无法正常展示。修正为:
const [infos, setInfos] = useState([]);
2. 排查CORS配置问题
方案一:验证CORS中间件配置有效性
先简化配置,允许所有origin测试是否生效:
// 替换原cors配置 app.use(cors());
如果测试有效,再锁定指定origin并补充必要配置:
app.use(cors({ origin: "http://localhost:3001", credentials: true, // 前端带Cookie时需开启,否则可省略 allowedHeaders: ["Content-Type"], methods: ["GET", "POST", "OPTIONS"] }));
方案二:手动添加CORS响应头(绕过cors包)
若cors包配置无效,可在路由中手动设置响应头,同时处理浏览器的OPTIONS预检请求:
// 全局处理OPTIONS预检请求 app.options("*", (req, res) => { res.setHeader("Access-Control-Allow-Origin", "http://localhost:3001"); res.setHeader("Access-Control-Allow-Methods", "GET, POST, OPTIONS"); res.setHeader("Access-Control-Allow-Headers", "Content-Type"); res.sendStatus(200); }); // 在接口中添加CORS头 app.get("/infos", async (req, res) => { res.setHeader("Access-Control-Allow-Origin", "http://localhost:3001"); try { const pool = await connectToDB(); const result = await pool.request().query("SELECT * FROM Information"); res.json(result.recordset); } catch (err) { console.error("Error fetching information:", err); res.status(500).json({ error: "Server error" }); } });
方案三:检查origin匹配性
确认前端运行地址确实是http://localhost:3001,CORS对域名/IP严格区分,localhost和127.0.0.1属于不同origin,不能混用。
方案四:开发环境使用代理
在React项目的package.json中添加代理配置,避免跨域:
{ "proxy": "http://localhost:3000" }
修改前端请求为相对路径:
fetch("/infos")
此方式仅适用于开发环境,生产环境需部署在同一域名下或配置反向代理。
3. 验证配置
修改后重启Node服务和React应用,打开浏览器控制台查看/infos请求的响应头,若包含Access-Control-Allow-Origin: http://localhost:3001,则CORS配置生效。
内容的提问来源于stack exchange,提问作者unknown techh
相关产品推荐
相关产品推荐

