Повторное открытие классов движка Rails 3 из родительского приложения - PullRequest
7 голосов
/ 01 марта 2011

В настоящее время вы не можете снова открыть классы Engine, содержащиеся в каталоге /app движка, просто добавив этот же класс в каталог /app родительского приложения.Например:

/my_engine/app/controllers/users_controller.rb
/my_app/app/controllers/users_controller.rb

Файл из my_engine даже не загрузится, если в родительском приложении есть файл с таким же именем.Подробнее здесь:

http://www.cowboycoded.com/2011/02/28/why-you-cant-reopen-rails-3-engine-classes-from-the-parent-app/

Я ищу обходной путь, который позволил бы мне удалить то же имя файла / класса по тому же пути, что и родительское приложение, и открыть заново вместо перезаписи.класс.Может быть, я упускаю что-то очевидное.Я могу сделать эту работу с отдельным файлом (другое имя файла), который использует class_eval, но я не очень доволен этим решением.Есть идеи по поводу элегантного решения для этого?

Мне также интересно, есть ли причина этого ограничения, или это просто результат того, как rails загружает файлы (см. Включенную ссылку), а не преднамеренно.Мне кажется, что изменение поведения двигателей для возможности повторного открытия классов таким способом было бы хорошей особенностью в рельсах.Я знаю, что это сначала смутило меня, и я уверен, что другие разработчики тоже будут бороться с этой проблемой.

1 Ответ

9 голосов
/ 20 марта 2012

В Rails 3.2.2 / Ruby 1.9 включите перезагрузку плагинов, затем потребуйте класс в движке, используя require_dependency, прежде чем снова открыть класс и добавить функциональность.Это работает даже в среде разработки (т.е. перезагрузка класса).

# development.rb
config.reload_plugins = true 

# app/controllers/my_engine/documents_controller.rb
require_dependency MyEngine::Engine.root.join('app', 'controllers', 'my_engine', 'documents_controller').to_s

module MyEngine
  class DocumentsController
    def show
      render :text => 'different'
    end
  end
end
...