4

我正在尝试通过 Rails 3 模板设置 RVM gemset,然后通过模板中的命令开始使用 gemset 并将 gems 安装到新的 gemset 中(以应用程序命名)。这似乎无法正常工作。新的 gem 没有安装到 gemset 中,实际上 gemset 根本没有被创建。

以下是从模板文件中提取的一些相关代码:

rvmrc = <<-RVMRC
rvm_gemset_create_on_use_flag=1
rvm_trust_rvmrcs=1
rvm gemset use #{app_name}
RVMRC

create_file ".rvmrc", rvmrc

然后,再往前走:

run "cd path/to/new/app"
run 'gem install bundler --pre'
run 'bundle install'

我还尝试了一个不同的版本:

inside app_name do 
  run 'gem install bundler --pre'
  run 'bundle install'
end

第三个版本:

inside app_name do 
  run "rvm gemset create #{app_name} && rvm gemset use #{app_name}"
  run 'gem install bundler --pre'
  run 'bundle install'
end

如果我只是在模板运行cd 进入控制台中的新应用程序文件夹,它就可以完美地工作。我收到 RVM 消息:“信息:现在使用 gemset 'test_app'。” 如果我此时运行 bundle install 命令,gems 会正确安装到新的 gemset 中,但是如果我只是从模板文件中运行这些命令,我​​将无法获得相同的结果。

应用程序生成器的日志这样说:

 run    cd ~/rails3_sites/test_app from "."
 run    gem install bundler --pre from "./test_app"
 run    bundle install from "./test_app"

我错过了什么?任何帮助是极大的赞赏。顺便说一句,我正在使用 ruby​​ 1.9.2。

谢谢,

〜安德里亚

4

4 回答 4

6

您可以在不使用 rvm ruby​​ api 的情况下做到这一点。这是我们模板中的一个片段

current_ruby = %x{rvm list}.match(/^=>\s+(.*)\s\[/)[1].strip
run "rvm gemset create #{app_name}"
run "rvm #{current_ruby}@#{app_name} gem install bundler"
run "rvm #{current_ruby}@#{app_name} -S bundle install"

file ".rvmrc", <<-END
rvm use #{current_ruby}@#{app_name}
END

这将找到当前选定的 ruby​​,使用该名称创建一个 gemset,然后将 bundler 安装到其中。最后安装 Gemfile 中指定的 gem 并创建一个 .rvmrc 文件。

您可以在我的 github 存储库中看到整个模板https://github.com/andyh/Template

于 2011-03-01T16:42:00.237 回答
3

我最近重新审视了这个问题。它可以使用 RVM Ruby API 来完成。我将 API 调用放在与模板分开的 Ruby 文件中,如下所示:

rvm_lib_path = "#{`echo $rvm_path`.strip}/lib"
$LOAD_PATH.unshift(rvm_lib_path) unless $LOAD_PATH.include?(rvm_lib_path)
require 'rvm'

rvm_ruby = ARGV[0]
app_name = ARGV[1]

unless rvm_ruby
  puts "\n You need to specify a which rvm rubie to use."
end

unless app_name
  puts "\n You need to name your app."
end

@env = RVM::Environment.new(rvm_ruby)

puts "Creating gemset #{app_name} in #{rvm_ruby}"
@env.gemset_create(app_name)
puts "Now using gemset #{app_name}"
@env.gemset_use!(app_name)

puts "Installing bundler gem."
puts "Successfully installed bundler" if @env.system("gem", "install", "bundler")
puts "Installing rails gem."
puts "Successfully installed rails" if @env.system("gem", "install", "rails")

template_file = File.join(File.expand_path(File.dirname(__FILE__)), 'templater.rb')
system("rails new #{app_name} -JT -d mysql -m #{template_file}")

如果有人感兴趣,我已经写了一篇关于 Rails 3 模板的博客文章,其中更详细地介绍了这一点:

制作自定义 Rails 3 模板

于 2010-10-12T00:25:17.190 回答
0
rvm_lib_path = "#{`echo $rvm_path`.strip}/lib"
$LOAD_PATH.unshift(rvm_lib_path) unless $LOAD_PATH.include?(rvm_lib_path)
require 'rvm'

rvm_ruby = ARGV[0]
app_name = ARGV[1]

unless rvm_ruby
  puts "\n You need to specify a which rvm rubie to use."
end

unless app_name
  puts "\n You need to name your app."
end

@env = RVM::Environment.new(rvm_ruby)
ENV['RVM_RUBY'] = rvm_ruby

puts "Creating gemset #{app_name} in #{rvm_ruby}"
@env.gemset_create(app_name)
puts "Now using gemset #{app_name}"
@env = RVM::Environment.new("#{rvm_ruby}@#{app_name}")


puts "Installing bundler gem."
puts "Successfully installed bundler" if @env.system("gem install bundler --no-ri --no-rdoc")
puts "Installing rails gem."
puts "Successfully installed rails" if @env.system("gem install rails --no-ri --no-rdoc")

template_file = File.join(File.expand_path(File.dirname(__FILE__)), 'template.rb')
system("rvm #{rvm_ruby}@#{app_name} exec rails new #{app_name} -JT -d mysql -m #{template_file}")

system("mv #{app_name} #{app_name}.git")

作品。

rvm 存在一个错误,其中 @rvm_environment 实例变量没有使用 gemset_use 正确设置!因此,如果您执行 @env.send(:instance_variable_get, :@rvm_environment) 它不会反映更新的 gemset,因此当您调用系统时,它不会在正确的环境/gemset 中执行。将 @env var 重新设置为新的 RVM::Environment 实例可以解决问题。

于 2010-10-29T01:30:20.443 回答
0

Andrea,出色的方法和精彩的博客文章。但是,RVM 引导程序不起作用。

以下是在 irb 中创建新 gemset 的大致相同步骤:

ree-1.8.7-2010.02 > require 'rvm'
true
ree-1.8.7-2010.02 > @env = RVM::Environment.new('ree')
#<RVM::Environment environment_name="ree">
ree-1.8.7-2010.02 > @env.gemset_create('some_gemset')
true
ree-1.8.7-2010.02 > @env.gemset_use!('some_gemset')
true
ree-1.8.7-2010.02 > @env.gemset_name
nil
ree-1.8.7-2010.02 > 

注意最后一行尝试读取当前 gemset,它是 nil(终端会话使用默认 gemset,因此它是空的)。我希望它显示“some_gemset”。运行脚本时,我基本上得到了相同的行为:它将 gem 安装到我在运行脚本时碰巧所在的任何 gemset 中。

对这种奇怪的行为有什么想法或建议吗?

于 2010-10-28T11:25:28.413 回答