Движки Rails 3.1: отличие my_engine.gemspec, add_dependency, add_development_dependency и Gemfile

Просто из любопытства... в моем предыдущем посте Движок Rails3.1: не удается заставить SLIM или HAML работать в тестовом/фиктивном приложении Я спросил, где сказать Ruby, чтобы он использовал какой-то драгоценный камень в моем test/dummy приложении.

(Очевидный?) Ответ заключался в том, чтобы просто поместить его в Gemfile моего движка. Это работает, но мне немного неудобно, потому что в сообщении Иегуды Каца Уточнение ролей .gemspec и Gemfile он упоминает, что...

... при разработке гема Gemfile "Gemfile гема должен содержать исходный код Rubygems и одну строку gemspec".

С другой стороны, в Gemfile моего движка (который был сгенерирован с использованием Rails rails plugin new my_engine) есть:

# jquery-rails is used by the dummy application
gem "jquery-rails"

Так что это кажется правильным. Обновление: нет! Посмотрите на мой ответ ниже...

Тем не менее, где-то еще на StackOverflow Я вижу, что решение для этого просто требует необходимого драгоценного камня в config/application.rb, а https://stackoverflow.com/questions/5159607/rails-engine-gems-dependencies-how-to-load-them- в приложении сказано, что лучше всего помещать его в lib/<your_engine>/engine.rb file.

И вот моя мысль: почему приложение test/dummy просто автоматически не требует все драгоценные камни, указанные в файле .gemspec? Мы даже сообщаем гему, какие гемы использовать для производства, а какие для режима разработки, явно используя add_dependency и add_development_dependency, поэтому я не вижу причин, по которым test/dummy этого не делает.

Итак, вот последний вопрос: где именно я должен указать Ruby использовать гем в моем приложении test/dummy? Я НЕ ХОЧУ ЗАСТАВЛЯТЬ РУБИ ИСПОЛЬЗОВАТЬ ДРАГОЦЕННЫЙ КАМЕНЬ ТАКЖЕ В ПРИЛОЖЕНИИ HOST.


person Joshua Muheim    schedule 20.09.2012    source источник
comment
+1 к вопросу; жду ответов :-)   -  person Atastor    schedule 20.09.2012
comment
добавил еще немного интересной информации к вопросу с моими текущими выводами (см. Обновление).   -  person Joshua Muheim    schedule 20.09.2012
comment
Спасибо за обновления. Дал бы +1 за это, но не могу сделать это дважды ;-) Однако ситуация с группой gemfile кажется странной.   -  person emrass    schedule 23.09.2012


Ответы (3)


Я думаю, что правильный способ действий следующий:

Двигатель — обычный драгоценный камень. Когда вы разрабатываете гем, вы помещаете его зависимости в файл gemspec. Если вы используете пакет, вы, как разработчик, можете затем создать файл .lock с конкретными версиями, у которых у вас не было проблем. Но того, что зависимости объявлены в gemspec, недостаточно для их использования, вы должны require их использовать в своем коде gem. Когда они требуются, если гем используется с пакетом, используются версии .lock.

В двигателе, как и в любом другом камне, то же самое. Вы определяете свои зависимости в файле gemspec и запускаете bundle install, но этого недостаточно для их использования. Вы должны потребовать их, например, в lib/my_engine.rb.

Например:

# File: my_engine.rspec
# ...
s.add_dependency `slim_rails`, ' ~>1.0'

# ...

# File: lib/my_engine.rb
require "my_engine/engine"
require "slim-rails"

module MyEngine
end

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

Зависимости Gem внутри движка должны быть указаны в файле .gemspec в корне движка. Причина в том, что движок может быть установлен как гем. Если бы внутри Gemfile были указаны зависимости, они не были бы распознаны традиционной установкой gem и, следовательно, не были бы установлены, что привело бы к сбоям в работе движка.

person Waiting for Dev...    schedule 27.07.2013
comment
Спасибо за ответ (извините, я забыл об этом посте). Я все еще немного сбит с толку. - person Joshua Muheim; 17.02.2014

Вот что я узнал до сих пор.

Внутри движка (созданного с помощью rails plugin new my_engine) вы должны указать необходимые гемы только в файле my_engine.gemspec, поскольку затем на них ссылаются из файла test/dummy/Gemfile с помощью gemspec.

Вот сгенерированный контент test/dummy/Gemfile:

source "http://rubygems.org"

# Declare your gem's dependencies in simple_view_helpers.gemspec.
# Bundler will treat runtime dependencies like base dependencies, and
# development dependencies will be added by default to the :development group.
gemspec

# jquery-rails is used by the dummy application
gem "jquery-rails"

# Declare any dependencies that are still in development here instead of in
# your gemspec. These might include edge Rails or gems from your path or
# Git. Remember to move these dependencies to your gemspec before releasing
# your gem to rubygems.org.

# To use debugger
# gem 'debugger'

Что здесь делает строка gem "jquery-rails", я действительно не знаю, кажется, полностью противоречит тому, что предлагается в комментариях. С другой стороны, когда я пытаюсь использовать гем SLIM (вместо ERB) в своем тесте /dummy application, кажется, мне нужно указать его в Gemfile, иначе оно не будет работать. Все еще немного сбивает с толку этот материал...

person Joshua Muheim    schedule 27.09.2012
comment
Странно, в более новых версиях Rails (3.2.11) Gemfile для двигателей находится в корневом каталоге, а в тестовом фиктивном приложении его нет. Это заставило бы меня поверить, что зависимости движка находятся в gemspec, а зависимости фиктивного приложения помещаются в Gemfile. - person James; 17.01.2013

TL;DR:

Не используйте Gemfile при разработке Engine. Поместите все в gemspec вашего движка и позвольте движку самому требовать все, что ему нужно.


почему тестовое/фиктивное приложение просто автоматически не требует всех драгоценных камней, указанных в файле .gemspec?

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

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

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

говорят, что просто требуется необходимый драгоценный камень в config/application.rb

Это также может маскировать зависимости вашего движка во время выполнения, поэтому лучше этого не делать.

Итак, вот последний вопрос: где именно я должен сказать Ruby использовать драгоценный камень в моем тестовом/фиктивном приложении? Я не хочу заставлять рубин использовать драгоценный камень также в хост-приложении.

Если этот гем нужен только для тестов, укажите его в помощнике по тесту/спецификации.

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

Джеймс: Это наводит меня на мысль, что зависимости движка находятся в спецификации gem, а зависимости фиктивного приложения — в Gemfile.

Заглушка сборщика фиктивного приложения фактически ссылается на собственный отсутствующий Gemfile фиктивного приложения. Так что я думаю, что это опущено намеренно. И это имеет смысл.

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

Если вы действительно хотите иметь возможность повторно использовать свой движок и поместить его в любое пустое новое приложение Rails, ваше фиктивное приложение должно быть именно таким: пустым новым приложением Rails.

person Janosch    schedule 23.11.2015