2

The ruby included with RedHat/CentOS-6 is of version 1.8.7, which is too old for many applications. Though simply updating it with a custom-built RPM is possible, my colleagues shy away from the idea and wish to use the rh-ruby22 packages available from the SCL-repo.

That installs ruby-2.2, which is great, but under /opt/rh/rh-ruby22. I now need to install several gems and would like to, obviously, use Puppet:

package {'example':
  ensure   => '0.25',
  provider => 'gem'
}

Unfortunately, the gem-provider invokes /usr/bin/gem instead of /opt/rh/rh-ruby22/root/usr/bin/gem that needs to be invoked. Is there any other way? Thanks!

Mikhail T.
  • 2,272
  • 1
  • 22
  • 49

2 Answers2

1

The package resource, and in particular the gem provider, now supports the use of the command attribute. Your particular example is now supported like this:

package {'example':
  ensure   => '0.25',
  provider => 'gem',
  command  => '/opt/rh/rh-ruby22/root/usr/bin/gem'
}
Zach
  • 126
  • 2
0

Ok, the "easy" way is to implement one's own package-provider. Fortunately, one can inherit everything from the existing gem-provider overriding only the gem-command itself.

Because SCL's rh-ruby22 is so retarded, you can't even invoke its ruby or gem directly -- without setting LD_LIBRARY_PATH first -- we create wrappers for them in /usr/bin. The /usr/bin/gem2, for example, sets the library path (and PATH) and then execs the real /opt/rh/rh-ruby22/root/usr/bin/gem with its own arguments ("$@").

My new provider uses the gem2 wrapper script to do its thing.

I created the file gem2.rb in modules/SOMEMODULE/lib/puppet/provider/package/ with the following content (tested with Puppet-3.8.7):

require 'puppet/provider/package'

Puppet::Type.type(:package).provide File.basename(__FILE__, ".rb"),
    :parent => :gem, :source => :gem do
        desc "Ruby Gem support using #{@name}-executable"

        commands :gemcmd => @name.to_s
end

Though I was hoping, my implementation would allow one to specify the gem-command as a parameter in the puppet-manifest, it is impossible to do this without completely rewriting the existing gem-provider. My way is much easier and just as efficient.

As a bonus, copying the file to some other name (such as gem19.rb) will automatically create the new provider -- just be sure, gem19 is in the $PATH.

The module, under which you'll save this file, can be any module used by the machine(s) that need the new provider.

Mikhail T.
  • 2,272
  • 1
  • 22
  • 49