1 |
# Copyright 1999-2009 Gentoo Foundation |
2 |
# Distributed under the terms of the GNU General Public License v2 |
3 |
# $Header: /var/cvsroot/gentoo-x86/eclass/ruby-fakegem.eclass,v 1.15 2010/02/19 08:47:36 flameeyes Exp $ |
4 |
# |
5 |
# @ECLASS: ruby-fakegem.eclass |
6 |
# @MAINTAINER: |
7 |
# Ruby herd <ruby@gentoo.org> |
8 |
# |
9 |
# Author: Diego E. Pettenò <flameeyes@gentoo.org> |
10 |
# |
11 |
# Author: Alex Legler <a3li@gentoo.org> |
12 |
# |
13 |
# @BLURB: An eclass for installing Ruby packages to behave like RubyGems. |
14 |
# @DESCRIPTION: |
15 |
# This eclass allows to install arbitrary Ruby libraries (including Gems), |
16 |
# providing integration into the RubyGems system even for "regular" packages. |
17 |
# |
18 |
|
19 |
inherit ruby-ng |
20 |
|
21 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_NAME |
22 |
# @DESCRIPTION: |
23 |
# Sets the Gem name for the generated fake gemspec. |
24 |
# RUBY_FAKEGEM_NAME="${PN}" |
25 |
|
26 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_VERSION |
27 |
# @DESCRIPTION: |
28 |
# Sets the Gem version for the generated fake gemspec. |
29 |
# RUBY_FAKEGEM_VERSION="${PV}" |
30 |
|
31 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_TASK_DOC |
32 |
# @DESCRIPTION: |
33 |
# Specify the rake(1) task to run to generate documentation. |
34 |
# RUBY_FAKEGEM_TASK_DOC="rdoc" |
35 |
|
36 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_TASK_TEST |
37 |
# @DESCRIPTION: |
38 |
# Specify the rake(1) task used for executing tests. |
39 |
# RUBY_FAKEGEM_TASK_TEST="test" |
40 |
|
41 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_DOCDIR |
42 |
# @DESCRIPTION: |
43 |
# Specify the directory under which the documentation is built; |
44 |
# if empty no documentation will be installed automatically. |
45 |
# RUBY_FAKEGEM_DOCDIR="" |
46 |
|
47 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_EXTRADOC |
48 |
# @DESCRIPTION: |
49 |
# Extra documentation to install (readme, changelogs, …). |
50 |
# RUBY_FAKEGEM_EXTRADOC="" |
51 |
|
52 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_BINWRAP |
53 |
# @DESCRIPTION: |
54 |
# Binaries to wrap around (relative to the bin/ directory) |
55 |
# RUBY_FAKEGEM_BINWRAP="*" |
56 |
|
57 |
# @ECLASS-VARIABLE: RUBY_FAKEGEM_REQUIRE_PATHS |
58 |
# @DESCRIPTION: |
59 |
# Extra require paths (beside lib) to add to the specification |
60 |
# RUBY_FAKEGEM_REQUIRE_PATHS="" |
61 |
|
62 |
RUBY_FAKEGEM_NAME="${RUBY_FAKEGEM_NAME:-${PN}}" |
63 |
RUBY_FAKEGEM_VERSION="${RUBY_FAKEGEM_VERSION:-${PV/_pre/.pre}}" |
64 |
RUBY_FAKEGEM_SUFFIX="${RUBY_FAKEGEM_SUFFIX:-}" |
65 |
|
66 |
RUBY_FAKEGEM_TASK_DOC="${RUBY_FAKEGEM_TASK_DOC-rdoc}" |
67 |
RUBY_FAKEGEM_TASK_TEST="${RUBY_FAKEGEM_TASK_TEST-test}" |
68 |
|
69 |
RUBY_FAKEGEM_BINWRAP="${RUBY_FAKEGEM_BINWRAP-*}" |
70 |
|
71 |
if [[ ${RUBY_FAKEGEM_TASK_DOC} != "" ]]; then |
72 |
IUSE="$IUSE doc" |
73 |
ruby_add_bdepend doc "dev-ruby/rake" |
74 |
fi |
75 |
|
76 |
if [[ ${RUBY_FAKEGEM_TASK_TEST} != "" ]]; then |
77 |
IUSE="$IUSE test" |
78 |
ruby_add_bdepend test "dev-ruby/rake" |
79 |
fi |
80 |
|
81 |
SRC_URI="mirror://rubygems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}${RUBY_FAKEGEM_SUFFIX:+-${RUBY_FAKEGEM_SUFFIX}}.gem" |
82 |
|
83 |
ruby_add_rdepend virtual/rubygems |
84 |
|
85 |
# @FUNCTION: ruby_fakegem_gemsdir |
86 |
# @RETURN: Returns the gem data directory |
87 |
# @DESCRIPTION: |
88 |
# This function returns the gems data directory for the ruby |
89 |
# implementation in question. |
90 |
ruby_fakegem_gemsdir() { |
91 |
local _gemsitedir=$(${RUBY} -r rbconfig -e 'print Config::CONFIG["sitelibdir"]' | sed -e 's:site_ruby:gems:') |
92 |
|
93 |
[[ -z ${_gemsitedir} ]] && { |
94 |
eerror "Unable to find the gems dir" |
95 |
die "Unable to find the gems dir" |
96 |
} |
97 |
|
98 |
echo "${_gemsitedir}" |
99 |
} |
100 |
|
101 |
# @FUNCTION: ruby_fakegem_doins |
102 |
# @USAGE: file [file...] |
103 |
# @DESCRIPTION: |
104 |
# Installs the specified file(s) into the gems directory. |
105 |
ruby_fakegem_doins() { |
106 |
( |
107 |
insinto $(ruby_fakegem_gemsdir)/gems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION} |
108 |
doins "$@" |
109 |
) || die "failed $0 $@" |
110 |
} |
111 |
|
112 |
# @FUNCTION: ruby_fakegem_newsins() |
113 |
# @USAGE: file filename |
114 |
# @DESCRIPTION: |
115 |
# Installs the specified file into the gems directory using the provided filename. |
116 |
ruby_fakegem_newins() { |
117 |
( |
118 |
# Since newins does not accept full paths but just basenames |
119 |
# for the target file, we want to extend it here. |
120 |
local newdirname=/$(dirname "$2") |
121 |
[[ ${newdirname} == "/." ]] && newdirname= |
122 |
|
123 |
local newbasename=$(basename "$2") |
124 |
|
125 |
insinto $(ruby_fakegem_gemsdir)/gems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}${newdirname} |
126 |
newins "$1" ${newbasename} |
127 |
) || die "failed $0 $@" |
128 |
} |
129 |
|
130 |
# @FUNCTION: ruby_fakegem_genspec |
131 |
# @DESCRIPTION: |
132 |
# Generates a gemspec for the package and places it into the "specifications" |
133 |
# directory of RubyGems. |
134 |
# In the gemspec, the following values are set: name, version, summary, |
135 |
# homepage, and require_paths=["lib"]. |
136 |
# See RUBY_FAKEGEM_NAME and RUBY_FAKEGEM_VERSION for setting name and version. |
137 |
# See RUBY_FAKEGEM_REQUIRE_PATHS for setting extra require paths. |
138 |
ruby_fakegem_genspec() { |
139 |
( |
140 |
local required_paths="'lib'" |
141 |
for path in ${RUBY_FAKEGEM_REQUIRE_PATHS}; do |
142 |
required_paths="${required_paths}, '${path}'" |
143 |
done |
144 |
|
145 |
# We use the _ruby_implementation variable to avoid having stray |
146 |
# copies with different implementations; while for now we're using |
147 |
# the same exact content, we might have differences in the future, |
148 |
# so better taking this into consideration. |
149 |
local quoted_description=${DESCRIPTION//\"/\\\"} |
150 |
cat - > "${T}"/${RUBY_FAKEGEM_NAME}-${_ruby_implementation} <<EOF |
151 |
# generated by ruby-fakegem.eclass $Id: $ |
152 |
Gem::Specification.new do |s| |
153 |
s.name = "${RUBY_FAKEGEM_NAME}" |
154 |
s.version = "${RUBY_FAKEGEM_VERSION}" |
155 |
s.summary = "${quoted_description}" |
156 |
s.homepage = "${HOMEPAGE}" |
157 |
s.require_paths = [${required_paths}] |
158 |
end |
159 |
EOF |
160 |
|
161 |
insinto $(ruby_fakegem_gemsdir)/specifications |
162 |
newins "${T}"/${RUBY_FAKEGEM_NAME}-${_ruby_implementation} ${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}.gemspec |
163 |
) || die "Unable to install fake gemspec" |
164 |
} |
165 |
|
166 |
# @FUNCTION: ruby_fakegem_binwrapper |
167 |
# @USAGE: command [path] |
168 |
# @DESCRIPTION: |
169 |
# Creates a new binary wrapper for a command installed by the RubyGem. |
170 |
# path defaults to /usr/bin/$command |
171 |
ruby_fakegem_binwrapper() { |
172 |
( |
173 |
local gembinary=$1 |
174 |
local newbinary=${2:-/usr/bin/$gembinary} |
175 |
local relativegembinary=${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}/bin/${gembinary} |
176 |
local binpath=$(dirname $newbinary) |
177 |
[[ ${binpath} = . ]] && binpath=/usr/bin |
178 |
|
179 |
# Try to find out whether the package is going to install for |
180 |
# one or multiple implementations; if we're installing for a |
181 |
# *single* implementation, no need to use “/usr/bin/env ruby” |
182 |
# in the shebang, and we can actually avoid errors when |
183 |
# calling the script by default (see for instance the |
184 |
# JRuby-specific commands). |
185 |
local rubycmd= |
186 |
for implementation in ${USE_RUBY}; do |
187 |
# ignore non-enabled implementations |
188 |
use ruby_targets_${implementation} || continue |
189 |
if [ -z $rubycmd ]; then |
190 |
# if no other implementation was set before, set it. |
191 |
rubycmd="/usr/bin/${implementation}" |
192 |
else |
193 |
# if another implementation already arrived, then make |
194 |
# it generic and break out of the loop. This ensures |
195 |
# that we do at most two iterations. |
196 |
rubycmd="/usr/bin/env ruby" |
197 |
break |
198 |
fi |
199 |
done |
200 |
|
201 |
cat - > "${T}"/gembin-wrapper-${gembinary} <<EOF |
202 |
#!${rubycmd} |
203 |
# This is a simplified version of the RubyGems wrapper |
204 |
# |
205 |
# Generated by ruby-fakegem.eclass $Id: $ |
206 |
|
207 |
require 'rubygems' |
208 |
|
209 |
load Gem::default_path[-1] + "/gems/${relativegembinary}" |
210 |
|
211 |
EOF |
212 |
|
213 |
exeinto ${binpath:-/usr/bin} |
214 |
newexe "${T}"/gembin-wrapper-${gembinary} $(basename $newbinary) |
215 |
) || die "Unable to create fakegem wrapper" |
216 |
} |
217 |
|
218 |
# @FUNCTION: all_fakegem_compile |
219 |
# @DESCRIPTION: |
220 |
# Build documentation for the package if indicated by the doc USE flag |
221 |
# and if there is a documetation task defined. |
222 |
all_fakegem_compile() { |
223 |
if [[ ${RUBY_FAKEGEM_TASK_DOC} != "" ]] && use doc; then |
224 |
rake ${RUBY_FAKEGEM_TASK_DOC} || die "failed to (re)build documentation" |
225 |
fi |
226 |
} |
227 |
|
228 |
# @FUNCTION: all_ruby_unpack |
229 |
# @DESCRIPTION: |
230 |
# Unpack the source archive, including support for unpacking gems. |
231 |
all_ruby_unpack() { |
232 |
# Special support for extracting .gem files; the file need to be |
233 |
# extracted twice and the mtime from the archive _has_ to be |
234 |
# ignored (it's always set to epoch 0). |
235 |
# |
236 |
# This only works if there is exactly one archive and that archive |
237 |
# is a .gem file! |
238 |
if [[ $(wc -w <<< ${A}) == 1 ]] && |
239 |
[[ ${A} == *.gem ]]; then |
240 |
ebegin "Unpacking .gem file..." |
241 |
tar -mxf ${DISTDIR}/${A} || die |
242 |
eend $? |
243 |
|
244 |
mkdir "${S}" |
245 |
pushd "${S}" &>/dev/null |
246 |
|
247 |
ebegin "Unpacking data.tar.gz" |
248 |
tar -mxf "${my_WORKDIR}"/data.tar.gz || die |
249 |
eend $? |
250 |
popd &>/dev/null |
251 |
else |
252 |
[[ -n ${A} ]] && unpack ${A} |
253 |
fi |
254 |
} |
255 |
|
256 |
# @FUNCTION: all_ruby_compile |
257 |
# @DESCRIPTION: |
258 |
# Compile the package. |
259 |
all_ruby_compile() { |
260 |
all_fakegem_compile |
261 |
} |
262 |
|
263 |
# @FUNCTION: each_fakegem_test |
264 |
# @DESCRIPTION: |
265 |
# Run tests for the package for each ruby target if the test task is defined. |
266 |
each_fakegem_test() { |
267 |
local rubyflags= |
268 |
${RUBY} ${rubyflags} -S rake ${RUBY_FAKEGEM_TASK_TEST} || die "tests failed" |
269 |
} |
270 |
|
271 |
if [[ ${RUBY_FAKEGEM_TASK_TEST} != "" ]]; then |
272 |
# @FUNCTION: each_ruby_test |
273 |
# @DESCRIPTION: |
274 |
# Run the tests for this package. |
275 |
each_ruby_test() { |
276 |
each_fakegem_test |
277 |
} |
278 |
fi |
279 |
|
280 |
# @FUNCTION: each_fakegem_install |
281 |
# @DESCRIPTION: |
282 |
# Install the package for each ruby target. |
283 |
each_fakegem_install() { |
284 |
ruby_fakegem_genspec |
285 |
|
286 |
local _gemlibdirs="${RUBY_FAKEGEM_EXTRAINSTALL}" |
287 |
for directory in bin lib; do |
288 |
[[ -d ${directory} ]] && _gemlibdirs="${_gemlibdirs} ${directory}" |
289 |
done |
290 |
|
291 |
[[ -n ${_gemlibdirs} ]] && \ |
292 |
ruby_fakegem_doins -r ${_gemlibdirs} |
293 |
} |
294 |
|
295 |
# @FUNCTION: each_ruby_install |
296 |
# @DESCRIPTION: |
297 |
# Install the package for each target. |
298 |
each_ruby_install() { |
299 |
each_fakegem_install |
300 |
} |
301 |
|
302 |
# @FUNCTION: all_fakegem_install |
303 |
# @DESCRIPTION: |
304 |
# Install files common to all ruby targets. |
305 |
all_fakegem_install() { |
306 |
if [[ -n ${RUBY_FAKEGEM_DOCDIR} ]] && [[ ${RUBY_FAKEGEM_TASK_DOC} != "" ]] && use doc; then |
307 |
for dir in ${RUBY_FAKEGEM_DOCDIR}; do |
308 |
pushd ${dir} &>/dev/null |
309 |
dohtml -r * || die "failed to install documentation" |
310 |
popd &>/dev/null |
311 |
done |
312 |
fi |
313 |
|
314 |
if [[ -n ${RUBY_FAKEGEM_EXTRADOC} ]]; then |
315 |
dodoc ${RUBY_FAKEGEM_EXTRADOC} || die "failed to install further documentation" |
316 |
fi |
317 |
|
318 |
# binary wrappers; we assume that all the implementations get the |
319 |
# same binaries, or something is wrong anyway, so... |
320 |
if [[ -n ${RUBY_FAKEGEM_BINWRAP} ]]; then |
321 |
local bindir=$(find "${D}" -type d -path "*/gems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}/bin" -print -quit) |
322 |
|
323 |
if [[ -d "${bindir}" ]]; then |
324 |
pushd "${bindir}" &>/dev/null |
325 |
local binaries=$(eval ls ${RUBY_FAKEGEM_BINWRAP}) |
326 |
for binary in $binaries; do |
327 |
ruby_fakegem_binwrapper $binary |
328 |
done |
329 |
popd &>/dev/null |
330 |
fi |
331 |
fi |
332 |
} |
333 |
|
334 |
# @FUNCTION: all_ruby_install |
335 |
# @DESCRIPTION: |
336 |
# Install files common to all ruby targets. |
337 |
all_ruby_install() { |
338 |
all_fakegem_install |
339 |
} |