mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
[rubygems/rubygems] Support binstubs with --enable-load-relative
prolog
32a5e9057a
This commit is contained in:
parent
044b0ae8e0
commit
7d42b442bb
2 changed files with 208 additions and 66 deletions
|
@ -220,7 +220,17 @@ class Gem::Installer
|
||||||
existing = nil
|
existing = nil
|
||||||
|
|
||||||
File.open generated_bin, 'rb' do |io|
|
File.open generated_bin, 'rb' do |io|
|
||||||
next unless io.gets =~ /^#!/ # shebang
|
line = io.gets
|
||||||
|
shebang = /^#!.*ruby/
|
||||||
|
|
||||||
|
if load_relative_enabled?
|
||||||
|
until line.nil? || line =~ shebang do
|
||||||
|
line = io.gets
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
next unless line =~ shebang
|
||||||
|
|
||||||
io.gets # blankline
|
io.gets # blankline
|
||||||
|
|
||||||
# TODO detect a specially formatted comment instead of trying
|
# TODO detect a specially formatted comment instead of trying
|
||||||
|
@ -585,7 +595,6 @@ class Gem::Installer
|
||||||
#
|
#
|
||||||
|
|
||||||
def shebang(bin_file_name)
|
def shebang(bin_file_name)
|
||||||
ruby_name = ruby_install_name if @env_shebang
|
|
||||||
path = File.join gem_dir, spec.bindir, bin_file_name
|
path = File.join gem_dir, spec.bindir, bin_file_name
|
||||||
first_line = File.open(path, "rb") {|file| file.gets } || ""
|
first_line = File.open(path, "rb") {|file| file.gets } || ""
|
||||||
|
|
||||||
|
@ -614,14 +623,12 @@ class Gem::Installer
|
||||||
end
|
end
|
||||||
|
|
||||||
"#!#{which}"
|
"#!#{which}"
|
||||||
elsif not ruby_name
|
elsif @env_shebang
|
||||||
"#!#{Gem.ruby}#{opts}"
|
|
||||||
elsif opts
|
|
||||||
"#!/bin/sh\n'exec' #{ruby_name.dump} '-x' \"$0\" \"$@\"\n#{shebang}"
|
|
||||||
else
|
|
||||||
# Create a plain shebang line.
|
# Create a plain shebang line.
|
||||||
@env_path ||= ENV_PATHS.find {|env_path| File.executable? env_path }
|
@env_path ||= ENV_PATHS.find {|env_path| File.executable? env_path }
|
||||||
"#!#{@env_path} #{ruby_name}"
|
"#!#{@env_path} #{ruby_install_name}"
|
||||||
|
else
|
||||||
|
"#{bash_prolog_script}#!#{Gem.ruby}#{opts}"
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -980,4 +987,29 @@ TEXT
|
||||||
def ruby_install_name
|
def ruby_install_name
|
||||||
rb_config["ruby_install_name"]
|
rb_config["ruby_install_name"]
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def load_relative_enabled?
|
||||||
|
rb_config["LIBRUBY_RELATIVE"] == 'yes'
|
||||||
|
end
|
||||||
|
|
||||||
|
def bash_prolog_script
|
||||||
|
if load_relative_enabled?
|
||||||
|
script = +<<~EOS
|
||||||
|
bindir="${0%/*}"
|
||||||
|
EOS
|
||||||
|
|
||||||
|
script << %Q(exec "$bindir/#{ruby_install_name}" "-x" "$0" "$@"\n)
|
||||||
|
|
||||||
|
<<~EOS
|
||||||
|
#!/bin/sh
|
||||||
|
# -*- ruby -*-
|
||||||
|
_=_\\
|
||||||
|
=begin
|
||||||
|
#{script.chomp}
|
||||||
|
=end
|
||||||
|
EOS
|
||||||
|
else
|
||||||
|
""
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -18,11 +18,12 @@ class TestGemInstaller < Gem::InstallerTestCase
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_app_script_text
|
def test_app_script_text
|
||||||
installer = setup_base_installer
|
load_relative "no" do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, ''
|
util_make_exec @spec, ''
|
||||||
|
|
||||||
expected = <<-EOF
|
expected = <<-EOF
|
||||||
#!#{Gem.ruby}
|
#!#{Gem.ruby}
|
||||||
#
|
#
|
||||||
# This file was generated by RubyGems.
|
# This file was generated by RubyGems.
|
||||||
|
@ -52,10 +53,11 @@ else
|
||||||
gem "a", version
|
gem "a", version
|
||||||
load Gem.bin_path("a", "executable", version)
|
load Gem.bin_path("a", "executable", version)
|
||||||
end
|
end
|
||||||
EOF
|
EOF
|
||||||
|
|
||||||
wrapper = installer.app_script_text 'executable'
|
wrapper = installer.app_script_text 'executable'
|
||||||
assert_equal expected, wrapper
|
assert_equal expected, wrapper
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_check_executable_overwrite
|
def test_check_executable_overwrite
|
||||||
|
@ -724,17 +726,19 @@ gem 'other', version
|
||||||
def test_generate_bin_uses_default_shebang
|
def test_generate_bin_uses_default_shebang
|
||||||
pend "Symlinks not supported or not enabled" unless symlink_supported?
|
pend "Symlinks not supported or not enabled" unless symlink_supported?
|
||||||
|
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
installer.wrappers = true
|
installer.wrappers = true
|
||||||
util_make_exec
|
util_make_exec
|
||||||
|
|
||||||
installer.generate_bin
|
installer.generate_bin
|
||||||
|
|
||||||
default_shebang = Gem.ruby
|
default_shebang = Gem.ruby
|
||||||
shebang_line = File.open("#{@gemhome}/bin/executable") {|f| f.readlines.first }
|
shebang_line = File.open("#{@gemhome}/bin/executable") {|f| f.readlines.first }
|
||||||
assert_match(/\A#!/, shebang_line)
|
assert_match(/\A#!/, shebang_line)
|
||||||
assert_match(/#{default_shebang}/, shebang_line)
|
assert_match(/#{default_shebang}/, shebang_line)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_generate_bin_with_dangling_symlink
|
def test_generate_bin_with_dangling_symlink
|
||||||
|
@ -1804,13 +1808,15 @@ gem 'other', version
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang
|
def test_shebang
|
||||||
installer = setup_base_installer
|
load_relative "no" do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/ruby"
|
util_make_exec @spec, "#!/usr/bin/ruby"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby}", shebang
|
assert_equal "#!#{Gem.ruby}", shebang
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_process_options
|
def test_process_options
|
||||||
|
@ -1844,42 +1850,80 @@ gem 'other', version
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_arguments
|
def test_shebang_arguments
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/ruby -ws"
|
util_make_exec @spec, "#!/usr/bin/ruby -ws"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby} -ws", shebang
|
assert_equal "#!#{Gem.ruby} -ws", shebang
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_shebang_arguments_with_load_relative
|
||||||
|
load_relative 'yes' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
|
util_make_exec @spec, "#!/usr/bin/ruby -ws"
|
||||||
|
|
||||||
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
|
shebang_lines = shebang.split "\n"
|
||||||
|
|
||||||
|
assert_equal "#!/bin/sh", shebang_lines.shift
|
||||||
|
assert_includes shebang_lines, "#!#{Gem.ruby} -ws"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_empty
|
def test_shebang_empty
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, ''
|
util_make_exec @spec, ''
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
assert_equal "#!#{Gem.ruby}", shebang
|
assert_equal "#!#{Gem.ruby}", shebang
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_env
|
def test_shebang_env
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/env ruby"
|
util_make_exec @spec, "#!/usr/bin/env ruby"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby}", shebang
|
assert_equal "#!#{Gem.ruby}", shebang
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_env_arguments
|
def test_shebang_env_arguments
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/env ruby -ws"
|
util_make_exec @spec, "#!/usr/bin/env ruby -ws"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby} -ws", shebang
|
assert_equal "#!#{Gem.ruby} -ws", shebang
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_shebang_env_arguments_with_load_relative
|
||||||
|
load_relative 'yes' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
|
util_make_exec @spec, "#!/usr/bin/env ruby -ws"
|
||||||
|
|
||||||
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
|
shebang_lines = shebang.split "\n"
|
||||||
|
|
||||||
|
assert_equal "#!/bin/sh", shebang_lines.shift
|
||||||
|
assert_includes shebang_lines, "#!#{Gem.ruby} -ws"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_env_shebang
|
def test_shebang_env_shebang
|
||||||
|
@ -1897,63 +1941,120 @@ gem 'other', version
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_nested
|
def test_shebang_nested
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/opt/local/ruby/bin/ruby"
|
util_make_exec @spec, "#!/opt/local/ruby/bin/ruby"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby}", shebang
|
assert_equal "#!#{Gem.ruby}", shebang
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_nested_arguments
|
def test_shebang_nested_arguments
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/opt/local/ruby/bin/ruby -ws"
|
util_make_exec @spec, "#!/opt/local/ruby/bin/ruby -ws"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby} -ws", shebang
|
assert_equal "#!#{Gem.ruby} -ws", shebang
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_shebang_nested_arguments_with_load_relative
|
||||||
|
load_relative 'yes' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
|
util_make_exec @spec, "#!/opt/local/ruby/bin/ruby -ws"
|
||||||
|
|
||||||
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
|
shebang_lines = shebang.split "\n"
|
||||||
|
|
||||||
|
assert_equal "#!/bin/sh", shebang_lines.shift
|
||||||
|
assert_includes shebang_lines, "#!#{Gem.ruby} -ws"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_version
|
def test_shebang_version
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/ruby18"
|
util_make_exec @spec, "#!/usr/bin/ruby18"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby}", shebang
|
assert_equal "#!#{Gem.ruby}", shebang
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_version_arguments
|
def test_shebang_version_arguments
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/ruby18 -ws"
|
util_make_exec @spec, "#!/usr/bin/ruby18 -ws"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby} -ws", shebang
|
assert_equal "#!#{Gem.ruby} -ws", shebang
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_shebang_version_arguments_with_load_relative
|
||||||
|
load_relative 'yes' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
|
util_make_exec @spec, "#!/usr/bin/ruby18 -ws"
|
||||||
|
|
||||||
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
|
shebang_lines = shebang.split "\n"
|
||||||
|
|
||||||
|
assert_equal "#!/bin/sh", shebang_lines.shift
|
||||||
|
assert_includes shebang_lines, "#!#{Gem.ruby} -ws"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_version_env
|
def test_shebang_version_env
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/env ruby18"
|
util_make_exec @spec, "#!/usr/bin/env ruby18"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby}", shebang
|
assert_equal "#!#{Gem.ruby}", shebang
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_version_env_arguments
|
def test_shebang_version_env_arguments
|
||||||
installer = setup_base_installer
|
load_relative 'no' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
util_make_exec @spec, "#!/usr/bin/env ruby18 -ws"
|
util_make_exec @spec, "#!/usr/bin/env ruby18 -ws"
|
||||||
|
|
||||||
shebang = installer.shebang 'executable'
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
assert_equal "#!#{Gem.ruby} -ws", shebang
|
assert_equal "#!#{Gem.ruby} -ws", shebang
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_shebang_version_env_arguments_with_load_relative
|
||||||
|
load_relative 'yes' do
|
||||||
|
installer = setup_base_installer
|
||||||
|
|
||||||
|
util_make_exec @spec, "#!/usr/bin/env ruby18 -ws"
|
||||||
|
|
||||||
|
shebang = installer.shebang 'executable'
|
||||||
|
|
||||||
|
shebang_lines = shebang.split "\n"
|
||||||
|
|
||||||
|
assert_equal "#!/bin/sh", shebang_lines.shift
|
||||||
|
assert_includes shebang_lines, "#!#{Gem.ruby} -ws"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def test_shebang_custom
|
def test_shebang_custom
|
||||||
|
@ -2283,4 +2384,13 @@ gem 'other', version
|
||||||
def mask
|
def mask
|
||||||
0100755
|
0100755
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def load_relative(value)
|
||||||
|
orig_LIBRUBY_RELATIVE = RbConfig::CONFIG['LIBRUBY_RELATIVE']
|
||||||
|
RbConfig::CONFIG['LIBRUBY_RELATIVE'] = value
|
||||||
|
|
||||||
|
yield
|
||||||
|
ensure
|
||||||
|
RbConfig::CONFIG['LIBRUBY_RELATIVE'] = orig_LIBRUBY_RELATIVE
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue