如何解决POST http://localhost:8000/comment/saveComment 404未找到
新来的反应。我正在使用带有 express mongoose 和 node js 的 mern 堆栈。我正在尝试为 youtube 克隆创建评论功能,并且我一直在关注 youtube 视频,但由于某种原因我无法让它工作。我不知道是路由有问题,是 post axios 方法还是模型。 这是 post.js
import { Avatar,IconButton } from "@material-ui/core";
import FavoriteIcon from "@material-ui/icons/Favorite";
import SmsIcon from "@material-ui/icons/Sms";
import SpaIcon from "@material-ui/icons/Spa";
import React,{ useRef,useState,useEffect } from "react";
import minime from "../images/me.jpg";
import vid from "../videos/ed.MP4";
import GpsFixedIcon from "@material-ui/icons/GpsFixed";
import FormatListBulletedIcon from "@material-ui/icons/FormatListBulleted";
import GamepadIcon from "@material-ui/icons/Gamepad";
import "../styles/Post.css";
import EmojiEmotionsIcon from "@material-ui/icons/EmojiEmotions";
import VideoModal from "./VideoModal";
import PostMotivationModal from "../components/modals/PostMotivationModal";
import PostHappinessModal from "../components/modals/PostHappinessModal";
import Comments from "./post/Comments";
import axios from "../axios";
const Post = ({
avatar,name,caption,filePath,motivation,goals,happiness,}) => {
const [isOpen,setIsOpen] = useState(false);
const [motivationIsOpen,setMotivationIsOpen] = useState(false);
const [happinessIsOpen,setHappinessIsOpen] = useState(false);
const [playing,setPlaying] = useState(false);
const vidRef = useRef(null);
const [commentList,setCommentList] = useState([]);
const handleVideoPress = () => {
//If video is playing... stop it
if (playing) {
vidRef.current.pause();
setPlaying(false);
} else {
vidRef.current.play();
setPlaying(true);
}
//otherwise... play it
};
const [videos,setVideos] = useState([]);
const [vid,setVid] = useState([]);
useEffect(() => {
async function fetchPosts() {
const res = await axios.get("video/getVideos");
setVideos(res.data.videos);
let video = res.data.videos.find((video) => video._id);
console.log(video);
setVid(video);
return res;
}
fetchPosts();
},[]);
// useEffect(() => {
// async function fetchPosts() {
// const res = await axios.get("video/getVideo");
// setVid(res.data.video);
// let video = res.data.videos.find((video) => video._id);
// console.log(video);
// setVid(video);
// return res;
// }
// fetchPosts();
// },[]);
const videoId = vid._id;
const variable = {
videoId: videoId,};
// useEffect(() => {
// axios.post("/video/getVideo",variable).then((response) => {
// console.log(response.data);
// if (response.data.success) {
// setVid(response.data.video);
// } else {
// console.log(response.data);
// alert("Failed to get video Info");
// }
// });
// },[]);
const updateComment = (newComment) => {
setCommentList(commentList.push(newComment));
};
return (
<div className="post">
<div className="post-head">
<div className="post-header">
<Avatar src={avatar} />
<h3>{name}</h3>
</div>
<div className="caption">
<p>{caption}</p>
</div>
</div>
<div className="video-container">
<div className="flex-container">
<div className="video-card">
<video
ratiowidth="calc(0.56 * (400px + (100vw - 768px) / 1152 * 100))"
ratioheight="calc(400px + (100vw - 768px) / 1152 * 100)"
musicinfomaxwidth="250.56"
style={{
width: "calc(0.56 * (400px + ((100vw - 768px) / 1152) * 100))",}}
loop
onClick={handleVideoPress}
ref={vidRef}
src={`http://localhost:8000/${filePath}`}
></video>
<div className="post__personalItems">
<div title="Goals" className="personalIcon">
<GpsFixedIcon
onClick={() => setIsOpen(true)}
style={{ cursor: "pointer" }}
/>
</div>
<div title="Motivation" className="personalIcon">
<GamepadIcon
onClick={() => setMotivationIsOpen(true)}
style={{ cursor: "pointer" }}
/>
</div>
<div title="Happiness" className="personalIcon">
<EmojiEmotionsIcon
onClick={() => setHappinessIsOpen(true)}
style={{ cursor: "pointer" }}
/>
</div>
</div>
<VideoModal
open={isOpen}
onClose={() => setIsOpen(false)}
goals={goals}
></VideoModal>
<PostMotivationModal
open={motivationIsOpen}
onClose={() => setMotivationIsOpen(false)}
motivation={motivation}
></PostMotivationModal>
<PostHappinessModal
open={happinessIsOpen}
onClose={() => setHappinessIsOpen(false)}
happiness={happiness}
></PostHappinessModal>
</div>
<div className="post-icons">
<div className="post-icon" title="like">
<IconButton>
<FavoriteIcon />
</IconButton>
<div className="icon-detail">
<p>112</p>
</div>
</div>
<div className="post-icon" title="hug">
<IconButton>
<SpaIcon />
</IconButton>
<div className="icon-detail">
<p>300</p>
</div>
</div>
<div className="post-icon" title="comment">
<IconButton>
<SmsIcon />
</IconButton>
<div className="icon-detail">
<p>30</p>
</div>
</div>
</div>
</div>
</div>
<Comments
commentList={commentList}
postId={videoId}
refreshFunction={updateComment}
/>
</div>
);
};
export default Post;
这里是comment.js
import React,{ useState } from "react";
import { Input } from "antd";
import "../../styles/Comments.css";
import axios from "../../axios";
const { TextArea } = Input;
const Comments = (props) => {
const [user,setUser] = useState(JSON.parse(localStorage.getItem("profile")));
const [submitOn,setSubmitOn] = useState(false);
const [comment,setComment] = useState("");
const btnSwap = () => {
if (submitOn === false) {
setSubmitOn(true);
}
};
const handleChange = (e) => {
setComment(e.currentTarget.value);
};
// console.log(user?.result.googleId);
// console.log(props);
const onSubmit = (e) => {
e.preventDefault();
const variables = {
content: comment,name: user?.result.name,avatar: user?.result.imageUrl,postId: props.postId,};
axios.post("/comment/saveComment",variables).then((res) => {
if (res.data.success) {
setComment("");
props.refreshFunction(res.data.result);
} else {
alert("Failed to save comment");
}
});
};
return (
<div className="comments-section">
<p className="replies-txt">Replies</p>
<hr />
{/*Comment Lists */}
{console.log(props.commentList)}
{/* Root comment form */}
<form className="comment-form1" onSubmit={onSubmit}>
<input
className="txtarea-comments"
style={{ width: "100%" }}
onChange={handleChange}
value={comment}
placeholder="Type your comments here..."
onClick={btnSwap}
/>
<div className="comment-submit-div">
<button
className={submitOn ? "txt-true" : "comment-submit-btn"}
onClick={onSubmit}
>
Submit
</button>
</div>
</form>
</div>
);
};
export default Comments;
这里是模型/comment.js
import mongoose from "mongoose";
const Schema = mongoose.Schema;
const commentSchema = mongoose.Schema(
{
name: { type: String },avatar: { type: String },postId: { type: String },responseto: { type: String },content: {
type: String,},{ timestamps: true }
);
export default mongoose.model("Comment",commentSchema);
这里是评论路由器
import express from "express";
import Comment from "../models/Comment.js";
const router = express.Router();
router.post("/saveComment",(req,res) => {
const comment = new Comment(req.body);
comment.save((err,comment) => {
if (err) return res.json({ success: false,err });
Comment.find({ _id: comment._id })
.populate("name","avatar")
.exec((err,result) => {
if (err) return res.json({ success: false,err });
return res.status(200).json({ success: true,result });
});
});
});
export default router;
这是视频路由器
import express from "express";
import multer from "multer";
import Upload from "../models/Upload.js";
const router = express.Router();
var storage = multer.diskStorage({
destination: (req,file,cb) => {
cb(null,"uploads/");
},filename: (req,`${Date.Now()}_${file.originalname}`);
},fileFilter: (req,cb) => {
const ext = path.extname(file.originalname);
if (ext !== ".mp4") {
return cb(res.status(400).end("only video format is allowed"),false);
}
cb(null,true);
},});
let upload = multer({ storage: storage }).single("file");
//=================================
// Video
//=================================
router.post("/uploadfiles",res) => {
upload(req,res,(err) => {
if (err) {
return res.json({ success: false,err });
}
return res.json({
success: true,filePath: res.req.file.path,fileName: res.req.file.filename,});
});
});
router.post("/uploadVideo",res) => {
const video = new Upload(req.body);
video.save((err,video) => {
if (err) return res.status(400).json({ success: false,err });
return res.status(200).json({
success: true,});
});
});
router.get("/getVideos",res) => {
Upload.find()
.sort({ createdAt: -1 })
.exec((err,videos) => {
if (err) return res.status(400).send(err);
res.status(200).json({ success: true,videos });
});
});
router.post("/getVideo",res) => {
Upload.findOne({ _id: req.body.videoId })
.populate("name","avatar")
.exec((err,video) => {
if (err) return res.status(400).send(err);
res.status(200).json({ success: true,video });
});
});
export default router;
这里是 server.js
import express from "express";
import mongoose from "mongoose";
import cors from "cors";
import data from "./data.js";
import Videos from "./dbModel.js";
import postRoutes from "./routes/posts.js";
import userRouter from "./routes/user.js";
import commentRouter from "./routes/comment.js";
import uploadRouter from "./routes/upload.js";
const app = express();
const port = process.env.PORT || 8000;
//Middlewares
app.use(express.json());
app.use(cors());
app.use("/posts",postRoutes);
app.use("/user",userRouter);
app.use("/video",uploadRouter);
app.use("/uploads",express.static("uploads"));
if (process.env.NODE_ENV === "production") {
// Set static folder
app.use(express.static("client/build"));
// index.html for all page routes
app.get("*",res) => {
res.sendFile(path.resolve(__dirname,"client","build","index.html"));
});
}
app.use("/comment",commentRouter);
//db config
const CONNECTION_URL =
"mongodb+srv://dimerson:9zRHuVcHLh5fSznu@cluster0.5n5rb.mongodb.net/KweebleDatabase?retryWrites=true&w=majority";
mongoose.connect(CONNECTION_URL,{
useNewUrlParser: true,useCreateIndex: true,useUnifiedTopology: true,});
app.get("/",res) => res.status(200).send("hello world"));
app.get("/v1/posts",res) => res.status(200).send(data));
app.post("/v2/posts",res) => {
const dbVideos = req.body;
Videos.create(dbVideos,(err,data) => {
if (err) {
res.status(500).send(err);
} else {
res.status(201).send(data);
}
});
});
app.get("/v2/posts",res) => {
Videos.find((err,data) => {
if (err) {
res.status(500).send(err);
} else {
res.status(200).send(data);
}
});
});
app.listen(port,() => console.log(`listening on localhost:${port}`));
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。