React Router 6教程中调用MirageJS接口遇JSON解析错误求助
React + MirageJS 请求返回HTML而非JSON的错误排查
问题描述
我在学习Scrimba的React与React Router 6教程时,复制教程代码后遇到数据请求错误。错误信息为:67:1 Uncaught (in promise) SyntaxError: Unexpected token '<', "<!DOCTYPE "... is not valid JSON
触发位置在Vans.jsx的第9行.then(data => setVans(data.vans))处。
Vans.jsx 代码
import React from 'react' import { Link } from 'react-router-dom' export default function Vans() { const [vans, setVans] = React.useState([]) React.useEffect(() => { fetch("/api/vans") .then(res => res.json()) .then(data => setVans(data.vans)) }, []) const vanElements = vans.map(van => ( <div key={van.id} className="van-tile"> <Link to={`/vans/${van.id}`}> <img src={van.imageUrl} /> <div className="van-info"> <h3>{van.name}</h3> <p>${van.price}<span>/day</span></p> </div> <i className={`van-type ${van.type} selected`}>{van.type}</i> </Link> </div> )) return ( <div className="van-list-container"> <h1>Explore our van options</h1> <div className="van-list"> {vanElements} </div> </div> ) }
server.js(MirageJS模拟接口)代码
import { createServer, Model } from "miragejs" createServer({ models: { vans: Model, }, seeds(server) { server.create("van", { id: "1", name: "Modest Explorer", price: 60, description: "The Modest Explorer is a van designed to get you out of the house and into nature. This beauty is equipped with solar panels, a composting toilet, a water tank and kitchenette. The idea is that you can pack up your home and escape for a weekend or even longer!", imageUrl: "https://assets.scrimba.com/advanced-react/react-router/modest-explorer.png", type: "simple" }) server.create("van", { id: "2", name: "Beach Bum", price: 80, description: "Beach Bum is a van inspired by surfers and travelers. It was created to be a portable home away from home, but with some cool features in it you won't find in an ordinary camper.", imageUrl: "https://assets.scrimba.com/advanced-react/react-router/beach-bum.png", type: "rugged" }) server.create("van", { id: "3", name: "Reliable Red", price: 100, description: "Reliable Red is a van that was made for travelling. The inside is comfortable and cozy, with plenty of space to stretch out in. There's a small kitchen, so you can cook if you need to. You'll feel like home as soon as you step out of it.", imageUrl: "https://assets.scrimba.com/advanced-react/react-router/reliable-red.png", type: "luxury" }) server.create("van", { id: "4", name: "Dreamfinder", price: 65, description: "Dreamfinder is the perfect van to travel in and experience. With a ceiling height of 2.1m, you can stand up in this van and there is great head room. The floor is a beautiful glass-reinforced plastic (GRP) which is easy to clean and very hard wearing. A large rear window and large side windows make it really light inside and keep it well ventilated.", imageUrl: "https://assets.scrimba.com/advanced-react/react-router/dreamfinder.png", type: "simple" }) server.create("van", { id: "5", name: "The Cruiser", price: 120, description: "The Cruiser is a van for those who love to travel in comfort and luxury. With its many windows, spacious interior and ample storage space, the Cruiser offers a beautiful view wherever you go.", imageUrl: "https://assets.scrimba.com/advanced-react/react-router/the-cruiser.png", type: "luxury" }) server.create("van", { id: "6", name: "Green Wonder", price: 70, description: "With this van, you can take your travel life to the next level. The Green Wonder is a sustainable vehicle that's perfect for people who are looking for a stylish, eco-friendly mode of transport that can go anywhere.", imageUrl: "https://assets.scrimba.com/advanced-react/react-router/green-wonder.png", type: "rugged" }) }, routes() { this.namespace = "api" this.get("/vans", (schema, request) => { return schema.vans.all() }) this.get("/vans/:id", (schema, request) => { const id = request.params.id return schema.vans.find(id) }) } })
问题原因与解决方案
这个错误的核心是:fetch("/api/vans")返回的不是预期的JSON数据,而是HTML页面(通常是404错误页面的<!DOCTYPE>内容),说明MirageJS的模拟接口没有拦截到请求,或者根本没启动。
1. 最可能的原因:server.js未被项目入口文件引入
MirageJS需要在应用启动时初始化,必须在React项目的入口文件(比如index.js、main.jsx或App.jsx)中导入server.js,否则MirageJS的模拟服务器不会启动,请求会直接发送到开发服务器,返回404的HTML页面。
解决办法:
在你的项目入口文件顶部添加导入语句:
import './server.js'
确保路径和server.js的实际位置匹配。
2. 额外验证与调试步骤
如果导入后问题仍存在,可以在fetch请求中添加调试代码,确认响应内容:
React.useEffect(() => { fetch("/api/vans") .then(res => { console.log("响应状态:", res.status) // 先获取文本内容,确认是HTML还是JSON return res.text() }) .then(text => { console.log("响应内容:", text) try { const data = JSON.parse(text) setVans(data.vans) } catch (err) { console.error("解析JSON失败:", err) } }) .catch(err => console.error("请求错误:", err)) }, [])
通过控制台输出可以明确看到返回的是HTML还是JSON,进一步定位问题。
3. 其他可能的小问题
- 检查server.js中的
this.namespace = "api"是否和请求路径/api/vans匹配(你的代码中这部分是正确的)。 - 确认MirageJS已正确安装:执行
npm install miragejs或yarn add miragejs确保依赖存在。
内容的提问来源于stack exchange,提问作者Vicente Antonio G. Reyes
相关产品推荐
相关产品推荐

