I'm new to developing rails apps, so for the most part here, I've relied heavily only on the rails generate command to make scaffolds for the entire app. While every other part of my app works fine, this one raises an error right after being automatically generated.
the error is as follows:
NoMethodError in ConfigurationsController#index
undefined method `all' for ActiveSupport::Configurable::Configuration:Class
here is the code snippet that contains said no method call
def index
@configurations = Configuration.all
end
and here is the said model in question
class Configuration < ActiveRecord::Base
belongs_to :users, class_name: 'User', foreign_key: 'user_id'
end
I added the belongs_to part... anyway, when I ran it through http://localhost.localhost:3000/users/1/configurations/ that error pops up! (yes, I used nested routes)
So i hit the rails console to check what Configuration.all returns and lo and behold
2.0.0-p247 :004 > Configuration.all
Configuration Load (0.3ms) SELECT "configurations".* FROM "configurations"
=> #<ActiveRecord::Relation [#<Configuration id: 1, user_id: 1, port: 3000, host: "example.org", annoy: 5000, version: "1", machines: nil, created_at: "2013-08-08 02:15:32", updated_at: "2013-08-08 02:15:32">]>
I'm kind of lost as to why that method works in rails console then fails in the html view on my browser. Did i do something wrong?
also, here is the output on webrick in case someone looks for it
Started GET "/users/1/configurations/" for 192.168.1.105 at 2013-08-08 10:24:59 +0800
Processing by ConfigurationsController#index as HTML
Parameters: {"user_id"=>"1"}
Completed 500 Internal Server Error in 1ms
NoMethodError (undefined method `all' for ActiveSupport::Configurable::Configuration:Class):
app/controllers/configurations_controller.rb:8:in `index'
Unfortunately, you created a class whose name is also part of the Rails API (though in a different namespace). Your class happens to be at the top-level namespace, while the Rails class is nested in the ActiveSupport::Configurable
namespace. Which class you'll actually get when you reference Configuration
depends on where the referencing code is located.
To specify that you want the class at top-level namespace, you can refer to your class as ::Configuration
.
Here's a simplified test to demonstrate what's happening:
# Let's say this module & class is defined by a library (e.g. Rails)
module Configurable # analogous to ActiveSupport::Configurable
class Configuration # analogous to ActiveSupport::Configurable::Configuration
end
end
class ControllerBase # analogous to ActionController::Base
# ActionController::Base includes ActiveSupport::Configurable.
# You can confirm this in Rails 4 that this returns true:
# ActionController::Base.included_modules.include? ActiveSupport::Configurable
include Configurable
end
# This is your class and constant
class Configuration
end
class MyController < ControllerBase
# This is analogous to code inside your Controller.
# Inheriting gives you access to the constants in the parent
def wrong_class
Configuration # oops, we wanted the top-level
end
def correct_class
::Configuration
end
end
# top-level scope
p(top_level_access: Configuration.name) # 'Configuration'
p(nested_access: MyController.new.wrong_class.name) # 'Configurable::Configuration'
p(scoped_nested_access: MyController.new.correct_class.name) # 'Configuration'
EDIT - Reply to @maru's comment:
In most cases you can just use Configuration.name
to get the fully-namespaced name of the class. Try this at the console.
If you try Rails.logger.info(Configuration.name)
inside the controller, you'll probably see ActiveSupport::Configurable::Configuration
in the log.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With