gpt4 book ai didi

javascript - Passport.js、 session 和 react |从/login 路由以外的任何路由访问 req.user 是未定义的

转载 作者:行者123 更新时间:2023-12-04 15:58:45 24 4
gpt4 key购买 nike

我在 localhost:3000 有一个 React 客户端设置,在 localhost:5000 有一个 node.js 服务器
我正在尝试一个简单的身份验证流程,其中客户端尝试使用 Passport.js Google OAuth2.0 对服务器进行身份验证,并使用与 MongoDB 存储的快速 session 保持身份验证。
我相信我发现 req.user 未定义的原因是因为我缺乏对身份验证流程应该如何工作以及实际代码的任何问题的理解。
我正在通过 react 客户端中的以下代码启动身份验证流程:

<Button href="http://localhost:5000/auth/google">
Login using Google
</Button>
以下是我的 auth.js 文件:
const express = require("express");
const passport = require("passport");
const router = express.Router();

// @desc Auth with Google
// @route GET /auth/google
router.get("/google", passport.authenticate("google", { scope: ["profile"] }));

// @desc Google auth callback
// @route GET /auth/google/callback
router.get(
"/google/callback",
passport.authenticate("google", {
failureRedirect: "/",
successRedirect: "http://localhost:3000/dashboard",
})
);

// @desc Logout user
// @route /auth/logout
router.get("/logout", (req, res) => {
req.logout();
res.redirect("/");
});

module.exports = router;
以下是我的谷歌策略配置:
const GoogleStrategy = require("passport-google-oauth20").Strategy;
const mongoose = require("mongoose");
const User = require("../models/User");

module.exports = function (passport) {
passport.use(
new GoogleStrategy(
{
clientID: process.env.GOOGLE_CLIENT_ID,
clientSecret: process.env.GOOGLE_CLIENT_SECRET,
callbackURL: "http://localhost:5000/auth/google/callback",
},
async (accessToken, refreshToken, profile, done) => {
const newUser = {
googleId: profile.id,
displayName: profile.displayName,
firstName: profile.name.givenName,
lastName: profile.name.familyName,
image: profile.photos[0].value,
};

try {
let user = await User.findOne({ googleId: profile.id });

if (user) {
done(null, user);
} else {
user = await User.create(newUser);
done(null, user);
}
} catch (err) {
console.error(err);
}
}
)
);

passport.serializeUser((user, done) => {
done(null, user.id);
});

passport.deserializeUser((id, done) => {
User.findById(id, (err, user) => done(err, user));
});
};
以下代码是我的 index.js 将所有内容结合在一起:
const express = require("express");
const cors = require("cors");
const bodyParser = require("body-parser");
const mongoose = require("mongoose");
const connectDB = require("./config/db");
const morgan = require("morgan");
const passport = require("passport");
const session = require("express-session");
const MongoStore = require("connect-mongo")(session);

// Dotenv config
const dotenv = require("dotenv").config({
path: "./config/config.env",
});

// Passport config
require("./config/passport")(passport);

// MongoDB config
connectDB();

const app = express();
const PORT = process.env.PORT;

// Middleware

app.use(cors());
app.use(bodyParser.json());
app.use(morgan("dev"));

// Sessions
app.use(
session({
secret: "stackoverflow",
resave: false,
saveUninitialized: false,
store: new MongoStore({ mongooseConnection: mongoose.connection }),
})
);

// Passport middleware
app.use(passport.initialize());
app.use(passport.session());

app.use("/posts", require("./routes/posts"));
app.use("/auth", require("./routes/auth"));

app.listen(PORT, () => console.log(`Server listening @ port ${PORT}`));
用户登录后,我通过其中一条路由从数据库中获取帖子:
...
// @desc Get all posts
// @route GET /posts

router.get("/", (req, res) => {
const posts = Post.find(function (error, posts) {
if (error) return console.error(error);
console.log(req.user) // <------ is undefined
res.json(posts);
});
});
我假设在用户被重定向到仪表板然后向路由发送请求以获取所有帖子后,用户未通过身份验证?虽然我在验证用户身份后将用户重定向到这条路线?
目标绝对不是在/posts 路由中获取用户,而是创建一个单独的/user 路由,将用户返回到客户端,但这也会导致 req.user 未定义。

最佳答案

终于让它工作了。
我不得不编辑两件事,
首先(服务器端):
我必须设置 CORS 以允许 cookie 像这样通过:

app.use(
cors({
origin: "http://localhost:3000", // allow to server to accept request from different origin
methods: "GET,HEAD,PUT,PATCH,POST,DELETE",
credentials: true, // allow session cookie from browser to pass through
})
);
第二(客户端):
我必须让 Axios 知道它必须将 cookie 与请求一起发送,如下所示:
axios
.get("http://localhost:5000/auth/user", { withCredentials: true })
.then(console.log)
.catch(console.error);
/auth/user路线定义如下:
router.get("/user", (req, res) => {
if (req.user) {
res.json(req.user);
}
});
如果我对整个身份验证过程有更好的了解,这些错误是可以避免的,现在我做到了。
我们生活,我们学习。

关于javascript - Passport.js、 session 和 react |从/login 路由以外的任何路由访问 req.user 是未定义的,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63152640/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com