使用Axios连接前后端与MongoDB时遇404错误,数据无法存储
404错误排查:Axios连接前后端失败无法存储数据到MongoDB
我尝试使用Axios模块连接server.js后端与App.jsx前端,期望将数据保存至MongoDB文档,但未成功,反而出现以下404错误:
Error fetching data: AxiosError {message: 'Request failed with status code 404', name: 'AxiosError', code: 'ERR_BAD_REQUEST', config: {…}, request: XMLHttpRequest, …} code : "ERR_BAD_REQUEST"
后端server.js代码
const express = require('express'); const bodyParser = require('body-parser'); const mongoose = require('mongoose'); const cors = require('cors'); const app = express(); const PORT = 3001; app.use(cors()); app.use(bodyParser.json()); app.use(bodyParser.urlencoded({ extended: true })); mongoose.connect('mongodb://localhost:27017/yourDB', { useNewUrlParser: true, useUnifiedTopology: true }) .then(() => { console.log('Connected to MongoDB'); }) .catch((error) => { console.error('Error connecting to MongoDB:', error); }); const postSchema = mongoose.Schema({ title: String, content: String }); const Post = mongoose.model('Post', postSchema); // API endpoint for fetching data app.get("/api/posts", (req, res) => { Post.find({}, (err, posts) => { if (err) { console.error('Error fetching posts:', err); res.status(500).json({ error: 'Internal server error' }); } else { res.json(posts); } }); }); // API endpoint for creating new data app.post("/api/posts", (req, res) => { const { title, content } = req.body; const newPost = new Post({ title, content }); newPost.save((err, savedPost) => { if (err) { console.error('Error saving post:', err); res.status(500).json({ error: 'Internal server error' }); } else { res.json(savedPost); } }); }); // API endpoint for deleting data app.delete("/api/posts/:id", (req, res) => { const { id } = req.params; Post.findByIdAndDelete(id, (err) => { if (err) { console.error('Error deleting post:', err); res.status(500).json({ error: 'Internal server error' }); } else { res.json({ message: 'Post deleted successfully' }); } }); }); // Start the server app.listen(PORT, () => { console.log(`Server started on port ${PORT}`); });
前端App.jsx代码
import React, { useEffect, useState } from "react"; import axios from "axios"; import Header from "./Header"; import Footer from "./Footer"; import Note from "./Note"; import CreateArea from "./CreateArea"; function App() { const [notes, setNotes] = useState([]); useEffect(() => { axios.get("/api/posts") .then(response => { setNotes(response.data); }) .catch(error => { console.error('Error fetching data:', error); }); }, []); function addNote(note) { setNotes(prevNotes => { return [...prevNotes, note]; }); axios.post("/api/posts", note) .then(response => { console.log("Post saved successfully:", response.data); }) .catch(error => { console.error("Error saving post:", error); }); } function deleteNote(id) { setNotes(prevNotes => { return prevNotes.filter((noteItem, index) => { return index !== id; }); }); axios.delete(`/api/posts/${id}`) } return ( <div> <Header /> <CreateArea onAdd={addNote} /> {notes.map((noteItem, index) => ( <Note key={index} id={index} title={noteItem.title} content={noteItem.content} onDelete={deleteNote} /> ))} <Footer /> </div> ); } export default App;
错误原因分析
- 请求路径未指向后端服务:前端Axios使用相对路径
/api/posts,但前端默认运行端口(通常是3000)与后端的3001端口不同,相对路径会请求前端所在端口的接口,导致找不到后端路由,返回404。 - 删除功能ID不匹配:前端删除时传递的是数组索引
id,但后端findByIdAndDelete需要的是MongoDB生成的_id字段,不仅会导致删除接口无效,还可能因索引不是合法ObjectId触发错误。 - 删除请求未处理错误:前端
deleteNote中的Axios删除请求缺少.catch逻辑,无法捕获和排查删除时的异常。 - 状态更新逻辑不一致:前端添加笔记时先更新本地状态再发送请求,若请求失败会导致本地状态与后端数据不同步。
解决方法
1. 修正请求路径,指向后端服务
有三种方式可选:
- 开发环境代理配置:在前端项目的
package.json中添加代理,自动转发请求到后端:"proxy": "http://localhost:3001" - 指定完整请求地址:修改Axios请求的URL为后端完整地址:
axios.get("http://localhost:3001/api/posts") - 全局配置Axios基础URL:在App.jsx开头添加全局配置,后续请求自动拼接基础地址:
axios.defaults.baseURL = 'http://localhost:3001';
2. 修复删除功能的ID逻辑
- 更新
useEffect,直接存储后端返回的带_id的完整数据:useEffect(() => { axios.get("/api/posts") .then(response => { setNotes(response.data); }) .catch(error => { console.error('Error fetching data:', error); }); }, []); - 渲染
Note组件时传递MongoDB的_id而非数组索引:{notes.map((noteItem) => ( <Note key={noteItem._id} id={noteItem._id} title={noteItem.title} content={noteItem.content} onDelete={deleteNote} /> ))} - 修改
deleteNote函数,用_id过滤状态并添加错误处理:function deleteNote(postId) { setNotes(prevNotes => { return prevNotes.filter(noteItem => noteItem._id !== postId); }); axios.delete(`/api/posts/${postId}`) .then(response => { console.log("Post deleted successfully:", response.data); }) .catch(error => { console.error("Error deleting post:", error); }); }
3. 同步添加笔记的状态更新逻辑
等后端请求成功后,用返回的带_id的数据更新本地状态,确保前后端数据一致:
function addNote(note) { axios.post("/api/posts", note) .then(response => { console.log("Post saved successfully:", response.data); setNotes(prevNotes => [...prevNotes, response.data]); }) .catch(error => { console.error("Error saving post:", error); }); }
内容的提问来源于stack exchange,提问作者Vishal Pilli
相关产品推荐
相关产品推荐

