8

返回false。从Facebook登录重定向回调初始成功后,使用passport-facebook 1.0.3和express 4.6。 1,req.session.passport和req.user包含serialize调用期间设置的值(我从stragegy得到的),但在随后访问站点上的不同路由时,req.session.passport和req.user为空,并且req.isAuthenticated()返回false,所以在从FB初始成功登录后,所有其他路由上的ensureAuthentication方法失败。 我不使用集群设置,所以我相信在存储器存储足以解决这个问题,Express配置看起来不错(我指的顺序),这里是我的快速配置req.session.passport和req.user空白,req.isAuthenticated在初次成功登录后使用passport-facebook

configExpressApp.set('views', './views'); 
configExpressApp.set('view engine', 'jade'); 
configExpressApp.use(morgan('dev')); 
configExpressApp.use(cookieParser()); 
configExpressApp.use(bodyParser.urlencoded({ 
    extended: true, 
})); 
configExpressApp.use(bodyParser.json()); 
configExpressApp.use(expressSession({ 
    secret:'MyExpressSecret', 
    saveUninitialized: true, 
    resave: true 
})); 
configExpressApp.use(passport.initialize()); 
configExpressApp.use(passport.session()); 
configExpressApp.use(methodOverride()); 
configExpressApp.use(express.static('./public')); 

这里是REQ初始全成登录和重定向.session对象,该req.user包含相同的数据作为req.session.passport.user

{ cookie: 
    { path: '/', 
    _expires: null, 
    originalMaxAge: null, 
    httpOnly: true }, 
    passport: 
    { user: 
     { _id: 53ce23e3121421f229a438f8, 
     info: false, 
     loginType: 'fb', 
     fbId: 'MyId', 
     name: 'Karthic Rao', 
     email: '[email protected]' 

     } 
    } 
} 

这是我先前与内部的完成()回调相关联的信息策略,也在序列化调用中。成功登录和回调后,我使用res.redirect将用户重定向到不同的路由,但来自该路由的请求包含sessionID(所以我不认为它与会话存储问题),但req.user字段不存在(可能是因为passport.initialize()和passport.session()中间件不会找到请求进行身份验证)并且req.session.passport字段为空,以下是req的console.log中的详细信息对象。

sessionID: 'I9R1c3PIYgDW5OpWbNT7qb02Hn4lOeAB', 
session: 
    { cookie: 
     { path: '/', 
     _expires: null, 
     originalMaxAge: null, 
     httpOnly: true }, 
    passport: {} }, 

这里是我的反序列化方法

passport.deserializeUser(function(user, done) { 
    console.log('deserialize loginType facebook'); 
    db.collection("users").findOne({ 
     fbId: user.id 
    }, function(err, docs) { 
     console.log(docs); 
     done(err, docs); 
    }); 
}); 

这里是我的序列化方法

passport.serializeUser(function (user, done) { 
    console.log(user); 
    done(null, user); 
}); 

这是创造一个伟大的阻碍我的发展,我怎么能排序了这一点?

+0

嗯...我没有立即的解决方案来推荐你,但你能告诉我们你的'serializeUser'和'deserializeUser'方法吗? 对我来说,它看起来像会话中存储的任何内容都没有正确反序列化。 –

+0

我编辑了这个问题,在问题结尾添加了我的序列化和反序列化方法。谢谢你的回复! –

+0

我也注意到,在后续请求中发送给反序列化方法的'user'对象是'null'! –

回答

9

那么,如果你可以在你使用策略的地方添加代码(它应该在中间件中),那会给我们一个完整的问题视图,因为我们需要知道什么对象发送到serializeUser

(非常)基本上,当用户尝试进行身份验证,事情发生这样的:

  • 护照试图对Facebook的服务器上的用户进行身份验证
  • 如果成功,则回调函数(或successRedirect)被称为 包含用户的详细信息的对象
  • 然后,护照使得以req.login调用存储一些信息关于 用户在会话
  • 然后serializeUser被调用并有效存储您在会话中指定的数据

但是,从您发布的代码中,我怀疑在您的deserializeUser,用户。ID未定义,因为存储在会话中的user对象使用名为_id而不是ID的ID字段。

如果更改

db.collection("users").findOne({ 
     fbId: user.id 

db.collection("users").findOne({ 
     fbId: user._id 

db.collection("users").findById(user._id, [fields],[options],[callback]); 

,我认为它应该工作。

编辑:我根据@ BrandonZacharie的评论编辑了我的答案,该评论在我的代码中指出了一个错误。

+0

不应该是“... findOne({fbId:user.fbId} ...”或“... findOne({_id:mongodb.ObjectId(user._id)} ...”而不是? –

+0

@ BrandonZacharie我重新阅读了你的评论(并删除了我之前的评论,因为它是错误的)我认为你是对的,我只是复制粘贴了Karthic Rao的代码而没有留意,Mongoose甚至有一个[findById方法](http:///mongoosejs.com/docs/api.html#model_Model.findById),它接受一个“objectid或可以被转换为一个值”作为它的第一个参数。 如果没关系,我会根据你的建议编辑我的答案与你(或你可以发表你的评论作为答案) –

+1

是的_id提交被称为ID是肯定的问题之一,但另一个问题是,我在后端使用requirejs模块化和nodejs代码,我使用不同的护照对象配置为中间件(passport.session()和护照)的错误.initialize()),并且我在不同的护照对象上调用了serializeUser和deserializeUser。现在它的工作,感谢你为帮助我而做出的所有努力! –

相关问题