如何为开发和生产指定不同版本的gem

nPn*_*nPn 5 ruby ruby-on-rails heroku ruby-on-rails-3

为了开发和生产,我需要具有不同版本的gem,因此将以下内容放入了我的gemfile中。

group :development, :test do
  gem 'rspec-rails', '2.11.0'
  gem 'bcrypt-ruby', '3.1.2'
end

group :production do
  gem 'rails_12factor'
  gem 'bcrypt-ruby', '3.0.1'  
end
Run Code Online (Sandbox Code Playgroud)

但是,如果我尝试这样做bundle install,甚至只是rails console我得到上述错误

我试过了

bundle install --without production
Run Code Online (Sandbox Code Playgroud)

但我仍然收到错误消息。仅供参考:我需要这样做,因为我要通过Rails教程,并且在Windows,ruby 2.0.0和bcrypt和Heroku之间会发生冲突,因此我在Windows上使用bcrypt 3.1.2(对active记录gemfile)并在Heroku上使用bcrypt 3.0.1。

请参阅此以获取更多详细信息: Windows上将bcrypt 3.0.1与ruby2.0一起使用时的问题

我基本上做了第一个答案中提到的内容

编辑

###################################################################
Run Code Online (Sandbox Code Playgroud)

正如下面的答案所指出的,我确实应该在生产和开发中都使用相同的版本(即使我只是在学习教程)。我最终要做的是使用猴子修补ActiveModel

gem 'bcrypt-ruby', '3.1.2'
Run Code Online (Sandbox Code Playgroud)

而不是

gem 'bcrypt-ruby', '~> 3.0.0'
Run Code Online (Sandbox Code Playgroud)

在secure_password中。

我通过将以下内容放在lib / secure_password_using_3_1_2.rb中来完成此操作

module ActiveModel
  module SecurePassword
    extend ActiveSupport::Concern

    module ClassMethods

      def has_secure_password
        # Load bcrypt-ruby only when has_secure_password is used.
        # This is to avoid ActiveModel (and by extension the entire framework) being dependent on a binary library.
        #gem 'bcrypt-ruby', '~> 3.0.0'
        gem 'bcrypt-ruby', '3.1.2'
        require 'bcrypt'

        attr_reader :password

        validates_confirmation_of :password
        validates_presence_of     :password_digest

        include InstanceMethodsOnActivation

        if respond_to?(:attributes_protected_by_default)
          def self.attributes_protected_by_default
            super + ['password_digest']
          end
        end
      end
    end
  end
end
Run Code Online (Sandbox Code Playgroud)

然后将以下内容添加到config / environment.rb

require File.expand_path('../../lib/secure_password_using_3_1_2.rb', __FILE__)
Run Code Online (Sandbox Code Playgroud)

Vic*_*roz 6

这个怎么样?

gem "my_gem", ENV["RAILS_ENV"] == "production" ? "2.0" : "1.0"

RAILS_ENV=production bundle
Run Code Online (Sandbox Code Playgroud)


Tim*_*ore 1

简而言之,你不能轻易做到这一点。Bundler 旨在强制所有 gem 在开发和生产之间使用相同的版本。使用不同的版本可能会导致细微的错误。

为什么不想在生产环境中运行 3.1.2?