masciugo
masciugo

Reputation: 1191

can't include modules loaded from lib in Rails 5

In my rails 5 application (in dev environment) I have some modules to be loaded from the lib folder and included in models. So I set in my application.rb

config.autoload_paths += %W(#{config.root}/lib)

the module is something like

lib/surveyable/surveyable.rb

require 'active_support/concern'

module Surveyable
  extend ActiveSupport::Concern

  class_methods do

    def sjs_elements(&block)
      ....
    end
  end

end

which is included in my user model class:

app/models/user.rb

class User < ApplicationRecord

  include Surveyable # <= this doesn't raise any error

  sjs_elements do # <= *** NameError Exception: undefined local variable or method `sjs_elements' for User (call 'User.connection' to establish a connection):Class
     ....
  end

  ....
end

I need to manually require it at the beginning of application.rb to have it working but this violates rails conventions:

require_relative '../lib/surveyable/surveyable'

Upvotes: 0

Views: 1933

Answers (1)

max
max

Reputation: 102036

What you have is a simple misunderstanding of how rails resolves module names. Adding a directory to the autoload path does not cause rails to look recursively through its subdirectories.

In order for rails to properly load the module it would have to be declared as:

# lib/surveyable/surveyable.rb
module Surveyable::Surveyable
  extend ActiveSupport::Concern
end

This is because the autoloader deduces the file path based on module nesting.

Or you can move the file to lib/surveyable.rb.

But since what you are writing seems to be a model concern I would place it in app/models/concerns which is already added to the load path.

Upvotes: 1

Related Questions