Ответ 1
Вы можете использовать instance_eval
module CommonScopes
extend ActiveSupport::Concern
def self.included(klass)
klass.instance_eval do
scope :ordered_for_display, order("#{self.to_s.tableize}.rank asc")
end
end
end
Я хочу высушить несколько моделей, перемещая общие области в модуль, что-то вроде:
module CommonScopes
extend ActiveSupport::Concern
module ClassMethods
scope :ordered_for_display, order("#{self.to_s.tableize}.rank asc")
end
end
Я также хочу создать общие спецификации, которые проверяют модуль. К сожалению, когда я пытаюсь включить общий объём в мою модель, я получаю:
undefined method `order' for CommonScopes::ClassMethods:Module
Любые идеи? Спасибо!
Вы можете использовать instance_eval
module CommonScopes
extend ActiveSupport::Concern
def self.included(klass)
klass.instance_eval do
scope :ordered_for_display, order("#{self.to_s.tableize}.rank asc")
end
end
end
Как и в rails 4 синтаксисе видимости, вы можете просто использовать лямбда для задержки выполнения кода (также работает в rails 3):
module CommonScopes
extend ActiveSupport::Concern
included do
scope :ordered_for_display, -> { order("#{self.to_s.tableize}.rank asc") }
end
end
Поскольку ваш метод scope
вызывается немедленно, когда ваш модуль анализируется Ruby и он недоступен из вашего модуля CommonScopes
..
Но вы можете заменить вызов области вызовом методом класса:
module CommonScopes
extend ActiveSupport::Concern
module ClassMethods
def ordered_for_display
order("#{self.to_s.tableize}.rank asc")
end
end
end