#node.js #cookies #fetch #cross-domain
#node.js #файлы cookie #выборка #междоменный
Вопрос:
У меня есть экспресс-сервер, работающий на локальном хосте: 5000, и клиент, работающий на порту 3000. После отправки post-запроса от клиента для входа в систему с использованием fetch API браузер не устанавливает cookie. Я получаю cookie в заголовке ответа как «set-cookie», но он не установлен в браузере на стороне клиента.
Вот мой код запроса на выборку:
return (
fetch(baseUrl "users/login", {
method: "POST",
body: JSON.stringify(User),
headers: {
"Content-Type": "application/json",
},
credentials: "same-origin",
})
Код на стороне сервера:
router
.route("/login")
.options(cors.corsWithOptions, (req, res) => {
res.sendStatus(200);
})
.post(cors.corsWithOptions, (req, res, next) => {
passport.authenticate("local", (err, user, info) => {
if (err) return next(err);
if (!user) {
res.statusCode = 401;
res.setHeader("Content-Type", "application/json");
res.json({ success: false, status: "Log In unsuccessful", err: info });
}
req.logIn(user, (err) => {
if (err) {
res.statusCode = 401;
res.setHeader("Content-Type", "application/json");
// res.header("Access-Control-Allow-Credentials", true);
res.json({
success: false,
status: "Login Unsuccessful!",
err: "Could not log in user!",
});
}
var token = authenticate.getToken({ _id: req.user._id });
res.cookie("jwt-token", token, {
signed: true,
path: "/",
httpOnly: true,
});
res.statusCode = 200;
res.setHeader("Content-Type", "application/json");
res.json({ success: true, status: "Login Successful!", token: token });
});
})(req, res, next);
});
Комментарии:
1. Не отправляйте изображения своего кода, если вам нужна помощь в Stack Overflow скорее всего, вы получите помощь, если скопируете и вставите код с вашим вопросом, не забыв его форматировать… Пожалуйста, исправьте свой вопрос
2. Я изменил его. Пожалуйста, помогите сейчас
3. О, хорошо, я вижу, что здесь вы пытаетесь использовать файлы cookie сеанса на стороне сервера, я дам решение этой проблемы, я дам реализацию express-session amp; MongoDB … Но из вашего кода я вижу, что вы отправляете много данных полезной нагрузки, но вы должны просто отправлять токен только также в настройках cors вам нужны некоторые настройки конфигурации, которые вы увидите в моем ответе
Ответ №1:
Как обрабатывать сеанс на стороне сервера с помощью Express-session
Во-первых, вам понадобятся следующие пакеты
npm i express-session connect-mongodb-session
или yarn добавить экспресс-подключение к сеансу-mongodb-session
Теперь, когда у нас есть пакеты, которые нам нужны для настройки нашего MongoStore и промежуточного программного обеспечения express-session:
//Code in server.js/index.js (Depending on your server entry point)
import expressSession from "express-session";
import MongoDBStore from "connect-mongodb-session";
import cors from "cors";
const mongoStore = MongoDBStore(expressSession);
const store = new mongoStore({
collection: "userSessions",
uri: process.env.mongoURI,
expires: 1000,
});
app.use(
expressSession({
name: "SESS_NAME",
secret: "SESS_SECRET",
store: store,
saveUninitialized: false,
resave: false,
cookie: {
sameSite: false,
secure: process.env.NODE_ENV === "production",
maxAge: 1000,
httpOnly: true,
},
})
);
Теперь промежуточное программное обеспечение сеанса готово, но теперь вам нужно настроить cors на прием вашего ReactApp, чтобы передать файл cookie и установить его там на сервере
//Still you index.js/server.js (Server entry point)
app.use(
cors({
origin: "http://localhost:3000",
methods: ["POST", "PUT", "GET", "OPTIONS", "HEAD"],
credentials: true,
})
);
Теперь все наши промежуточные программы настроены, теперь давайте посмотрим на ваш маршрут входа
router.post('/api/login', (req, res)=>{
//Do all your logic and now below is how you would send down the cooki
//Note that "user" is the retrieved user when you were validating in logic
// So now you want to add user info to cookie so to validate in future
const sessionUser = {
id: user._id,
username: user.username,
email: user.email,
};
//Saving the info req session and this will automatically save in your mongoDB as configured up in sever.js(Server entry point)
request.session.user = sessionUser;
//Now we send down the session cookie to client
response.send(request.session.sessionID);
})
Теперь наш сервер готов, но теперь нам нужно исправить способ выполнения запроса в клиенте, чтобы этот поток мог работать на 100%:
Код ниже: приложение React / независимо от того, что вы используете, где вы выполняете вход в систему
//So you will have all your form logic and validation and below
//You will have a function that will send request to server
const login = () => {
const data = new FormData();
data.append("username", username);
data.append("password", password);
axios.post("http://localhost:5000/api/user-login", data, {
withCredentials: true, // Now this is was the missing piece in the client side
});
};
Теперь, при всем этом, у вас теперь есть файлы cookie сеансов сервера в виде HttpOnly
Комментарии:
1. Это настолько подробно, насколько это возможно для реализации сеанса на стороне сервера надеюсь, что ответ поможет вам в ваших проектах и будущих проектах