Search code examples
ruby-on-railsactivesupportactivesupport-concern

Undefined method in ActiveSupport concern


I have a model that extends ActiveRecord::Base and includes a concern:

class User < ActiveRecord::Base
    include UserConcern

    def self.create_user()
        ...
        results = some_method()
    end

end

UserConcern is stored in the concerns directory:

module UserConcern
    extend ActiveSupport::Concern

    def some_method()
        ...
    end
end

I am getting a run-time error when I try to create a new user by calling the create_user method that looks like this:

undefined method 'some_method' for #<Class:0x000000...>

I have two questions about this:

  1. Why is the some_method undefined? It seems to me that I am properly including it with the statement include UserConcern. Does it have something to do with my User class extending ActiveRecord::Base? Or maybe something to do with the fact that I am calling some_methods() from a class method (i.e. self.create_user())?

  2. Why does the run-time error refer to #<Class:0x000000...> instead of to #<User:0x000000...>?


Solution

  • try it

    models/concerns/user_concern.rb:

    module UserConcern
      extend ActiveSupport::Concern
    
      def some_instance_method
        'some_instance_method'
      end
    
      included do
        def self.some_class_method
          'some_class_method'
        end
      end
    end
    

    models/user.rb:

    class User < ActiveRecord::Base
      include UserConcern
      def self.create_user
        self.some_class_method
      end
    end
    

    rails console:

    user = User.new
    user.some_instance_method
    # => "some_instance_method"
    
    User.some_class_method
    # => "some_class_method"
    
    User.create_user
    # => "some_class_method"
    

    http://api.rubyonrails.org/classes/ActiveSupport/Concern.html