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

Devise添加自定义路由返回404 ActionNotFound报错排查

问题原因

配置错误共两处:

  • 自定义路由嵌套层级错误:你写的devise_scope :user块放在了api、v1两层命名空间的外面,属于顶层路由。虽然rails routes输出的路径、控制器指向看起来正常,但Devise的映射查找和路由嵌套上下文强绑定,顶层声明的devise_scope无法关联到api/v1命名空间下通过mount_devise_token_auth_for注册的User认证规则,直接触发找不到devise mapping的报错。
  • 路由匹配优先级错误:mount_devise_token_auth_for会在挂载位置生成带通配逻辑的内置路由,如果你把自定义路由写在它后面,请求会先被devise_token_auth的内置路由拦截,根本匹配不到你自定义的规则。
    另外你预期路径是/api/v1/auth/token,但路由里写的是/auth/tokens(多了个s),属于笔误,一并修正即可。
修复方法
  1. 把自定义路由块移动到namespace :api -> namespace :v1的块内部,且必须放在mount_devise_token_auth_for语句的前面,保证自定义路由优先匹配
  2. 修正路径为你需要的单数token,配置示例如下:
namespace :api do
  namespace :v1 do
    # 自定义路由必须放在mount_devise_token_auth_for之前
    devise_scope :user do
      post 'auth/token', to: 'users/sessions#tokens'
    end

    mount_devise_token_auth_for 'User', as: 'user', at: 'auth', controllers: {
      token_validations:  'api/v1/users/token_validations',
      confirmations:      'api/v1/users/confirmations',
      registrations:      'api/v1/users/registrations',
      passwords:          'api/v1/users/passwords',
      sessions:           'api/v1/users/sessions'
    }
  end
end
  1. 确认Sessions控制器中已经定义了对应tokens方法,注意控制器的命名空间要和目录结构一致:
# app/controllers/api/v1/users/sessions_controller.rb
module Api
  module V1
    module Users
      class SessionsController < DeviseTokenAuth::SessionsController
        # 按需添加认证过滤,比如要求已登录才能访问
        # before_action :authenticate_api_v1_user!, only: [:tokens]
        def tokens
          # 编写你的业务逻辑
          render json: { data: current_api_v1_user }
        end
      end
    end
  end
end
验证

修改完成后必须重启Rails服务(路由修改在开发环境下偶尔不会自动重载),再执行rails routes | grep token,能看到以下路由记录就说明配置正确:

api_v1_auth_token POST   /api/v1/auth/token(.:format)   api/v1/users/sessions#tokens

此时再发POST请求到对应地址就不会报404或者mapping找不到的错误。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.28 08:15:43