![](/img/trans.png)
[英]POST http://localhost:3000/api/auth/register 404 (Not Found)
[英]Error "POST http://localhost:3000/api/auth/createuser (same with /api/auth/login path) 404 (Not Found)" & "Uncaught in Promise: Syntax Error"
无法解决错误。 所有方法都设置正确,但仍然出现“无法发布”和未捕获(承诺中)的错误 SyntaxError: Unexpected token '<', "<.DOCTYPE"... is not valid JSON。 在服务器端和客户端都找不到我的 POST 或 GET 请求中的问题? 请通过查看以下代码提出解决方案?
另请注意:错误导致登录/注册用户出现问题。 API 在后端运行良好。 好像是前端的问题。
SignUp.js 文件:
import React, { useState } from "react";
import { useNavigate } from "react-router-dom";
export const SignUp = (props) => {
const host = "http://localhost:3000";
let navigate = useNavigate();
const [credentials, setCredentials] = useState({
name: "",
email: "",
password: "",
cpasswortd: "",
});
const handleSubmit = async (e) => {
e.preventDefault();
const { name, email, password } = credentials;
const response = await fetch(`${host}/api/auth/createuser`, {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
name,
email,
password,
}),
});
const json = await response.json();
console.log(json);
if(json.success){
// Save the auth token and redirect
localStorage.setItem("token", json.authtoken);
navigate("/login");
props.showAlert("Account created successfully" , "success")
} else {
props.showAlert("Invalid Details" , "danger")
}
};
const onChange = (e) => {
setCredentials({ ...credentials, [e.target.name]: e.target.value });
};
return (
<>
<section className="vh-100" style={{ backgroundColor: "white" }}>
<div className="container h-100">
<div className="row d-flex justify-content-center align-items-center h-100">
<div className="col-lg-12 col-xl-11">
<div className="card text-black" style={{ borderRadius: "25px" }}>
<div className="card-body p-md-5">
<div className="row justify-content-center">
<div className="col-md-10 col-lg-6 col-xl-5 order-2 order-lg-1">
<p className="text-center h1 fw-bold mb-5 mx-1 mx-md-4 mt-4">
Sign up
</p>
<form onSubmit={handleSubmit} className="mx-1 mx-md-4">
<div className="d-flex flex-row align-items-center mb-4">
<div className="form-outline flex-fill mb-0">
<input
type="text"
id="name"
onChange={onChange}
name="name"
className="form-control"
required
/>
<label className="form-label" htmlFor="name">
Your Name
</label>
</div>
</div>
<div className="d-flex flex-row align-items-center mb-4">
<div className="form-outline flex-fill mb-0">
<input
type="email"
id="email"
name="email"
onChange={onChange}
className="form-control"
aria-describedby="emailHelp"
required
/>
<label className="form-label" htmlFor="email">
Your Email
</label>
</div>
</div>
<div className="d-flex flex-row align-items-center mb-4">
<div className="form-outline flex-fill mb-0">
<input
type="password"
onChange={onChange}
name="password"
minLength={5}
id="password"
required
className="form-control"
/>
<label className="form-label" htmlFor="password">
Password
</label>
</div>
</div>
<div className="d-flex flex-row align-items-center mb-4">
<div className="form-outline flex-fill mb-0">
<input
type="password"
onChange={onChange}
name="cpassword"
minLength={5}
id="cpassword"
required
className="form-control"
/>
<label className="form-label" htmlFor="cpassword">
Confirm your password
</label>
</div>
</div>
<div className="d-flex justify-content-center mx-4 mb-3 mb-lg-4">
<button
type="submit"
className="btn btn-primary btn-lg"
>
Register
</button>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</section>
</>
);
};
登录.js 文件:
import React, { useState } from "react";
import { useNavigate } from "react-router-dom";
export const Login = (props) => {
const host = "http://localhost:3000";
const [credentials, setCredentials] = useState({ email: "", password: "" });
let navigate = useNavigate();
const handleSubmit = async (e) => {
e.preventDefault();
const response = await fetch(`${host}/api/auth/login`, {
method: "POST",
headers: {
"Content-Type": "application/json"
},
body: JSON.stringify({
email: credentials.email,
password: credentials.password,
}),
});
const json = await response.json();
console.log(json);
if (json.success) {
// Save the auth token and redirect
localStorage.setItem("token", json.authtoken);
navigate("/");
props.showAlert("Logged In Successfully", "success");
} else {
props.showAlert("Invalid Credentials", "danger");
}
};
const onChange = (e) => {
setCredentials({ ...credentials, [e.target.name]: e.target.value });
};
return (
<section className="vh-100">
<div className="container-fluid">
<div className="row">
<div className="col-sm-6 text-black">
<div className="px-5 ms-xl-4">
<i
className="fas fa-crow fa-2x me-3 pt-5 mt-xl-4"
style={{ color: "#709085" }}
></i>
<span className="h1 fw-bold mb-0">iNotebook</span>
</div>
<div className="d-flex align-items-center h-custom-2 px-5 ms-xl-4 mt-5 pt-5 pt-xl-0 mt-xl-n5">
<form onSubmit={handleSubmit} style={{ width: "23rem" }}>
<h3
className="fw-normal mb-3 pb-3"
style={{ letterSpacing: "1px" }}
>
Log in
</h3>
<div className="form-outline mb-4">
<input
type="email"
id="email"
name="email"
onChange={onChange}
value={credentials.email}
className="form-control form-control-lg"
required
/>
<label className="form-label" htmlFor="email">
Email address
</label>
</div>
<div className="form-outline mb-4">
<input
type="password"
name="password"
onChange={onChange}
value={credentials.password}
id="password"
className="form-control form-control-lg"
required
/>
<label className="form-label" htmlFor="password">
Password
</label>
</div>
<div className="pt-1 mb-4">
<button
className="btn btn-info btn-lg btn-block"
type="submit"
>
Login
</button>
</div>
<p>
Don't have an account?
<a href="/signup" className="link-info">
Signup here
</a>
</p>
</form>
</div>
</div>
</div>
</div>
</section>
);
};
auth.js(后端文件):
const express = require("express");
const router = express.Router();
const User = require("../models/User");
const { body, validationResult } = require("express-validator");
const bcrypt = require("bcryptjs");
const jwt = require("jsonwebtoken");
const fetchUser = require("../middleware/fetchUser");
const JWT_SECRET = "Harryisagoodboy";
// ROUTE 1: Create a User using: POST "/api/auth/createuser" . No login required.
router.post(
"/createuser",
[
body("name", "Enter a valid name.").isLength({ min: 3 }),
body("email", "Enter a valid email").isEmail(),
body("password", "Enter a password of minimum 5 characters.").isLength({
min: 5,
}),
],
async (req, res) => {
// If there are errors, return the Bad request and the errors
let success = false;
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(400).json({success, errors: errors.array() });
}
try {
// Check whether the user with this email exist already
let user = await User.findOne({ email: req.body.email });
if (user) {
return res
.status(400)
.json("Sorry a user with this email already exists.");
}
const salt = await bcrypt.genSalt(10);
const secPass = await bcrypt.hash(req.body.password, salt);
user = await User.create({
name: req.body.name,
password: secPass,
email: req.body.email,
});
const data = {
user: {
id: user.id,
},
};
const authToken = jwt.sign(data, JWT_SECRET);
// .then(user => res.json(user))
// .catch(err => {console.log(err),
// res.json({error: "Please enter a unique email ID"})})
success=true;
res.json({ success, authToken });
} catch (error) {
console.error(error.message);
res.status(500).send("Internal Server Error");
}
}
);
// ROUTE 2: Authenticate a User using: POST "/api/auth/login" . No login required.
router.post(
"/login",
[
body("email", "Enter a valid email").isEmail(),
body("password", "Password cannot be blank").exists(),
],
async (req, res) => {
let success = false;
// If there are errors, return the Bad request and the errors
const errors = validationResult(req);
if (!errors.isEmpty()) {
return res.status(400).json({success , errors: errors.array() });
}
const {email , password} = req.body;
try {
// Checks if the email already exists
let user = await User.findOne({email})
if(!user){
res.status(400).json({success, error: "Please enter correct credentials"})
}
// Compares the password entered by the user with stored password in database.
const comparePassword = await bcrypt.compare(password , user.password);
// If password does not matches.
if(!comparePassword){
res.status(400).json({success, error: "Please enter correct credentials"})
}
const data = {
user: {
id: user.id,
},
};
// Getting an Authentication token on the basis of user's id as 'Payload' and 'JWT SECRET'
const authToken = jwt.sign(data, JWT_SECRET);
success=true;
res.json({ success, authToken });
} catch (error) {
console.error(error.message);
res.status(500).send("Internal Server Error");
}
}
);
// ROUTE 3: Get Logged-in User Details using: POST "/api/auth/getuser" . Login required.
router.post(
"/getuser",
fetchUser,
async (req, res) => {
try {
userID = req.user.id;
const user = await User.findById(userID).select("-password")
res.send(user);
} catch (error) {
console.error(error.message);
res.status(500).send("Internal Server Error");
}
}
)
module.exports = router;
中间件 fetchUser.js 文件:
const jwt = require("jsonwebtoken");
const JWT_SECRET = "Harryisagoodboy";
const fetchUser = (req, res, next) => {
// Get the user from the JWT token and add id to req object
const token = req.header("auth-token");
if (!token) {
res.status(401).send({ error: "Please authenticate using a valid token" });
}
try {
const data = jwt.verify(token, JWT_SECRET);
req.user = data.user;
next();
} catch (error) {
res.status(401).send({ error: "Please authenticate using a valid token" });
}
};
module.exports = fetchUser;
也许您没有请求正确的 URL。 我懂了
const host = "http://localhost:3000";
这通常是前端的主机,而不是后端,可能类似于
const host = "http://localhost:8080";
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.