Installing gherkin from a git repository with bundler
I just installed our Rails application on new hardware running
Ubuntu 11.10. Everything went smoothly except for one gem: gherkin
1.0.30. (We’re on Rails 2 for now, so we’re using cucumber 0.8.0, which
uses gherkin 1.) bundle install
resulted in this error:
1 2 3 4 5 6 | /usr/lib/ruby/vendor_ruby/1.8/rubygems/installer.rb:533:in `build_extensions': ERROR: Failed to build gem native extension. (Gem::Installer::ExtensionBuildError) /usr/bin/ruby1.8 extconf.rb gcc -I. -I. -I/usr/lib/ruby/1.8/x86_64-linux -I. -fPIC -fno-strict-aliasing -g -g -O2 -fPIC -O0 -Wall -Werror -c gherkin_lexer_ar.c /Users/aslakhellesoy/scm/gherkin/tasks/../ragel/i18n/ar.c.rl: In function ‘CLexer_scan’: /Users/aslakhellesoy/scm/gherkin/tasks/../ragel/i18n/ar.c.rl:198:29: error: the comparison will always evaluate as ‘true’ for the address of ‘raise_lexer_error’ will never be NULL [-Werror=address] cc1: all warnings being treated as errors |
There wasn’t a serious problem with the native code, but the gcc I was using (4.6.1) had found a warning that earlier versions presumably had not — or 1.0.30 wouldn’t have compiled with -Werror.
The fix was easy; just remove -Werror from the compilation. (It’s in a rake task that compiles C code generated by the Ragel state machine compiler.) The trick was setting up the modified gem so bundler could use it.
The only way to install a modified version of a gem with native extensions that you don’t own is to use Gemfile’s :git option. (There’s also a :path option which installs a gem from a path on your filesystem, but it doesn’t compile native extensions.) So, in the including application’s Gemfile, we have
1 | gem 'gherkin', '1.0.30', :git => 'git@github.com:danaronson/gherkin.git', :branch => 'v1.0.30-no-Werror' |
pointing at the modified fork of gherkin.
What exactly needed to be modified? Although bundler can fake up a .gemspec if none is present, that .gemspec won’t compile native extensions. For native extensions to be compiled, a gem installed with :git must have its own gemspec which refers to the extensions. The native code itself must also be present in the gem, which (being generated) it is not in the original gherkin repo.
So I installed Ragel (with MacPorts) and the jeweler and rake-compiler gems, ran rake gems:posix
to generate the native code and the .gemspec, removed the .gitignore
entries that ignored what I’d just generated, and added the generated
code to my fork. Now bundle install
gets the native code from git and compiles it as it would if it came from a packaged gem.
You can look at the fork to see the details. I’m not promising that it’ll be there forever, so if you need to solve this problem too, make your own fork.
This is probably the most trouble I ever had making a seven-character fix in a single file. Anything to keep the films rolling!
Occasionally, some of your visitors may see an advertisement here.
Leave a Reply