2015-04-15 2 views
4

Мне нужно уметь видеть всех потомков класса от контроллера, когда я вхожу в консоль рельсов локально. У меня есть этот Api::BaseController, от которого все мои контроллеры Api унаследованы. Проблема, с которой я сталкиваюсь, - это когда я перехожу к консоли rails, чтобы проверить, какой контроллер Api у потомков, он появляется пустым, пока я не позвоню им. Вероятно, это связано с тем, как классы в разработке не загружаются, и они не кэшируются локально.Загрузка потомков классов в развитие рельсов

sample_app$ rails c 
Loading development environment (Rails 4.2.0) 
2.1.5 :001 > Api::BaseController.descendants 
=> [] 
2.1.5 :002 > Api::V1::FoosController 
=> Api::V1::FoosController 
2.1.5 :003 > Api::BaseController.descendants 
=> [Api::V1::FoosController] 

Из этого примера, вы можете видеть, когда я называю потомков на Api::BaseController в первый раз, это пустой массив. После вызова одного из контроллеров этот класс будет загружен и будет отображаться как потомок. В этом случае может быть любое количество контроллеров в V1, а также V2, V3 и т.д. ...

Как глупой уродливые взломать, я мог бы сделать

Dir.glob("#{Rails.root.join('app', 'controllers', 'api', 'v1')}/**/*.rb").each(&method(:require_dependency)) 

, но я не хочу писать каждый раз, когда я вхожу в консоль. Я также работаю над драгоценным камнем, и определенно не хочу вставлять этот код в свой драгоценный камень.

Другой вариант - это классы кэширования в разработке, но это вызывает огромные проблемы. У кого-нибудь есть идеи?

Редактировать Другой вариант - позвонить по телефону Rails.application.eager_load!. Этот параметр будет работать нормально, если я могу указать только контроллеры в моей папке API. Тогда мне не нужно было бы загружать все приложение, а просто небольшое подмножество контроллеров, которые мне нужны.

ответ

3

Я нашел следующее сообщение: http://avinmathew.com/using-rails-descendants-method-in-development/

Короче он говорит следующее:

В enviroments/development.rb добавить следующее:

config.eager_load_paths += Dir['path/to/files/*.rb'] 
ActionDispatch::Reloader.to_prepare do 
    Dir['path/to/files/*.rb'].each {|file| require_dependency file} 
end 

Первая линия добавить путь, который должен быть загружен, когда вы запускаете свое приложение (или консоль) , а остальные передаете рельсы, которые перезагружают классы по каждому запросу.

+0

T мотки. Это я и делал. Я просто хватаю всех контроллеров в api и охотно загружаю их. Я не думаю, что это повлияет на производительность, просто время загрузки немного увеличивается. Я в основном просто вырыл то, что делает метод 'eager_load!', И изменил путь – jeremywoertink

+0

Если вы используете Rails 5, часть перезагрузки теперь должна выглядеть так: Rails.application.reloader.to_prepare do Dir ["path/to/files/*. rb "]. each {| file | require_dependency file} end –

0

Ваш лучший выбор может состоять в том, чтобы посмотреть Rails.application.railties, в котором хранится список инициализаторов. Rails.application.eager_load! звонит eager_load! по каждому из них. Возможно, дело в том, чтобы найти правильный.

Если вы планируете создавать плагины для рельсов, возможно, есть очень простой способ получить доступ к инициализаторам, созданным вашим плагином. This blog обсуждает создание инициализаторов для плагинов, что может помочь.

Смежные вопросы