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

Rails应用登录后闲置访问接口出现重定向循环及401错误求助

原因分析
  1. 401报错核心原因
    你在session_store.rb中设置了10年的cookie过期时间,但Devise的config.timeout_in = 25.minutes配置优先级更高,用户登录后闲置满25分钟,Devise会主动销毁会话有效性,此时current_user就会返回空,触发401响应,和你配置的cookie过期时间无关。
  2. 重定向循环原因
    Devise默认对未登录的请求会触发302重定向到登录页,如果你未覆盖Devise的默认未登录处理逻辑,会话过期时请求会先被Devise拦截返回302;加上Postman默认开启自动跟随重定向,如果登录页逻辑又跳转回原请求地址,就会触发无限循环,导致Postman报错。
排查步骤
  • 确认ApiController及子类是否引入了Devise的authenticate_user!前置回调:如果加了这个回调,它的执行优先级高于你自定义的check_user,会话过期时Devise会直接触发302重定向,不会走到你写的返回401的逻辑
  • 查看Postman的重定向设置:是否开启了「Automatically follow redirects」,开启后遇到302响应会自动跳转,触发循环时就会报对应错误
  • 验证Devise timeout规则:登录后分别在25分钟以内、25分钟以上请求接口,看返回结果是否符合25分钟过期的规律,确认是timeout_in配置生效导致的会话过期
  • 检查自定义check_user的执行情况:在check_user方法里加日志,看会话过期时该方法是否被执行,有没有被Devise的默认回调拦截
解决方案

1. 解决会话过期问题(按需二选一)

  • 如果你确实需要长期会话适配移动端需求,直接把Devise的config.timeout_in设置为和session_store匹配的时长即可,比如config.timeout_in = 10.years,覆盖默认的25分钟过期规则
  • 如果需要保留闲置超时逻辑,就在客户端加401响应的捕获逻辑,遇到401时自动跳转到登录页重新登录

2. 解决重定向循环问题

禁用Devise对API请求的默认重定向行为,给API控制器添加如下配置即可:

class ApiController < ActionController::Base
  # 告诉Devise这是JSON请求,不要重定向,直接返回401
  protect_from_forgery with: :null_session
  before_action :configure_devise_params, if: :devise_controller?

  # 覆盖Devise的默认未登录处理逻辑
  def authenticate_user!
    if request.format.json?
      current_user.present? ? super : render(json: { err: 'Faça seu login antes de continuar' }, status: 401)
    else
      super
    end
  end

  # 原有逻辑保持不变
  before_action :check_user,
                except: %i[signin signinEmployee signup signupEmployee forgotPass getFaq getMessages updatePassword contactus
                           getBanners getPartners getCategories getServices getAllServices getServiceDetails getRecommended checkCode getInstructions checkCpf emailCode checkEmail getPipefyUrl log]
  skip_before_action :verify_authenticity_token

  def check_user
    return if current_user.present?
    render json: { err: 'Faça seu login antes de continuar' }, status: 401
  end

  private
  def configure_devise_params
    # 你需要的Devise参数白名单可以在这里添加
    devise_parameter_sanitizer.permit(:sign_up, keys: [:name, :phone, :cpf])
  end
end

3. Postman测试适配

在Postman的设置里关闭「Automatically follow redirects」,测试时就能直接看到接口真实的响应状态码和内容,不会触发循环跳转的报错。

内容的提问来源于stack exchange,提问作者Gustavo Trivelatto

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.12 13:36:03