Hi
This question popped up while discussing how to deal with Ruby gems on
Gentoo in a way that gives the user the freedom to choose Portage,
RubyGems or both for gem management.
http://bugs.gentoo.org/show_bug.cgi?id=268857
Here's what it boils down to:
If a Ruby gem ebuild is slotted, the executables it writes to /usr/bin
are currently postfixed with a version as Portage does not yet allow a
file to be owned by more than one slot. This is not a good solution,
see below for details.
Is it feasable to extend Portage to allow a file to be owned by
several slots and remove it only once the last slot is uninstalled
(aka: once the ebuild is completely uninstalled)?
Here's the background:
RubyGems (the gem manager) deals with dependencies and concurrent gem
versions. It's not unusual to have the same gem installed in various
versions as other installed gems may require different versions.
If a Ruby gem contains and installs executables, then those are mere
wrappers to a Ruby runner object. As per default, the wrapper will run
the most up-to-date code. You can, however, tell the wrapper to run a
specific code version (e.g. rake _0.7.3_ --version).
On Gentoo, slots are used for this and therefore ebuilds for software
written in Ruby should (and do) depend on slotted ebuilds of the gems
they need.
Unfortunately, Portage doesn't allow slots to share files at this
point, therefore every slot has to install it's own versioned copy of
gem supplied executables. This not only fills /usr/bin with
unnecessary identical wrappers, but has another consequence:
Every mayjor version of Ruby (currently 1.8, 1.9 and enterprise
edition) has it's own set of installed gems and therefore Ruby itself
is slotted and eselect-ruby does the switching. I've written a simple
patch for eselect-ruby which assures that all gem supplied executables
are switched correctly, no matter whether they were installed through
Portage or RubyGems. It will, however, only work, if Portage allows
gem executables to be shared between all slots of the gem.
And here's why plan B doesn't quite cut it:
Why not write a gem2ebuild tool and automatically add *all* gems from
Rubyforge and Github as ebuilds. This is most likely a bad idea,
because:
- External dependencies (e.g. with C libs) must be maintained manually.
- All outdated ebuilds must be kept due to gem dependencies to
outdated versions.
- Some useful gems are neither on Rubyforge nor Github and wouldn't be
covered.
There are currently about 7500 gems on Rubyforge and Github as of now.
Multiplied by the number of versions, you get a shitload of ebuilds to
host and sync.
RubyGems does a very good job dealing with versions and dependencies,
so it's IMHO a good idea not to delegate this to Portage unless
absolutely necessary. We better find a way for Portage and RubyGems to
work hand in hand.
What do you think?
-sven