问题
I have no idea what I'm doing wrong here. The POST method works from Postman, but doesn't work from the React frontend.
users.js (/api/users/login)
// @route POST api/users/login
// @desc Login user / Returning JWT Token
// @access Public
router.post('/login', (req, res, next) => {
const { errors, isValid } = validateLoginInput(req.body);
// Check validation
if (!isValid) {
return res.status(400).json(errors);
}
const email = req.body.email;
const password = req.body.password;
// Find user by email
User.findOne({ email }) // matching email: email
.then(user => {
if (!user) {
errors.email = 'User not found';
return res.status(404).json(errors);
}
// Check Password
bcrypt.compare(password, user.password)
.then(isMatch => {
if(isMatch) {
// User matched. Create JWT payload
const payload = {
id: user.id
}
// Sign Token
jwt.sign(
payload,
keys.secretOrKey,
{ expiresIn: 3600 },
(err, token) => {
res.json({
success: true,
token: 'Bearer ' + token
});
});
} else {
errors.password = 'Password incorrect'
return res.status(400).json(errors);
}
});
});
});
loginUser() function:
export const loginUser = userData => dispatch => {
axios
.post("/api/users/login", userData)
.then(res => {
// Save to localStorage
const { token } = res.data;
// Set token to localStorage
localStorage.setItem("jwtToken", token); // only stores strings
// Set token to Auth header
setAuthToken(token);
// Decode token to get user data
const decoded = jwt_decode(token);
// Set current user
dispatch(setCurrentUser(decoded));
})
.catch(err =>
dispatch({
type: GET_ERRORS,
payload: err.response.data
})
);
};
onSubmit() function in React component:
onSubmit(e) {
e.preventDefault();
const userData = {
email: this.state.email,
password: this.state.password
}
this.props.loginUser(userData);
}
Network:
Request URL: http://localhost:3000/api/users/login
Request Method: POST
Status Code: 404 Not Found
Remote Address: 127.0.0.1:3000
Referrer Policy: no-referrer-when-downgrade
Connection: keep-alive
Content-Length: 155
Content-Security-Policy: default-src 'self'
Content-Type: text/html; charset=utf-8
Date: Mon, 16 Jul 2018 01:53:03 GMT
Vary: Accept-Encoding
X-Content-Type-Options: nosniff
X-Powered-By: Express
Accept: application/json, text/plain, */*
Accept-Encoding: gzip, deflate, br
Accept-Language: en-US,en;q=0.9
Connection: keep-alive
Content-Length: 46
Content-Type: application/json;charset=UTF-8
Cookie: io=VtWk-hb742jVakwrAAAE; PHPSESSID=ige5g7257th8hiksjomg2khouu; i18next=en; connect.sid=s%3Aq6FkEveJbDYoKTy386QESFBxGaW8MjKd.qSBAkm2t23Ww4ZtHtcs7%2F1e5tDn528i0C6Hv7U3PwI0
Host: localhost:3000
Origin: http://localhost:3000
Referer: http://localhost:3000/login
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/67.0.3396.99 Safari/537.36
{email: "admin@gmail.com", password: "admin"}
email
:
"admin@gmail.com"
password
:
"admin"
The port on server.js:
// Initializint the port
const port = process.env.PORT || 5000;
app.listen(port, () => console.log(`Server running on port ${port}`));
I checked some similar issues here, and most of them were related to headers. In my case, the headers are application/json, so I don't think the problem is there. No problems hitting the endpoint through Postman.
回答1:
Your react app is running on a different port than your backend app. create-react-app
runs on port 3000 and as you've stated your backend is running on port 5000.
When your client side app is making a request to the server, its actually making a request to port 3000 as you can see here.
Request URL: http://localhost:3000/api/users/login
It's doing so because you never specified the origin url in your request as you can see here post("/api/users/login", userData)
, and in that case it defaults to the same port the request came from which is port 3000, and port 3000 does not in fact have the url you requested.
You can solve this by either including the origin url in the request, or by adding a proxy to the react app package.json as you can here.
https://github.com/facebook/create-react-app/blob/master/packages/react-scripts/template/README.md#proxying-api-requests-in-development
来源:https://stackoverflow.com/questions/51353658/reactjs-express-axios-post-returns-404-works-from-postman