You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

能否使用Doorkeeper实现Action Cable的授权认证?技术问询

用Doorkeeper为Action Cable实现授权认证:完全可行!

当然可以用Doorkeeper给Action Cable做授权认证,核心思路和Action Cable官方的自定义认证逻辑一致,而且能实现类似devise_token_auth的用户关联效果,下面是具体的实现步骤和代码示例:

一、核心实现:在Action Cable Connection中校验Doorkeeper Token

Action Cable的认证逻辑是在Connection类中处理的(而非控制器的before_action),我们需要在这里完成Doorkeeper access token的校验,并关联到当前用户。

修改app/channels/application_cable/connection.rb:

module ApplicationCable
  class Connection < ActionCable::Connection::Base
    # 用current_user标识当前连接的用户
    identified_by :current_user

    # 连接建立时执行的核心方法
    def connect
      self.current_user = find_verified_user
      logger.add_tags 'ActionCable', current_user.email # 日志中标记用户信息,方便调试
    end

    private

    def find_verified_user
      # 从请求头或URL参数中获取access token(兼容两种传递方式)
      token = request.params[:access_token] || request.headers['Authorization']&.split('Bearer ')&.last

      if token && doorkeeper_token = Doorkeeper::AccessToken.find_by(token: token)
        # 校验token是否有效(未过期、未被撤销)
        if doorkeeper_token.accessible?
          # 返回token对应的资源所有者(即你的User模型实例)
          doorkeeper_token.resource_owner
        else
          # token无效则拒绝连接
          reject_unauthorized_connection
        end
      else
        # 未提供token则拒绝连接
        reject_unauthorized_connection
      end
    end
  end
end

二、类比devise_token_auth的用户关联效果

和devise_token_auth集成Action Cable的逻辑类似,上面的代码完成了以下核心功能:

  1. 身份凭证校验:从请求中获取token并通过Doorkeeper验证有效性
  2. 用户关联:将验证通过的token绑定到对应的用户实例
  3. 连接标识:用current_user标识每个Action Cable连接,后续在频道中可以直接调用

比如在你的频道类中,就可以直接使用current_user操作:

class ChatChannel < ApplicationCable::Channel
  def subscribed
    # 只为当前用户订阅专属的消息流
    stream_from "chat_#{current_user.id}"
  end

  def send_message(data)
    # 直接用current_user创建消息
    Message.create!(user: current_user, content: data['content'])
  end
end

三、额外的安全优化建议

  1. 限制Token权限范围:如果需要更细粒度的控制,可以在校验时检查token的scope:
    # 确保token拥有"channel_access"权限才能连接
    if doorkeeper_token.accessible? && doorkeeper_token.includes_scope?('channel_access')
      doorkeeper_token.resource_owner
    else
      reject_unauthorized_connection
    end
    
  2. 强制HTTPS传输:避免token被明文窃取,生产环境一定要用HTTPS传递token
  3. 处理Token过期:如果token过期,客户端需要重新获取有效token后再发起连接

四、现有配置的兼容性

你当前的路由配置:

use_doorkeeper do 
  skip_controllers :authorizations, :applications, :authorized_applications 
end
mount ActionCable.server => '/cable'

完全不需要修改,Action Cable的认证逻辑已经在Connection类中独立处理,和Doorkeeper的控制器配置不冲突。

内容的提问来源于stack exchange,提问作者ViT-Vetal-

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.22 09:42:32