【问题标题】:Cannot log out of iOS Swift app when connecting to Rails API using Doorkeeper & Devise使用 Doorkeeper & Devise 连接到 Rails API 时无法注销 iOS Swift 应用程序
【发布时间】:2015-11-17 20:53:39
【问题描述】:

好的 - 48 小时后我放弃了。我用 Doorkeeper 和 Devise 设置了 Rails 3.2 应用程序。 doorkeeper.rb 初始化器非常简单:

resource_owner_authenticator do 
  current_account || warden.authenticate!(:scope => :account)
end

我在 iOS Swift 应用程序中使用很棒的 p2_oauth POD 进行 OAuth2 连接。这是问题/奇怪之处:

当我登录并开始 OAuth2 舞蹈时,p2 使用 iOS 的嵌入式 Web 视图来访问我的 Rails API。由于没有 current_account,它会适当地重定向到登录。太好了。

但是 - 我无法退出。

我什么都试过了:

  • warden.logout
  • 退出
  • session.delete("warden.user.account.key")
  • 在调用注销路由时清除 Rails 应用程序中的 cookie
  • 在调用注销路由时清除 Rails 应用程序中的会话

无论我做什么,当我再次登录时,Rails 应用程序都会保留 current_account!?我检查了会话,果然,会话中还有一个warden.user.account.key!真气人。

如果我在模拟器中停止并重新启动 iOS 应用程序,一切都会恢复正常,直到我登录/注销。很明显,iOS 正在维护一些会话,而不是清除 Rails 应用程序正在读取的会话。我还确保我的请求没有缓存策略:

    request.cachePolicy = NSURLRequestCachePolicy.ReloadIgnoringLocalAndRemoteCacheData
    request.setValue("application/json", forHTTPHeaderField: "Accept")
    request.HTTPMethod = "DELETE"

    let config = NSURLSessionConfiguration.defaultSessionConfiguration()
    config.URLCache = nil
    let session = NSURLSession(configuration: config)

    let task : NSURLSessionDataTask = session.dataTaskWithRequest(request, completionHandler: 

我真的不敢相信没有其他人遇到过这种情况。我应该如何使用此设置注销?

【问题讨论】:

  • 您有没有想出解决方案?我也有类似的问题。
  • 我最终使用密码授予流程而不是 Web 视图来避免整个 cookie 会话情况

标签: ios ruby-on-rails devise doorkeeper


【解决方案1】:

只是想跟进您的评论。

只是回顾一下我遇到的什么问题让我想到了你的问题: 用户可以正常登录,但无法正确注销。一旦他们再次点击登录,它会自动登录而无需再次询问密码。

正如您所说,使用密码授予流程确实可以避免 cookie 会话。对我来说,我不得不在我的 iOS 应用程序中使用某种 webview。所以我不得不坚持 authorization_code 授权。

我花了整整一周的时间试图弄清楚 doorkeeper+devise 发生了什么(我所有的链接都是紫色的......),我终于找到了一个适合我的解决方案。我不确定这是不是正确的方法,因为我根本不熟悉 ruby​​ on rails。稍后我将不得不再次检查代码。

基本上,要做的就是将它添加到 config/routes.rb 你说 user_doorkeeper 的地方

use_doorkeeper do
    controllers applications: 'doorkeeper', authorizations: 'authorizations'
end

然后在此处添加一个授权控制器app/controllers/authorizations_controller.rb

class AuthorizationsController < Doorkeeper::AuthorizationsController
  def new
    super
    env['warden'].logout
  end
end

这会强制用户在登录时注销。对于代码,我认为它所做的是将代码覆盖/添加到 Doorkeeper 中的原始 AuthorizationsController。

我在看起来像某人的博客上找到了这个解决方案,谢谢你好先生!现在就可以了。 http://www.kluks.de/blog/posts/14-rails-4-single-sign-out-of-all-applications-with-doorkeeper.

------------ 编辑 ------------

作为参考,对于提供商方面,我一直在关注这个guide,同时添加了我需要的东西。不过,我不建议您遵循她的客户端教程。这对我来说根本不起作用。

doorkeeper.rb

Doorkeeper.configure do
use_refresh_token
force_ssl_in_redirect_uri false

#for authorization_code grant
resource_owner_authenticator do
    current_user || begin
        session[:user_return_to] = request.fullpath
        redirect_to new_user_session_url
    end
end

end

【讨论】:

  • 我实际上尝试了这种方法以及在 create 方法上尝试它。无论出于何种原因,这也不起作用。您介意发布您的 devise.rb 和 doorkeeper.rb 吗?也许我的配置有误。
  • 我的 devise.rb 是默认给定的。我会发布doorkeeper.rb。当您说您在create方法上尝试过时,您的意思是您将env['warden'].logout放在了sessions_controller.rb中吗?我尝试在多个地方使用 env['warden'].logout ,但它只在 authorizations_controller.rb 覆盖中对我有用。
【解决方案2】:

我们遇到了类似的问题,后端设置相同,但我们能够通过清除 iOS 应用上的 cookie 来解决。

[[NSHTTPCookieStorage sharedHTTPCookieStorage] removeCookiesSinceDate:[NSDate dateWithTimeIntervalSince1970:0]];

【讨论】:

    【解决方案3】:

    加布里埃尔的回答只对我部分有效。问题在于,用户在调用 AuthorizationsController#new 后直接注销,因此用户第一次授权应用程序时需要的后续 AuthorizationsController#create 请求不起作用。

    为了让授权流程正常工作,我只需要在创建操作之后退出用户,或者如果不需要授权应用程序,则在 authorize#new 之后退出。

    class AuthorizationsController < Doorkeeper::AuthorizationsController
    
      def create
        redirect_or_render authorize_response
        # Sign out the user user clicked "Authorize" in the Authorize application page
        warden.logout
      end
    
      private
    
      def render_success
        if skip_authorization? || matching_token?
          redirect_or_render authorize_response
          # sign out directly if there is no need for authorizing the app
          warden.logout
        elsif Doorkeeper.configuration.api_only
          render json: pre_auth
        else
          render :new
        end
      end
    end
    

    请注意,此案例是与作为客户端的移动应用一起使用的,如果打算为多个应用提供 SSO,则此案例将不起作用。

    我使用了 doorkeeper 5.1 并设计了 4.7,所以对于其他版本可能看起来有点不同。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-31
      • 1970-01-01
      • 2012-04-11
      • 1970-01-01
      • 2013-04-18
      • 2016-09-03
      • 2016-02-21
      • 1970-01-01
      相关资源
      最近更新 更多