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

如何重构Ruby模块,获取包含Gem的API命名空间下所有控制器?

解决方案

原代码依赖Rails路由集合获取控制器,Gem中的控制器若未在主应用路由显式挂载,就不会出现在anchored_routes中。要覆盖Gem里的API控制器,需换思路直接从已加载的控制器类中筛选:

重构后的代码

# frozen_string_literal: true

module ApiControllers
  mattr_accessor :list

  def list
    return @list if @list

    @list = ActionController::Base.descendants.select do |controller_class|
      controller_class.respond_to?(:controller_path) && controller_class.controller_path.start_with?('api/')
    end.map(&:to_s).uniq
  end

  module_function :list
end

代码说明

  • ActionController::Base.descendants:获取所有已加载的、继承自ActionController::Base的控制器类,包含Gem中定义的控制器
  • controller_path.start_with?('api/'):通过控制器的controller_path判断是否属于API命名空间,这和路由配置中的controller参数完全对应,比单纯匹配类名更可靠
  • uniq:避免因类被多次加载导致的重复条目
  • 返回格式和原代码一致,均为控制器类名字符串数组

注意事项

  • 开发环境默认不会预加载所有类,若要获取完整的API控制器列表,可在调用list前执行Rails.application.eager_load!(生产环境默认已开启预加载)
  • 若Gem中的控制器是延迟加载的,需确保在调用该方法前已触发其加载逻辑

内容的提问来源于stack exchange,提问作者Anton-Ivanov

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.08 21:32:42