注销 Azure Passport 身份验证 Node js

Loging out of Azure Passport authentication Node js

我有一个节点 js 应用程序,我们在其中使用了带护照身份验证的 azure 登录。

我已经使用 azure 成功登录,应用程序运行正常。

但是,当我注销并向页面提供 url 时 - 它会检查身份验证并自动转到该页面而不要求登录。

登录后,我的 url 包含以下查询字符串 1. session_state 2.代码 3.状态 4.令牌

登录代码:

app.get('/login', passport.authenticate('azuread-openidconnect', { failureRedirect: '/' }), function (req, res) {
res.sendFile(path.join(__dirname+'/index.html'));

});

注销代码:

app.get('/logout', function (req, res) {
    req.session.destroy();
    req.logout();
    res.redirect('/');
});

当我注销时,页面重定向到我的索引页面。然后当我给 url '/login' 时,它会把我带到页面而不去登录页面

请帮忙摆脱这个...

查看 Azure xplat 的代码,他们似乎没有调用显式注销函数,而是简单地删除了所有相关的客户端令牌。

如果没有本地令牌,您将无法登录!

注销应用程序并不意味着用户已注销 Azure。当用户注销您的应用程序时,您只需销毁您的应用程序为该用户建立的会话。当他们再次登录时,它会将他们重定向到 Azure(他们仍然在其中登录,并且您的应用程序仍然具有权限),然后立即使用该用户的令牌重定向回您的应用程序。您需要让用户注销 Azure 才能再次提示他们输入凭据。

此问题是由 OAuth 2.0 的授权码授予流程引起的。类似这样的东西在 Azure AD OAuth 2.0 服务上有任何会话。不是passportjsexpressjs的问题。

我们可以进行以下简单测试,在浏览器中访问认证端点,https://login.microsoftonline.com/common/oauth2/authorize?response_type=id_token%20code&client_id=<client_id>&redirect_uri=<redirect_uri>&response_mode=query&scope=openid

您需要先填写邮箱和密码,完成登录流程后,第二次访问端点时,您将不再需要填写邮箱和密码。

我们可以在授权端点中将 url 参数 prompt 设置为 login强制用户每次都重新进行身份验证。

详情可参考https://msdn.microsoft.com/en-us/library/azure/dn645542.aspx#code-snippet-3

但是在 azure passport oidcstrategy 中,我们应该修改源代码以将参数添加到端点中。

安装passport-azure-ad模块后,打开文件/node_modules/passport-azure-ad/lib/passport-azure-ad/oidcstrategy.js,在第545行(或多或少),可以找到如下代码片段:

      var params = {};
      if (self.authorizationParams) { params = self.authorizationParams(options); }
      params['response_type'] = config.responseType;
      log.info('We are sending the response_type: ', params['response_type']);
      params['client_id'] = config.clientID;
      params['redirect_uri'] = callbackURL;
      ...

我们可以在代码段后面加上一句params['prompt'] = 'login';来增加支持。

如有任何疑问,请随时告诉我。

编辑

Is there any way to prompt login only when i logged out...

我不确定你的意思是,你想检查用户访问login路由时是否通过身份验证,如果是,不提示登录流程?

如果是这样,您可以自定义一个中间件来检查身份验证。例如:

function checkAuthenticatedOnLogin(req,res,next){
  if (!req.isAuthenticated()) { 
    return next(); 
  }else{
    res.send('do not need login');
  }
}

app.get('/login',checkAuthenticatedOnLogin,
  passport.authenticate('azuread-openidconnect',{ failureRedirect: '/login' }),
  function(req, res) {
    log.info('Login was called in the Sample');
    res.redirect('/');
});

1) 我遇到了同样的问题,正如 passpor-azure 记录的那样,我正在执行此功能以注销:

 logout: function(req, res) {
    req.logout();
    res.redirect('/');
  }

但是 Azure 登录会话保持活动状态,所以当我重新进入我的网站时,身份验证请求将自动生效并且不会显示登录页面。

我尝试了@Gary Liu - MSFT 建议配置 prompt:login 选项,但是@user3211705 发表了评论,这使得登录页面重新出现(即使我不注销并且我有一个 portal.azure.com 选项卡打开),例如当我重新启动我的服务器时(注意:这没有错,但是当我们开发时,一个人总是重新启动服务器,并且所有登录都变得很烦人时间)

2) 我的部分解决方案来自这个 :

建议调用此 url 以在 Azure AD 上注销用户:

https://login.microsoftonline.com/<tennantid>/oauth2/logout

但仅仅这样做并不能解决所有情况。

如果我在多个 window/tab 浏览器中打开我的网站,则通过调用此 url,用户在 Azure AD 中无效,但我可以继续在另一个选项卡中使用我的网站 (该选项卡会话中的用户似乎仍然处于活动状态。

这类似于让我的网站在一个选项卡和另一个选项卡上打开 portal.azure.com,然后在 portal.azure.com 中注销,这会使我在 Azure AD 上的用户无效。

所以我的最终解决方案是两者的结合

 logout: function(req, res) {
    req.logout();
    res.redirect('https://login.microsoftonline.com/<tennantid>/oauth2/logout');
  }

这会在请求中注销我的用户并在 Azure AD 中调用注销身份验证。

仍然可以在注销时添加重定向 uri url param ?post_logout_redirect_uri=

/oauth2/logout?post_logout_redirect_uri=<your website>