/[gentoo-x86]/eclass/ruby-fakegem.eclass
Gentoo

Contents of /eclass/ruby-fakegem.eclass

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1.45 - (show annotations) (download)
Sun Jul 5 09:10:53 2015 UTC (17 months, 1 week ago) by graaff
Branch: MAIN
CVS Tags: HEAD
Changes since 1.44: +6 -4 lines
Document that some variables must be set before inheriting the eclass.

1 # Copyright 1999-2015 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.44 2014/12/28 10:13:18 graaff Exp $
4
5 # @ECLASS: ruby-fakegem.eclass
6 # @MAINTAINER:
7 # Ruby herd <ruby@gentoo.org>
8 # @AUTHOR:
9 # Author: Diego E. Pettenò <flameeyes@gentoo.org>
10 # Author: Alex Legler <a3li@gentoo.org>
11 # @BLURB: An eclass for installing Ruby packages to behave like RubyGems.
12 # @DESCRIPTION:
13 # This eclass allows to install arbitrary Ruby libraries (including Gems),
14 # providing integration into the RubyGems system even for "regular" packages.
15
16 inherit ruby-ng
17
18 # @ECLASS-VARIABLE: RUBY_FAKEGEM_NAME
19 # @DESCRIPTION:
20 # Sets the Gem name for the generated fake gemspec.
21 # This variable MUST be set before inheriting the eclass.
22 # RUBY_FAKEGEM_NAME="${PN}"
23
24 # @ECLASS-VARIABLE: RUBY_FAKEGEM_VERSION
25 # @DESCRIPTION:
26 # Sets the Gem version for the generated fake gemspec.
27 # This variable MUST be set before inheriting the eclass.
28 # RUBY_FAKEGEM_VERSION="${PV}"
29
30 # @ECLASS-VARIABLE: RUBY_FAKEGEM_TASK_DOC
31 # @DESCRIPTION:
32 # Specify the rake(1) task to run to generate documentation.
33 # RUBY_FAKEGEM_TASK_DOC="rdoc"
34
35 # @ECLASS-VARIABLE: RUBY_FAKEGEM_RECIPE_TEST
36 # @DESCRIPTION:
37 # Specify one of the default testing function for ruby-fakegem:
38 # - rake (default; see also RUBY_FAKEGEM_TASK_TEST)
39 # - rspec (calls ruby-ng_rspec, adds dev-ruby/rspec:2 to the dependencies)
40 # - rspec3 (calls ruby-ng_rspec, adds dev-ruby/rspec:3 to the dependencies)
41 # - cucumber (calls ruby-ng_cucumber, adds dev-util/cucumber to the
42 # dependencies; does not work on JRuby).
43 # - none
44 # RUBY_FAKEGEM_RECIPE_TEST="rake"
45
46 # @ECLASS-VARIABLE: RUBY_FAKEGEM_TASK_TEST
47 # @DESCRIPTION:
48 # Specify the rake(1) task used for executing tests. Only valid
49 # if RUBY_FAKEGEM_RECIPE_TEST is set to "rake" (the default).
50 # RUBY_FAKEGEM_TASK_TEST="test"
51
52 # @ECLASS-VARIABLE: RUBY_FAKEGEM_RECIPE_DOC
53 # @DESCRIPTION:
54 # Specify one of the default API doc building function for ruby-fakegem:
55 # - rake (default; see also RUBY_FAKEGEM_TASK_DOC)
56 # - rdoc (calls `rdoc-2`, adds dev-ruby/rdoc to the dependencies);
57 # - yard (calls `yard`, adds dev-ruby/yard to the dependencies);
58 # - none
59 # RUBY_FAKEGEM_RECIPE_DOC="rake"
60
61 # @ECLASS-VARIABLE: RUBY_FAKEGEM_DOCDIR
62 # @DESCRIPTION:
63 # Specify the directory under which the documentation is built;
64 # if empty no documentation will be installed automatically.
65 # Note: if RUBY_FAKEGEM_RECIPE_DOC is set to `rdoc`, this variable is
66 # hardwired to `doc`.
67 # RUBY_FAKEGEM_DOCDIR=""
68
69 # @ECLASS-VARIABLE: RUBY_FAKEGEM_EXTRADOC
70 # @DESCRIPTION:
71 # Extra documentation to install (readme, changelogs, …).
72 # RUBY_FAKEGEM_EXTRADOC=""
73
74 # @ECLASS-VARIABLE: RUBY_FAKEGEM_DOC_SOURCES
75 # @DESCRIPTION:
76 # Allow settings defined sources to scan for documentation.
77 # This only applies if RUBY_FAKEGEM_DOC_TASK is set to `rdoc`.
78 # RUBY_FAKEGEM_DOC_SOURCES="lib"
79
80 # @ECLASS-VARIABLE: RUBY_FAKEGEM_BINWRAP
81 # @DESCRIPTION:
82 # Binaries to wrap around (relative to the bin/ directory)
83 # RUBY_FAKEGEM_BINWRAP="*"
84
85 # @ECLASS-VARIABLE: RUBY_FAKEGEM_REQUIRE_PATHS
86 # @DESCRIPTION:
87 # Extra require paths (beside lib) to add to the specification
88 # RUBY_FAKEGEM_REQUIRE_PATHS=""
89
90 # @ECLASS-VARIABLE: RUBY_FAKEGEM_GEMSPEC
91 # @DESCRIPTION:
92 # Filename of .gemspec file to install instead of generating a generic one.
93 # RUBY_FAKEGEM_GEMSPEC=""
94
95 # @ECLASS-VARIABLE: RUBY_FAKEGEM_EXTRAINSTALL
96 # @DESCRIPTION:
97 # List of files and directories relative to the top directory that also
98 # get installed. Some gems provide extra files such as version information,
99 # Rails generators, or data that needs to be installed as well.
100 # RUBY_FAKEGEM_EXTRAINSTALL=""
101
102 RUBY_FAKEGEM_NAME="${RUBY_FAKEGEM_NAME:-${PN}}"
103 RUBY_FAKEGEM_VERSION="${RUBY_FAKEGEM_VERSION:-${PV/_pre/.pre}}"
104 RUBY_FAKEGEM_SUFFIX="${RUBY_FAKEGEM_SUFFIX:-}"
105
106 RUBY_FAKEGEM_RECIPE_DOC="${RUBY_FAKEGEM_RECIPE_DOC-rake}"
107 RUBY_FAKEGEM_TASK_DOC="${RUBY_FAKEGEM_TASK_DOC-rdoc}"
108 RUBY_FAKEGEM_DOC_SOURCES="${RUBY_FAKEGEM_DOC_SOURCES-lib}"
109
110 RUBY_FAKEGEM_RECIPE_TEST="${RUBY_FAKEGEM_RECIPE_TEST-rake}"
111 RUBY_FAKEGEM_TASK_TEST="${RUBY_FAKEGEM_TASK_TEST-test}"
112
113 RUBY_FAKEGEM_BINWRAP="${RUBY_FAKEGEM_BINWRAP-*}"
114
115 [[ ${RUBY_FAKEGEM_TASK_DOC} == "" ]] && RUBY_FAKEGEM_RECIPE_DOC="none"
116
117 case ${RUBY_FAKEGEM_RECIPE_DOC} in
118 rake)
119 IUSE+=" doc"
120 ruby_add_bdepend "doc? ( dev-ruby/rake )"
121 RUBY_FAKEGEM_DOCDIR="doc"
122 ;;
123 rdoc)
124 IUSE+=" doc"
125 ruby_add_bdepend "doc? ( dev-ruby/rdoc )"
126 RUBY_FAKEGEM_DOCDIR="doc"
127 ;;
128 yard)
129 IUSE+="doc"
130 ruby_add_bdepend "doc? ( dev-ruby/yard )"
131 RUBY_FAKEGEM_DOCDIR="doc"
132 ;;
133 none)
134 [[ -n ${RUBY_FAKEGEM_DOCDIR} ]] && IUSE+=" doc"
135 ;;
136 esac
137
138 [[ ${RUBY_FAKEGEM_TASK_TEST} == "" ]] && RUBY_FAKEGEM_RECIPE_TEST="none"
139
140 case ${RUBY_FAKEGEM_RECIPE_TEST} in
141 rake)
142 IUSE+=" test"
143 ruby_add_bdepend "test? ( dev-ruby/rake )"
144 ;;
145 rspec)
146 IUSE+=" test"
147 # Also require a new enough rspec-core version that installs the
148 # rspec-2 wrapper.
149 ruby_add_bdepend "test? ( dev-ruby/rspec:2 >=dev-ruby/rspec-core-2.14.8-r2 )"
150 ;;
151 rspec3)
152 IUSE+=" test"
153 ruby_add_bdepend "test? ( dev-ruby/rspec:3 )"
154 ;;
155 cucumber)
156 IUSE+=" test"
157 # Unfortunately as of August 2012, cucumber is not supported on
158 # JRuby. We work it around here to avoid repeating the same
159 # code over and over again.
160 USE_RUBY="${USE_RUBY/jruby/}" ruby_add_bdepend "test? ( dev-util/cucumber )"
161 ;;
162 *)
163 RUBY_FAKEGEM_RECIPE_TEST="none"
164 ;;
165 esac
166
167 SRC_URI="mirror://rubygems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}${RUBY_FAKEGEM_SUFFIX:+-${RUBY_FAKEGEM_SUFFIX}}.gem"
168
169 ruby_add_bdepend virtual/rubygems
170 ruby_add_rdepend virtual/rubygems
171
172 # @FUNCTION: ruby_fakegem_gemsdir
173 # @RETURN: Returns the gem data directory
174 # @DESCRIPTION:
175 # This function returns the gems data directory for the ruby
176 # implementation in question.
177 ruby_fakegem_gemsdir() {
178 has "${EAPI}" 2 && ! use prefix && EPREFIX=
179
180 local _gemsitedir=$(ruby_rbconfig_value 'sitelibdir')
181 _gemsitedir=${_gemsitedir//site_ruby/gems}
182 _gemsitedir=${_gemsitedir#${EPREFIX}}
183
184 [[ -z ${_gemsitedir} ]] && {
185 eerror "Unable to find the gems dir"
186 die "Unable to find the gems dir"
187 }
188
189 echo "${_gemsitedir}"
190 }
191
192 # @FUNCTION: ruby_fakegem_doins
193 # @USAGE: file [file...]
194 # @DESCRIPTION:
195 # Installs the specified file(s) into the gems directory.
196 ruby_fakegem_doins() {
197 (
198 insinto $(ruby_fakegem_gemsdir)/gems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}
199 doins "$@"
200 ) || die "failed $0 $@"
201 }
202
203 # @FUNCTION: ruby_fakegem_newsins()
204 # @USAGE: file filename
205 # @DESCRIPTION:
206 # Installs the specified file into the gems directory using the provided filename.
207 ruby_fakegem_newins() {
208 (
209 # Since newins does not accept full paths but just basenames
210 # for the target file, we want to extend it here.
211 local newdirname=/$(dirname "$2")
212 [[ ${newdirname} == "/." ]] && newdirname=
213
214 local newbasename=$(basename "$2")
215
216 insinto $(ruby_fakegem_gemsdir)/gems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}${newdirname}
217 newins "$1" ${newbasename}
218 ) || die "failed $0 $@"
219 }
220
221 # @FUNCTION: ruby_fakegem_install_gemspec
222 # @DESCRIPTION:
223 # Install a .gemspec file for this package. Either use the file indicated
224 # by the RUBY_FAKEGEM_GEMSPEC variable, or generate one using
225 # ruby_fakegem_genspec.
226 ruby_fakegem_install_gemspec() {
227 local gemspec="${T}"/${RUBY_FAKEGEM_NAME}-${_ruby_implementation}
228
229 (
230 if [[ ${RUBY_FAKEGEM_GEMSPEC} != "" ]]; then
231 ruby_fakegem_gemspec_gemspec ${RUBY_FAKEGEM_GEMSPEC} ${gemspec}
232 else
233 local metadata="${WORKDIR}"/${_ruby_implementation}/metadata
234
235 if [[ -e ${metadata} ]]; then
236 ruby_fakegem_metadata_gemspec ${metadata} ${gemspec}
237 else
238 ruby_fakegem_genspec ${gemspec}
239 fi
240 fi
241 ) || die "Unable to generate gemspec file."
242
243 insinto $(ruby_fakegem_gemsdir)/specifications
244 newins ${gemspec} ${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}.gemspec || die "Unable to install gemspec file."
245 }
246
247 # @FUNCTION: ruby_fakegem_gemspec_gemspec
248 # @USAGE: gemspec-input gemspec-output
249 # @DESCRIPTION:
250 # Generates an installable version of the specification indicated by
251 # RUBY_FAKEGEM_GEMSPEC. This file is eval'ed to produce a final specification
252 # in a way similar to packaging the gemspec file.
253 ruby_fakegem_gemspec_gemspec() {
254 ${RUBY} -e "puts eval(File::open('$1').read).to_ruby" > $2
255 }
256
257 # @FUNCTION: ruby_fakegem_metadata_gemspec
258 # @USAGE: gemspec-metadata gemspec-output
259 # @DESCRIPTION:
260 # Generates an installable version of the specification indicated by
261 # the metadata distributed by the gem itself. This is similar to how
262 # rubygems creates an installation from a .gem file.
263 ruby_fakegem_metadata_gemspec() {
264 case ${RUBY} in
265 *jruby)
266 ${RUBY} -r yaml -e "puts Gem::Specification.from_yaml(File::open('$1').read).to_ruby" > $2
267 ;;
268 *)
269 ${RUBY} -r yaml -e "puts Gem::Specification.from_yaml(File::open('$1', :encoding => 'UTF-8').read).to_ruby" > $2
270 ;;
271 esac
272 }
273
274 # @FUNCTION: ruby_fakegem_genspec
275 # @USAGE: output-gemspec
276 # @DESCRIPTION:
277 # Generates a gemspec for the package and places it into the "specifications"
278 # directory of RubyGems.
279 # If the metadata normally distributed with a gem is present then that is
280 # used to generate the gemspec file.
281 #
282 # As a fallback we can generate our own version.
283 # In the gemspec, the following values are set: name, version, summary,
284 # homepage, and require_paths=["lib"].
285 # See RUBY_FAKEGEM_NAME and RUBY_FAKEGEM_VERSION for setting name and version.
286 # See RUBY_FAKEGEM_REQUIRE_PATHS for setting extra require paths.
287 ruby_fakegem_genspec() {
288 local required_paths="'lib'"
289 for path in ${RUBY_FAKEGEM_REQUIRE_PATHS}; do
290 required_paths="${required_paths}, '${path}'"
291 done
292
293 # We use the _ruby_implementation variable to avoid having stray
294 # copies with different implementations; while for now we're using
295 # the same exact content, we might have differences in the future,
296 # so better taking this into consideration.
297 local quoted_description=${DESCRIPTION//\"/\\\"}
298 cat - > $1 <<EOF
299 # generated by ruby-fakegem.eclass $Revision: 1.44 $
300 Gem::Specification.new do |s|
301 s.name = "${RUBY_FAKEGEM_NAME}"
302 s.version = "${RUBY_FAKEGEM_VERSION}"
303 s.summary = "${quoted_description}"
304 s.homepage = "${HOMEPAGE}"
305 s.require_paths = [${required_paths}]
306 end
307 EOF
308 }
309
310 # @FUNCTION: ruby_fakegem_binwrapper
311 # @USAGE: command [path] [content]
312 # @DESCRIPTION:
313 # Creates a new binary wrapper for a command installed by the RubyGem.
314 # path defaults to /usr/bin/$command content is optional and can be used
315 # to inject additional ruby code into the wrapper. This may be useful to
316 # e.g. force a specific version using the gem command.
317 ruby_fakegem_binwrapper() {
318 (
319 local gembinary=$1
320 local newbinary=${2:-/usr/bin/$gembinary}
321 local content=$3
322 local relativegembinary=${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}/bin/${gembinary}
323 local binpath=$(dirname $newbinary)
324 [[ ${binpath} = . ]] && binpath=/usr/bin
325
326 # Try to find out whether the package is going to install for
327 # one or multiple implementations; if we're installing for a
328 # *single* implementation, no need to use “/usr/bin/env ruby”
329 # in the shebang, and we can actually avoid errors when
330 # calling the script by default (see for instance the
331 # JRuby-specific commands).
332 local rubycmd=
333 for implementation in ${USE_RUBY}; do
334 # ignore non-enabled implementations
335 use ruby_targets_${implementation} || continue
336 if [ -z $rubycmd ]; then
337 # if no other implementation was set before, set it.
338 rubycmd="$(ruby_implementation_command ${implementation})"
339 else
340 # if another implementation already arrived, then make
341 # it generic and break out of the loop. This ensures
342 # that we do at most two iterations.
343 rubycmd="/usr/bin/env ruby"
344 break
345 fi
346 done
347
348 cat - > "${T}"/gembin-wrapper-${gembinary} <<EOF
349 #!${rubycmd}
350 # This is a simplified version of the RubyGems wrapper
351 #
352 # Generated by ruby-fakegem.eclass $Revision: 1.44 $
353
354 require 'rubygems'
355
356 ${content}
357 load Gem::default_path[-1] + "/gems/${relativegembinary}"
358
359 EOF
360
361 exeinto ${binpath:-/usr/bin}
362 newexe "${T}"/gembin-wrapper-${gembinary} $(basename $newbinary)
363 ) || die "Unable to create fakegem wrapper"
364 }
365
366 # @FUNCTION: all_fakegem_compile
367 # @DESCRIPTION:
368 # Build documentation for the package if indicated by the doc USE flag
369 # and if there is a documetation task defined.
370 all_fakegem_compile() {
371 if [[ -n ${RUBY_FAKEGEM_DOCDIR} ]] && use doc; then
372 case ${RUBY_FAKEGEM_RECIPE_DOC} in
373 rake)
374 rake ${RUBY_FAKEGEM_TASK_DOC} || die "failed to (re)build documentation"
375 ;;
376 rdoc)
377 rdoc ${RUBY_FAKEGEM_DOC_SOURCES} || die "failed to (re)build documentation"
378 ;;
379 yard)
380 yard doc ${RUBY_FAKEGEM_DOC_SOURCES} || die "failed to (re)build documentation"
381 ;;
382 esac
383 fi
384 }
385
386 # @FUNCTION: all_ruby_unpack
387 # @DESCRIPTION:
388 # Unpack the source archive, including support for unpacking gems.
389 all_ruby_unpack() {
390 # Special support for extracting .gem files; the file need to be
391 # extracted twice and the mtime from the archive _has_ to be
392 # ignored (it's always set to epoch 0).
393 for archive in ${A}; do
394 case "${archive}" in
395 *.gem)
396 # Make sure that we're not running unpack for more than
397 # one .gem file, since we won't support that at all.
398 [[ -d "${S}" ]] && die "Unable to unpack ${archive}, ${S} exists"
399
400 ebegin "Unpacking .gem file..."
401 tar -mxf "${DISTDIR}"/${archive} || die
402 eend $?
403
404 ebegin "Uncompressing metadata"
405 gunzip metadata.gz || die
406 eend $?
407
408 mkdir "${S}"
409 pushd "${S}" &>/dev/null
410
411 ebegin "Unpacking data.tar.gz"
412 tar -mxf "${my_WORKDIR}"/data.tar.gz || die
413 eend $?
414
415 popd &>/dev/null
416 ;;
417 *.patch.bz2)
418 # We apply the patches with RUBY_PATCHES directly from DISTDIR,
419 # as the WORKDIR variable changes value between the global-scope
420 # and the time all_ruby_unpack/_prepare are called. Since we can
421 # simply decompress them when applying, this is much easier to
422 # deal with for us.
423 einfo "Keeping ${archive} as-is"
424 ;;
425 *)
426 unpack ${archive}
427 ;;
428 esac
429 done
430 }
431
432 # @FUNCTION: all_ruby_compile
433 # @DESCRIPTION:
434 # Compile the package.
435 all_ruby_compile() {
436 all_fakegem_compile
437 }
438
439 # @FUNCTION: each_fakegem_test
440 # @DESCRIPTION:
441 # Run tests for the package for each ruby target if the test task is defined.
442 each_fakegem_test() {
443 case ${RUBY_FAKEGEM_RECIPE_TEST} in
444 rake)
445 ${RUBY} -S rake ${RUBY_FAKEGEM_TASK_TEST} || die "tests failed"
446 ;;
447 rspec)
448 RSPEC_VERSION=2 ruby-ng_rspec
449 ;;
450 rspec3)
451 RSPEC_VERSION=3 ruby-ng_rspec
452 ;;
453 cucumber)
454 ruby-ng_cucumber
455 ;;
456 none)
457 ewarn "each_fakegem_test called, but \${RUBY_FAKEGEM_RECIPE_TEST} is 'none'"
458 ;;
459 esac
460 }
461
462 if [[ ${RUBY_FAKEGEM_RECIPE_TEST} != none ]]; then
463 # @FUNCTION: each_ruby_test
464 # @DESCRIPTION:
465 # Run the tests for this package.
466 each_ruby_test() {
467 each_fakegem_test
468 }
469 fi
470
471 # @FUNCTION: each_fakegem_install
472 # @DESCRIPTION:
473 # Install the package for each ruby target.
474 each_fakegem_install() {
475 ruby_fakegem_install_gemspec
476
477 local _gemlibdirs="${RUBY_FAKEGEM_EXTRAINSTALL}"
478 for directory in bin lib; do
479 [[ -d ${directory} ]] && _gemlibdirs="${_gemlibdirs} ${directory}"
480 done
481
482 [[ -n ${_gemlibdirs} ]] && \
483 ruby_fakegem_doins -r ${_gemlibdirs}
484 }
485
486 # @FUNCTION: each_ruby_install
487 # @DESCRIPTION:
488 # Install the package for each target.
489 each_ruby_install() {
490 each_fakegem_install
491 }
492
493 # @FUNCTION: all_fakegem_install
494 # @DESCRIPTION:
495 # Install files common to all ruby targets.
496 all_fakegem_install() {
497 if [[ -n ${RUBY_FAKEGEM_DOCDIR} ]] && use doc; then
498 for dir in ${RUBY_FAKEGEM_DOCDIR}; do
499 [[ -d ${dir} ]] || continue
500
501 pushd ${dir} &>/dev/null
502 dohtml -r * || die "failed to install documentation"
503 popd &>/dev/null
504 done
505 fi
506
507 if [[ -n ${RUBY_FAKEGEM_EXTRADOC} ]]; then
508 dodoc ${RUBY_FAKEGEM_EXTRADOC} || die "failed to install further documentation"
509 fi
510
511 # binary wrappers; we assume that all the implementations get the
512 # same binaries, or something is wrong anyway, so...
513 if [[ -n ${RUBY_FAKEGEM_BINWRAP} ]]; then
514 local bindir=$(find "${D}" -type d -path "*/gems/${RUBY_FAKEGEM_NAME}-${RUBY_FAKEGEM_VERSION}/bin" -print -quit)
515
516 if [[ -d "${bindir}" ]]; then
517 pushd "${bindir}" &>/dev/null
518 local binaries=$(eval ls ${RUBY_FAKEGEM_BINWRAP})
519 for binary in $binaries; do
520 ruby_fakegem_binwrapper $binary
521 done
522 popd &>/dev/null
523 fi
524 fi
525 }
526
527 # @FUNCTION: all_ruby_install
528 # @DESCRIPTION:
529 # Install files common to all ruby targets.
530 all_ruby_install() {
531 all_fakegem_install
532 }

  ViewVC Help
Powered by ViewVC 1.1.20