bin/autoproj_install in autoproj-2.0.0.rc15 vs bin/autoproj_install in autoproj-2.0.0.rc16

- old
+ new

@@ -32,10 +32,12 @@ # The configuration hash attr_reader :config # A set of options that should be passed to autoproj when calling it # in a subprocess attr_reader :autoproj_options + # The Ruby interpreter we use for this install + attr_reader :ruby_executable def initialize(root_dir) @root_dir = root_dir if File.file?(autoproj_gemfile_path) @gemfile = File.read(autoproj_gemfile_path) @@ -52,19 +54,20 @@ env['PATH'] = self.class.sanitize_env(ENV['PATH'] || "") env['BUNDLE_GEMFILE'] = [] load_config if config['ruby_executable'] != Gem.ruby - raise "this autoproj installation was already bootstrapped using #{config['ruby_executable']}, but you are currently running under #{Gem.ruby}. Changing the ruby interpreter in a given workspace is not supported" + raise "this autoproj installation was already bootstrapped using #{config['ruby_executable']}, but you are currently running under #{Gem.ruby}. Changing the ruby interpreter in a given workspace is not supported, you need to do a clean bootstrap" end - + @ruby_executable = config['ruby_executable'] @local = false end def env_for_child - result = env.inject(Hash.new) do |h, (k, v)| - h[k] = (v.join(File::PATH_SEPARATOR) if v && !v.empty?) + env.inject(Hash.new) do |h, (k, v)| + h[k] = if v && !v.empty? then v.join(File::PATH_SEPARATOR) + end h end end def apply_env(env) @@ -99,10 +102,12 @@ def autoproj_install_dir; File.join(dot_autoproj, 'autoproj') end # The path to the gemfile used to install autoproj def autoproj_gemfile_path; File.join(autoproj_install_dir, 'Gemfile') end def autoproj_config_path; File.join(dot_autoproj, 'config.yml') end + def shim_path; File.join(dot_autoproj, 'bin') end + # Whether we can access the network while installing def local?; !!@local end # (see #local?) def local=(flag); @local = flag end @@ -159,11 +164,11 @@ ruby_bin = RbConfig::CONFIG['RUBY_INSTALL_NAME'] ruby_bindir = RbConfig::CONFIG['bindir'] candidates = ['gem'] if ruby_bin =~ /^ruby(.+)$/ - candidates << "gem#{$1}" + candidates.unshift "gem#{$1}" end candidates.each do |gem_name| if File.file?(gem_full_path = File.join(ruby_bindir, gem_name)) return gem_full_path @@ -183,24 +188,34 @@ "gem \"utilrb\", \">= 3.0.0.a\""].join("\n") end # Parse the provided command line options and returns the non-options def parse_options(args = ARGV) + default_gem_path = File.join(Dir.home, '.autoproj', 'gems') + self.private_bundler = default_gem_path + self.private_gems = default_gem_path + self.private_autoproj = default_gem_path + options = OptionParser.new do |opt| opt.on '--local', 'do not access the network (may fail)' do @local = true end + opt.on '--public', "install gems in the default RubyGems locations. Consider using this if you don't have a v1 install anymore" do + self.private_bundler = false + self.private_autoproj = false + self.private_gems = false + end opt.on '--private-bundler[=PATH]', 'install bundler locally in the workspace' do |path| self.private_bundler = path || true end opt.on '--private-autoproj[=PATH]', 'install autoproj locally in the workspace' do |path| self.private_autoproj = path || true end opt.on '--private-gems[=PATH]', 'install gems locally in the prefix directory' do |path| self.private_gems = path || true end - opt.on '--private[=PATH]', 'whether bundler, autoproj and the workspace gems should be installed locally in the workspace' do |path| + opt.on '--private[=PATH]', "whether bundler, autoproj and the workspace gems should be installed locally in the workspace. This is the default, with a path of #{default_gem_path}" do |path| self.private_bundler = path || true self.private_autoproj = path || true self.private_gems = path || true end opt.on '--version=VERSION_CONSTRAINT', String, 'use the provided string as a version constraint for autoproj' do |version| @@ -233,19 +248,20 @@ local = ['--local'] if local? result = system( env_for_child.merge('GEM_PATH' => "", 'GEM_HOME' => bundler_gem_home), - gem_program, 'install', '--no-document', '--no-format-executable', + Gem.ruby, gem_program, 'install', '--no-document', '--no-format-executable', *local, "--bindir=#{File.join(bundler_gem_home, 'bin')}", 'bundler') - if !result + if result + File.join(bundler_gem_home, 'bin', 'bundler') + else STDERR.puts "FATAL: failed to install bundler in #{dot_autoproj}" - return + nil end - File.join(bundler_gem_home, 'bin', 'bundler') end def find_bundler clean_env = env_for_child if bundler = find_in_clean_path('bundler', gem_bindir) @@ -257,15 +273,15 @@ STDERR.puts "installing it now ..." bundler = install_bundler if !bundler if ENV['PATH'] != clean_path STDERR.puts " it appears that you already have some autoproj-generated env.sh loaded" - STDERR.puts " - if you are running 'autoproj upgrade', please contact the autoproj author at https://github.com/rock-core/autoproj/issues/new" - STDERR.puts " - if you are running an install, try again in a console where the env.sh is not loaded" + STDERR.puts " - if you are upgrading a v1 install, please contact the autoproj author at https://github.com/rock-core/autoproj/issues/new" + STDERR.puts " - if you are running a fresh install, try again in a console where the env.sh is not loaded" exit 1 else - STDERR.puts " the recommended action is to install it manually first by running 'gem install bundler'" + STDERR.puts " you might want to try and install it manually first by running 'gem install bundler'" STDERR.puts " or call this command again with --private-bundler to have it installed in the workspace" exit 1 end end @@ -290,11 +306,11 @@ opts = Array.new opts << '--local' if local? if private_autoproj? clean_env['GEM_PATH'] = bundler_gem_home clean_env['GEM_HOME'] = nil - opts << "--clean" << "--path=#{autoproj_gem_home}" + opts << "--path=#{autoproj_gem_home}" end binstubs_path = File.join(autoproj_install_dir, 'bin') result = system(clean_env.merge('GEM_HOME' => autoproj_gem_home), Gem.ruby, bundler, 'install', "--gemfile=#{autoproj_gemfile_path}", @@ -309,11 +325,11 @@ ensure self.class.clean_binstubs(binstubs_path) end def self.clean_binstubs(binstubs_path) - %w{bundler bundle}.each do |bundler_bin| + %w{bundler bundle rake thor}.each do |bundler_bin| path = File.join(binstubs_path, bundler_bin) if File.file?(path) FileUtils.rm path end end @@ -407,10 +423,24 @@ else raise "FATAL: cannot run #{Gem.ruby} -e 'puts Gem.bindir'" end end + def save_ruby_and_bundler_shims(bundler_path) + FileUtils.mkdir_p shim_path + File.open(File.join(shim_path, 'bundler'), 'w') do |io| + io.puts "#! /bin/sh" + io.puts "exec #{ruby_executable} #{bundler_path} \"$@\"" + end + FileUtils.chmod 0755, File.join(shim_path, 'bundler') + File.open(File.join(shim_path, 'ruby'), 'w') do |io| + io.puts "#! /bin/sh" + io.puts "exec #{ruby_executable} \"$@\"" + end + FileUtils.chmod 0755, File.join(shim_path, 'ruby') + end + def install if private_bundler? puts "Installing bundler in #{bundler_gem_home}" if !(bundler = install_bundler) exit 1 @@ -418,10 +448,12 @@ elsif bundler = find_bundler puts "Detected bundler at #{bundler}" else exit 1 end + save_ruby_and_bundler_shims(bundler) + env['PATH'].unshift shim_path save_gemfile puts "Installing autoproj in #{dot_autoproj}" install_autoproj(bundler) end @@ -468,14 +500,25 @@ def run_autoproj(*args) system env_for_child.merge('BUNDLE_GEMFILE' => autoproj_gemfile_path), Gem.ruby, autoproj_path, *args, *autoproj_options end + def v1_workspace? + File.file?(File.join(root_dir, 'autoproj', 'config.yml')) && + !File.directory?(File.join(root_dir, '.autoproj')) + end + def stage1 + if v1_workspace? && File.file?(v1_envsh = File.join(root_dir, 'env.sh')) + FileUtils.cp v1_envsh, 'env.sh-autoproj-v1' + end FileUtils.mkdir_p dot_autoproj save_config install + rescue Exception + FileUtils.rm_rf dot_autoproj + raise end def call_stage2 clean_env = env_for_child stage2_vars = clean_env.map { |k, v| "#{k}=#{v}" } @@ -488,9 +531,14 @@ def stage2(*vars) require 'autobuild' puts "saving env.sh and .autoproj/env.sh" save_env_sh(*vars) if !system(Gem.ruby, autoproj_path, 'envsh', *autoproj_options) + exit 1 + end + # This is really needed on an existing install to install the + # gems that were present in the v1 layout + if !system(Gem.ruby, autoproj_path, 'osdeps') exit 1 end end end end