Skip to content

Commit

Permalink
Use ENV variables to set conf paths (#222)
Browse files Browse the repository at this point in the history
closes: GH-202

Instead of creating `.rake-compiler-siteconf.rb` to override
`RbConfig::MAKEFILE_CONFIG` and `RbConfig::CONFIG`, set environment
variables to `make install` command. Since `RbConfig` is suppose to be
readonly, we shouldn't overwrite its values.

Additionally, this update addresses a bug caused by
`.rake-compiler-siteconf.rb`. The file's hardcoded destination path
causes `rake-compiler` to consistently create files in that location,
even if the project is renamed or moved. Consequently, changes to the
gem project's path do not trigger the file task to update the file. This
fix resolves this issue.

---------

Co-authored-by: Sutou Kouhei <kou@clear-code.com>
  • Loading branch information
ggmichaelgo and kou committed Aug 1, 2023
1 parent 100d424 commit 0d93b08
Show file tree
Hide file tree
Showing 2 changed files with 18 additions and 29 deletions.
34 changes: 14 additions & 20 deletions lib/rake/extensiontask.rb
@@ -1,4 +1,5 @@
require "rbconfig"
require "shellwords"

require 'rake/baseextensiontask'
require "rubygems/package_task"
Expand Down Expand Up @@ -79,7 +80,7 @@ def cross_config_options(for_platform=nil)
end.flatten
end

def make_makefile_cmd(root_path, tmp_path, extconf, siteconf_path, cross_platform) # :nodoc:
def make_makefile_cmd(root_path, tmp_path, extconf, cross_platform) # :nodoc:
# include current directory
include_dirs = ['.'].concat(@config_includes).uniq.join(File::PATH_SEPARATOR)

Expand All @@ -89,7 +90,7 @@ def make_makefile_cmd(root_path, tmp_path, extconf, siteconf_path, cross_platfor
rel_extconf = abs_extconf.relative_path_from(abs_tmp_path).to_s

# base command
cmd = [Gem.ruby, "-I#{include_dirs}", "-r#{File.basename(siteconf_path)}", rel_extconf]
cmd = [Gem.ruby, "-I#{include_dirs}", rel_extconf]

# add all the options
cmd += @config_options
Expand Down Expand Up @@ -140,7 +141,6 @@ def define_compile_tasks(for_platform = nil, ruby_ver = RUBY_VERSION)
tmp_path = "#{@tmp_dir}/#{platf}/#{@name}/#{ruby_ver}"
stage_path = "#{@tmp_dir}/#{platf}/stage"

siteconf_path = "#{tmp_path}/.rake-compiler-siteconf.rb"
tmp_binary_path = "#{tmp_path}/#{binary_path}"
tmp_binary_dir_path = File.dirname(tmp_binary_path)
stage_binary_path = "#{stage_path}/#{lib_binary_path}"
Expand All @@ -158,26 +158,20 @@ def define_compile_tasks(for_platform = nil, ruby_ver = RUBY_VERSION)
directory lib_path
directory stage_binary_dir_path

directory File.dirname(siteconf_path)
# Set paths for "make install" destinations
file siteconf_path => File.dirname(siteconf_path) do
File.open(siteconf_path, "w") do |siteconf|
siteconf.puts "require 'rbconfig'"
siteconf.puts "require 'mkmf'"
siteconf.puts "dest_path = mkintpath(#{File.expand_path(lib_path).dump})"
%w[sitearchdir sitelibdir].each do |dir|
siteconf.puts "RbConfig::MAKEFILE_CONFIG['#{dir}'] = dest_path"
siteconf.puts "RbConfig::CONFIG['#{dir}'] = dest_path"
end
end
end

# copy binary from temporary location to final lib
# tmp/extension_name/extension_name.{so,bundle} => lib/
task "copy:#{@name}:#{platf}:#{ruby_ver}" => [lib_path, tmp_binary_path, "#{tmp_path}/Makefile"] do
# install in lib for native platform only
unless for_platform
sh "#{make} install target_prefix=", chdir: tmp_path
relative_lib_path = Pathname(lib_path).relative_path_from(tmp_path)

make_command_line = Shellwords.shellsplit(make)
make_command_line << "install"
make_command_line << "sitearchdir=#{relative_lib_path}"
make_command_line << "sitelibdir=#{relative_lib_path}"
make_command_line << "target_prefix="

sh(*make_command_line, chdir: tmp_path)
end
end
# copy binary from temporary location to staging directory
Expand Down Expand Up @@ -207,14 +201,14 @@ def define_compile_tasks(for_platform = nil, ruby_ver = RUBY_VERSION)

# makefile depends of tmp_dir and config_script
# tmp/extension_name/Makefile
file "#{tmp_path}/Makefile" => [tmp_path, extconf, siteconf_path] do |t|
file "#{tmp_path}/Makefile" => [tmp_path, extconf] do |t|
if t.prerequisites.include?("#{tmp_path}/fake.rb")
cross_platform = platf
else
cross_platform = nil
end

command = make_makefile_cmd(Dir.pwd, tmp_path, extconf, siteconf_path, cross_platform)
command = make_makefile_cmd(Dir.pwd, tmp_path, extconf, cross_platform)

chdir tmp_path do
sh(*command)
Expand Down
13 changes: 4 additions & 9 deletions spec/lib/rake/extensiontask_spec.rb
Expand Up @@ -289,7 +289,6 @@
around :each do |test|
@tmp_path = "injectedtmp"
@extconf = "injectedextconf.rb"
@siteconf_path = "#{@tmp_path}/.injected-siteconf.rb"

Dir.mktmpdir do |root_path|
@root_path = root_path
Expand All @@ -313,13 +312,12 @@
end

it "runs the extconf with proper arguments when not cross-compiling" do
command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, @siteconf_path, nil)
command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, nil)

expected_includes = [".", "/injected/include1", "/injected/include2"].join(File::PATH_SEPARATOR)
expected = [
Gem.ruby,
"-I#{expected_includes}",
"-r.injected-siteconf.rb",
"../#{@extconf}",
"--with-a", # config_options
"--", "--with-b", # extra_options
Expand All @@ -329,13 +327,12 @@
end

it "runs the extconf with proper arguments when cross-compiling" do
command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, @siteconf_path, "universal-known")
command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, "universal-known")

expected_includes = [".", "/injected/include1", "/injected/include2"].join(File::PATH_SEPARATOR)
expected = [
Gem.ruby,
"-I#{expected_includes}",
"-r.injected-siteconf.rb",
"../#{@extconf}",
"--with-a", # config_options
"--with-c", "--with-d", # cross_config_options
Expand All @@ -348,13 +345,12 @@
it "handles spaces in arguments correctly" do
@ext.extra_options << "--with-spaces='a b'"

command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, @siteconf_path, nil)
command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, nil)

expected_includes = [".", "/injected/include1", "/injected/include2"].join(File::PATH_SEPARATOR)
expected = [
Gem.ruby,
"-I#{expected_includes}",
"-r.injected-siteconf.rb",
"../#{@extconf}",
"--with-a", # config_options
"--", "--with-b", "--with-spaces='a b'", # extra_options
Expand All @@ -366,13 +362,12 @@
it "handles 'nil' in the command array gracefully" do
@ext.config_options << nil # imagine this is ENV['NONEXISTENT_VALUE']

command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, @siteconf_path, nil)
command = @ext.make_makefile_cmd(@root_path, @tmp_path, @extconf, nil)

expected_includes = [".", "/injected/include1", "/injected/include2"].join(File::PATH_SEPARATOR)
expected = [
Gem.ruby,
"-I#{expected_includes}",
"-r.injected-siteconf.rb",
"../#{@extconf}",
"--with-a", # config_options
"--", "--with-b", # extra_options
Expand Down

0 comments on commit 0d93b08

Please sign in to comment.