首页 > 解决方案 > Rails 5.2.0 中的“无法自动加载常量”错误

问题描述

我正在运行 Rails 5.2.0 应用程序。这LoadError总是出现在重新启动或重新编译后的第一个请求中:

Unable to autoload constant Api::V1::ApplesController, expected /fruits_and_vegetables/app/controllers/api/v1/apples_controller.rb to define it

相关文件:

routes.rb

Rails.application.routes.draw do
  namespace :api do
    namespace :v1 do
      get 'apples', to: 'apples#get'
    end
  end
end

这是文件结构:

 - app
  - controllers
   - api
    - v1
     - apples_controller.rb

里面有什么apples_controller.rb

class Api::V1::ApplesController < ApplicationController
   // stuff
end

StackOverflow 上的一些帖子表明此错误可能是由我的控制器文件中的拼写错误引起的,但事实并非如此。或者,有些人提到了 Rails 的大小写敏感性。但是,如果我尝试在文件或控制器中更改apiv1Api或,Rails 将抛出错误。V1routes.rb

我看到一条评论建议应该运行rails r 'puts ActiveSupport::Dependencies.autoload_paths',如果我在输出列表中没有看到/fruits_and_vegetables/app/controllers/api,则添加config.autoload_paths << Rails.root.join("app/controllers/api")到我的config/application.rb文件中,但似乎不鼓励这样做

有什么想法吗?我在这里看到至少十几个类似的帖子,但似乎没有真正的具体解决方案?

标签: ruby-on-railsapicontrollerautoload

解决方案


当我将 Rails 升级到 5.2.0 版时,我的旧版 Rails 5.1 应用程序代码也发生了同样的(LoadError)错误。修复(对我来说)是添加一个丢失的源文件,它只定义一个子模块(以满足自动加载器)。我将在原始帖子示例的上下文中解释修复。

在原始帖子中,ApplesControllerV1命名空间的一部分。问题是,V1子模块没有(明确)定义。解决方案是在正确的(自动加载)路径上创建一个定义V1模块的文件:

app/controllers/api/v1.rb

module Api
  module V1
  end
end

显然,从 Rails 5.2 开始,自动加载器需要显式定义每个模块命名空间。您可以阅读有关Rails 5.2 常量自动加载的技术细节。

以及对同一问题的相关 SO 答案。


推荐阅读