Installing nokogiri with rbenv on Mavericks

As is often the case after a Mac OS X upgrade, installing Ruby gems that depend on compiled C code can require a bit of fiddling about. I've just upgraded my laptop to Mavericks, and lo and behold, the nokogiri Ruby gem won't install. I should have had déjà vu here, as I went through a similar process installing nokogiri on Leopard!

On the off chance that the solution that worked for me might also work for you, I made a few notes.

tl;dr – Apple's command line tools went awol during the upgrade to Mavericks (even though I have XCode installed), and I had to jump through a couple of hoops to re-install them, then run a binary as root to force Apple to ask me to accept the license agreement.

The error

When running gem install nokogiri I got this error:

$ gem install nokogiri
Building native extensions.  This could take a while...
ERROR:  Error installing nokogiri:
        ERROR: Failed to build gem native extension.

        /Users/graham/.rbenv/versions/1.9.3-p194/bin/ruby extconf.rb
Extracting libxml2-2.8.0.tar.gz into tmp//ports/libxml2/2.8.0... OK
Running 'configure' for libxml2 2.8.0... ERROR, review 'tmp//ports/libxml2/2.8.0/configure.log' to see what happened
.
*** extconf.rb failed ***
Could not create Makefile due to some reason, probably lack of
necessary libraries and/or headers.  Check the mkmf.log file for more
details.  You may need configuration options.

My Ruby setup

Firstly, I should tell you a bit about where I was starting from.

  • I use rbenv to install different versions of Ruby. The notes in this post were collated while getting nokogiri to build with Ruby 1.9.3p194, but I would expect my solution to work just as well if you're compiling gems for any version of 1.9.3 or 2.0.0.
  • When this machine was still running Mountain Lion, homebrew and XCode were both already installed. The "App Store" app offered me an XCode upgrade, and I took it. I therefore thought I had the command line tools (i.e. a C compiler, make, etc) available. In reality they weren't there, but we'll get to that in a minute.

How I fixed it

The top tip in the error message (see above) was that the output had been written to tmp/ports/libxml2/2.8.0/configure.log. I had a look inside, and lo and behold, it turned out that I didn't have a working C compiler.

$ cat ~/rbenv/versions/1.9.3-p194/lib/ruby/gems/1.9.1/gems/nokogiri-1.6.0/ext/nokogiri/tmp/ports/libxml2/2.8.0/configure.log
checking build system type... i386-apple-darwin13.0.0
checking host system type... i386-apple-darwin13.0.0
checking for a BSD-compatible install... /usr/bin/install -c
checking whether build environment is sane... yes
checking for a thread-safe mkdir -p... ./install-sh -c -d
checking for gawk... no
checking for mawk... no
checking for nawk... no
checking for awk... awk
checking whether make sets $(MAKE)... no
checking for gcc... gcc
checking whether the C compiler works... no
configure: error: in
`/Users/graham/.rbenv/versions/1.9.3-p194/lib/ruby/gems/1.9.1/gems/nokogiri-1.6.0/ext/nokogiri/tmp/ports/libxml2/2.8.0/libxml2-2.8.0':
configure: error: C compiler cannot create executables
See `config.log' for more details

I suspected I didn't actually have XCode at this point. I wish I'd checked, as I'd discovered that it was there, and I'd have launched it to check that it was in fact version 5. See my footnote at the bottom of this post to find out why; if your problem resembles mine at this point I recommend launching XCode and checking that it doesn't also report that bits are missing!

The standard advice online for getting the XCode command line tools installed on Mavericks is to run xcode-select --install. So I did that, and a small dialog popped up and then proceeded to download the command line tools for me. I rather thought I was set at this point. But no...

If, after re-running gem install ... you find that the gem still won't install, and that the configure.log file still complains that you don't have any command line tools, try cd-ing into the directory of the code that won't build and running make.

$ cd ~/rbenv/versions/1.9.3-p194/lib/ruby/gems/1.9.1/gems/nokogiri-1.6.0/ext/nokogiri/tmp/ports/libxml2/2.8.0/
$ cd libxml2-2.8.0/
$ make clean


Agreeing to the Xcode/iOS license requires admin privileges, please
re-run as root via sudo.

It appears as though xcode-select could have asked me to accept a license agreement. Instead, you're prompted the first time you try and run the command line binary, and the Ruby build scripts had gobbled up the error message.

I tried again with sudo.

$ sudo make


You have not agreed to the Xcode license agreements. You must agree to
both license agreements below in order to use Xcode.

Hit the Enter key to view the license agreements at
'/Applications/Xcode.app/Contents/Resources/English.lproj/License.rtf'

IMPORTANT: BY USING THIS SOFTWARE, YOU ARE AGREEING TO BE BOUND BY THE
FOLLOWING APPLE TERMS:

A. MAC SDK AND XCODE AGREEMENT
B. iOS SDK AGREEMENT

[snip]

Result. Once I'd accepted that licence agreement I found that gem install nokogiri ran without a hitch.

Footnote about the XCode 5 upgrade

Note that I didn't run XCode 5 inbetween upgrading to it (in the App Store app) and trying to build any Ruby gems. When I did finally run it (after I'd successfully got gcc installed), I was presented with a dialog box asking if I'd like to "install additional required components?"

XCode 5: Installing additional required components

It's as if the upgrade to XCode 5 wasn't finished; maybe installing these components before I started would have made gcc and friends available to me from the outset? Who knows...

UPDATE: Since writing this post I've upgraded to Mavericks on a second computer, ran into the same problem, and launched XCode. After it had installed its missing components I could run gcc without being prompted to accept a license agreement, and gem compilation just worked. Also take a look at the comments below, where others have been explaining what's worked for them.

I love feedback and questions — please feel free to get in touch on Mastodon or Twitter, or leave a comment.