Autodesk forge Forge 3腿Oauth-以其他用户身份登录/强制注销

Autodesk forge Forge 3腿Oauth-以其他用户身份登录/强制注销,autodesk-forge,Autodesk Forge,我有三条腿去工作,我有自己的会话登录/注销管理 注销后,如果用户想再次登录,我会将其发送到 https://developer.api.autodesk.com/authentication/v1/authorize,它将直接进入我的回调,之前的用户已通过身份验证,而不是提示重新登录 似乎Autodesk正在将会话存储为cookie,因此授权后切换用户的唯一方法是清除浏览器缓存/数据 是否有强制注销的方法,或者类似于“以其他用户身份登录”的方法 这是我第一次使用oauth,所以我不确定我是否遗漏

我有三条腿去工作,我有自己的会话登录/注销管理

注销后,如果用户想再次登录,我会将其发送到
https://developer.api.autodesk.com/authentication/v1/authorize
,它将直接进入我的回调,之前的用户已通过身份验证,而不是提示重新登录

似乎Autodesk正在将会话存储为cookie,因此授权后切换用户的唯一方法是清除浏览器缓存/数据

是否有强制注销的方法,或者类似于“以其他用户身份登录”的方法

这是我第一次使用oauth,所以我不确定我是否遗漏了什么,但似乎应该有办法强制清除会话并强制重新登录


编辑 让我进一步澄清我试图实现的目标:

这是我的。 1.我将用户定向到身份验证页面,将其定向到:
https://developer.api.autodesk.com/authentication/v1/authorize?response_type=code&client_id=obQDn8P0GanGFQha4ngKKVWcxwyvFAGE&redirect_uri=http%3A%2F%2F{{mycallback}%2Fcallback%3Ffoo%3Dbar&scope=data:read

  • 用户使用其Autodesk凭据登录

  • 授权流将用户重定向到`mycallback.com/callback/?code={{code}}

  • 我的后端从url请求中获取
    code
    参数,并向
    https://developer.api.autodesk.com/authentication/v1/gettoken

  • 除其他外,请求返回
    access\u令牌

  • 我将
    access\u令牌
    存储到用户的会话中,并使用该令牌向API发出下一个请求

  • 到目前为止,它的工作方式与我预期的一样。现在我想注销该用户,并可能以其他用户的身份登录

  • 我的服务器上的A/logout端点将清除用户会话,从而消除存储的访问令牌

  • 一旦后端意识到没有活动会话/访问令牌,它就会将用户重定向到身份验证流(上面的步骤1)

  • 此时,我希望看到另一个Autodesk登录页面,但Autodesk的服务器会自动授权,而无需重新登录,并重定向用户回拨,然后用户再次登录

  • 因此,重新表述我的问题,如何更改上面#9上的行为,以便用户必须重新输入其凭证

    我经常在开发过程中遇到这种情况,我用我的个人帐户登录,然后注销,我想用我的工作帐户登录。 目前,我唯一能做的就是清除浏览器的缓存。 这让我想到Autodesk正在将会话存储在浏览器中,这就是为什么它在不获取新凭据的情况下重新进行身份验证

    在dm.autodesk.io上也会发生相同的行为 在第一次登录后,如果我再次尝试授权,则第二次登录时不会提示我,而是会自动在与我一起登录的第一个用户中重新登录

    如果我正确理解发生了什么,那么API应该有一个端点,当我的用户注销以强制重新验证时,我们可以调用该端点

    有道理吗


    谢谢

    我不知道你说的“我把他送到”是什么意思,但这必须发生在你的服务器上

    检查我的示例:允许弹出窗口并单击导航栏中的“用户数据”。登录后,用户会话将安全地存储在服务器上。如果重新加载页面,它将自动让您登录。如果再次单击导航栏按钮,它将清除服务器上的会话,如果重新加载,则不会登录。我想这就是你想要的行为

    此项目的代码位于。三条腿的逻辑是从下面处理的(node.js):

    只需加载此URL:“ 这将注销以前的用户会话,新用户可以登录


    请参阅此以了解更多详细信息:

    Hi Phillippe-我在问题中添加了更多详细信息。我知道,是的,我认为如果您在同一浏览器上登录A360帐户,它将使用会话数据。我会看看有没有办法绕过它。一个解决方法是也从A360注销,感谢您记录解决方案。不幸的是,2年多前当这个问题被提出时,这是不存在的。标记并回答。
    import ServiceManager from '../services/SvcManager'
    import { serverConfig as config } from 'c0nfig'
    import { OAuth2 } from 'oauth'
    import express from 'express'
    
    module.exports = function() {
    
      var router = express.Router()
    
      ///////////////////////////////////////////////////////////////////////////
      // 2-legged client token: exposes a 'data:read' only token to client App
      //
      ///////////////////////////////////////////////////////////////////////////
      router.get('/token/2legged', async(req, res) => {
    
        try {
    
          var forgeSvc = ServiceManager.getService('ForgeSvc')
    
          var token = await forgeSvc.request2LeggedToken('data:read')
    
          res.json(token)
    
        } catch (error) {
    
          res.status(error.statusCode || 404)
          res.json(error)
        }
      })
    
      /////////////////////////////////////////////////////////////////////////////
      // Initialize OAuth library
      //
      /////////////////////////////////////////////////////////////////////////////
    
      var oauth2 = new OAuth2(
        config.forge.oauth.clientId,
        config.forge.oauth.clientSecret,
        config.forge.oauth.baseUri,
        config.forge.oauth.authorizationUri,
        config.forge.oauth.accessTokenUri,
        null)
    
      /////////////////////////////////////////////////////////////////////////////
      // login endpoint
      //
      /////////////////////////////////////////////////////////////////////////////
      router.post('/login', function (req, res) {
    
        var authURL = oauth2.getAuthorizeUrl({
          redirect_uri: config.forge.oauth.redirectUri,
          scope: config.forge.oauth.scope.join(' ')
        })
    
        res.json(authURL + '&response_type=code')
      })
    
      /////////////////////////////////////////////////////////////////////////////
      // logout endpoint
      //
      /////////////////////////////////////////////////////////////////////////////
      router.post('/logout', (req, res) => {
    
        var forgeSvc = ServiceManager.getService(
          'ForgeSvc')
    
        forgeSvc.delete3LeggedToken(req.session)
    
        res.json('success')
      })
    
      /////////////////////////////////////////////////////////////////////////////
      // Reply looks as follow:
      //
      //  access_token: "fk7dd21P4FAhJWl6MptumGkXIuei",
      //  refresh_token: "TSJpg3xSXxUEAtevo3lIPEmjQUxXbcqNT9AZHRKYM3",
      //  results: {
      //    token_type: "Bearer",
      //    expires_in: 86399,
      //    access_token: "fk7dd21P4FAhJWl6MptumGkXIuei"
      //  }
      //
      /////////////////////////////////////////////////////////////////////////////
      router.get('/callback/oauth', (req, res) => {
    
        var socketSvc = ServiceManager.getService(
          'SocketSvc')
    
        // filter out errors (access_denied, ...)
        if (req.query && req.query.error) {
    
          if (req.session.socketId) {
    
            socketSvc.broadcast(
              'callback', req.query.error,
              req.session.socketId)
          }
    
          res.json(req.query.error)
          return
        }
    
        if(!req.query || !req.query.code) {
    
          res.status(401)
          res.json('invalid request')
          return
        }
    
        oauth2.getOAuthAccessToken(
          req.query.code, {
            grant_type: 'authorization_code',
            redirect_uri: config.forge.oauth.redirectUri
          },
          function (err, access_token, refresh_token, results) {
    
            try {
    
              var forgeSvc = ServiceManager.getService(
                'ForgeSvc')
    
              var token = {
                scope: config.forge.oauth.scope,
                expires_in: results.expires_in,
                refresh_token: refresh_token,
                access_token: access_token
              }
    
              forgeSvc.set3LeggedTokenMaster(
                req.session, token)
    
              if(req.session.socketId) {
    
                socketSvc.broadcast(
                  'callback',
                  'success',
                  req.session.socketId)
              }
    
              res.end('success')
    
            } catch (ex) {
    
              res.status(500)
              res.end(ex)
            }
          }
        )
      })
    
      /////////////////////////////////////////////////////////////////////////////
      // logout route
      //
      /////////////////////////////////////////////////////////////////////////////
      router.post('/logout', (req, res) => {
    
        var forgeSvc = ServiceManager.getService(
          'ForgeSvc')
    
        forgeSvc.logout(req.session)
    
        res.json('success')
      })
    
      ///////////////////////////////////////////////////////////////////////////
      // 3-legged client token: exposes a 'data:read' only token to client App
      //
      ///////////////////////////////////////////////////////////////////////////
      router.get('/token/3legged', async (req, res) => {
    
        var forgeSvc = ServiceManager.getService(
          'ForgeSvc')
    
        try {
    
          var token = await forgeSvc.get3LeggedTokenClient(
            req.session)
    
          res.json({
            expires_in: forgeSvc.getExpiry(token),
            access_token: token.access_token,
            scope: token.scope
          })
    
        } catch (error) {
    
          forgeSvc.logout(req.session)
    
          res.status(error.statusCode || 404)
          res.json(error)
        }
      })
    
      return router
    }