Binaries installed into subdirectories based on Ruby version - incompatible with how bundler's Rust extension template works
I had no issues getting my Rust extension working locally, but one of the issues I ran into was using the cross-compile action. Once I got the build working, the resulting gem packages were built with the precompiled binary in a path like lib/my_gem/3.0/my_gem.bundle. This is incompatible with the extconf.rb generated by Bundler. The local build generates lib/my_gem/my_gem.bundle.
# lib/my_gem/extconf.rb as generated by Bundler
# frozen_string_literal: true
require_relative "my_gem/version"
require_relative "my_gem/my_gem"
module MyGem
class Error < StandardError; end
end
I saw that wasmtime seemed to have the same problem, and they fixed it like so:
# lib/my_gem/extconf.rb
# frozen_string_literal: true
require_relative "my_gem/version"
# Tries to require the extension for the given Ruby version first
begin
RUBY_VERSION =~ /(\d+\.\d+)/
require "my_gem/#{Regexp.last_match(1)}/my_gem"
rescue LoadError
require_relative "my_gem/my_gem"
end
module MyGem
class Error < StandardError; end
end
EDIT: Looks like specifying a single Ruby version target gets you the standard my_gem/my_gem.bundle, multiple gets you the subdirectories. Understandable, but worth mentioning.
Yeah, it's a bit of a hack but that's the recommended rake-compiler pattern so I went with it... Would def accept a patch to document this better.