x11-misc/alock: Take ownership of package
[gentoo.git] / eclass / python-any-r1.eclass
1 # Copyright 1999-2015 Gentoo Foundation
2 # Distributed under the terms of the GNU General Public License v2
3 # $Id$
4
5 # @ECLASS: python-any-r1.eclass
6 # @MAINTAINER:
7 # Python team <python@gentoo.org>
8 # @AUTHOR:
9 # Author: Michał Górny <mgorny@gentoo.org>
10 # Based on work of: Krzysztof Pawlik <nelchael@gentoo.org>
11 # @BLURB: An eclass for packages having build-time dependency on Python.
12 # @DESCRIPTION:
13 # A minimal eclass for packages which need any Python interpreter
14 # installed without a need for explicit choice and invariability.
15 # This usually involves packages requiring Python at build-time
16 # but having no other relevance to it.
17 #
18 # This eclass provides a minimal PYTHON_DEPS variable with a dependency
19 # string on any of the supported Python implementations. It also exports
20 # pkg_setup() which finds the best supported implementation and sets it
21 # as the active one.
22 #
23 # Optionally, you can define a python_check_deps() function. It will
24 # be called by the eclass with EPYTHON set to each matching Python
25 # implementation and it is expected to check whether the implementation
26 # fulfills the package requirements. You can use the locally exported
27 # PYTHON_USEDEP to check USE-dependencies of relevant packages. It
28 # should return a true value (0) if the Python implementation fulfills
29 # the requirements, a false value (non-zero) otherwise.
30 #
31 # Please note that python-any-r1 will always inherit python-utils-r1
32 # as well. Thus, all the functions defined there can be used in the
33 # packages using python-any-r1, and there is no need ever to inherit
34 # both.
35 #
36 # For more information, please see the wiki:
37 # https://wiki.gentoo.org/wiki/Project:Python/python-any-r1
38
39 case "${EAPI:-0}" in
40         0|1|2|3|4|5|6)
41                 ;;
42         *)
43                 die "Unsupported EAPI=${EAPI} (unknown) for ${ECLASS}"
44                 ;;
45 esac
46
47 if [[ ! ${_PYTHON_ANY_R1} ]]; then
48
49 if [[ ${_PYTHON_R1} ]]; then
50         die 'python-any-r1.eclass can not be used with python-r1.eclass.'
51 elif [[ ${_PYTHON_SINGLE_R1} ]]; then
52         die 'python-any-r1.eclass can not be used with python-single-r1.eclass.'
53 fi
54
55 inherit python-utils-r1
56
57 fi
58
59 EXPORT_FUNCTIONS pkg_setup
60
61 if [[ ! ${_PYTHON_ANY_R1} ]]; then
62
63 # @ECLASS-VARIABLE: PYTHON_COMPAT
64 # @REQUIRED
65 # @DESCRIPTION:
66 # This variable contains a list of Python implementations the package
67 # supports. It must be set before the `inherit' call. It has to be
68 # an array.
69 #
70 # Example:
71 # @CODE
72 # PYTHON_COMPAT=( python{2_5,2_6,2_7} )
73 # @CODE
74
75 # @ECLASS-VARIABLE: PYTHON_COMPAT_OVERRIDE
76 # @INTERNAL
77 # @DESCRIPTION:
78 # This variable can be used when working with ebuilds to override
79 # the in-ebuild PYTHON_COMPAT. It is a string naming the implementation
80 # which will be used to build the package. It needs to be specified
81 # in the calling environment, and not in ebuilds.
82 #
83 # It should be noted that in order to preserve metadata immutability,
84 # PYTHON_COMPAT_OVERRIDE does not affect dependencies. The value of
85 # EPYTHON and eselect-python preferences are ignored. Dependencies need
86 # to be satisfied manually.
87 #
88 # Example:
89 # @CODE
90 # PYTHON_COMPAT_OVERRIDE='pypy' emerge -1v dev-python/bar
91 # @CODE
92
93 # @ECLASS-VARIABLE: PYTHON_REQ_USE
94 # @DEFAULT_UNSET
95 # @DESCRIPTION:
96 # The list of USEflags required to be enabled on the Python
97 # implementations, formed as a USE-dependency string. It should be valid
98 # for all implementations in PYTHON_COMPAT, so it may be necessary to
99 # use USE defaults.
100 #
101 # Example:
102 # @CODE
103 # PYTHON_REQ_USE="gdbm,ncurses(-)?"
104 # @CODE
105 #
106 # It will cause the Python dependencies to look like:
107 # @CODE
108 # || ( dev-lang/python:X.Y[gdbm,ncurses(-)?] ... )
109 # @CODE
110
111 # @ECLASS-VARIABLE: PYTHON_DEPS
112 # @DESCRIPTION:
113 # This is an eclass-generated Python dependency string for all
114 # implementations listed in PYTHON_COMPAT.
115 #
116 # Any of the supported interpreters will satisfy the dependency.
117 #
118 # Example use:
119 # @CODE
120 # DEPEND="${RDEPEND}
121 #       ${PYTHON_DEPS}"
122 # @CODE
123 #
124 # Example value:
125 # @CODE
126 # || ( dev-lang/python:2.7[gdbm]
127 #       dev-lang/python:2.6[gdbm] )
128 # @CODE
129
130 _python_any_set_globals() {
131         local usestr i PYTHON_PKG_DEP
132         [[ ${PYTHON_REQ_USE} ]] && usestr="[${PYTHON_REQ_USE}]"
133
134         _python_set_impls
135
136         PYTHON_DEPS=
137         for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do
138                 python_export "${i}" PYTHON_PKG_DEP
139
140                 PYTHON_DEPS="${PYTHON_PKG_DEP} ${PYTHON_DEPS}"
141         done
142         PYTHON_DEPS="|| ( ${PYTHON_DEPS})"
143         readonly PYTHON_DEPS
144 }
145 _python_any_set_globals
146 unset -f _python_any_set_globals
147
148 # @ECLASS-VARIABLE: PYTHON_USEDEP
149 # @DESCRIPTION:
150 # An eclass-generated USE-dependency string for the currently tested
151 # implementation. It is set locally for python_check_deps() call.
152 #
153 # The generate USE-flag list is compatible with packages using python-r1,
154 # python-single-r1 and python-distutils-ng eclasses. It must not be used
155 # on packages using python.eclass.
156 #
157 # Example use:
158 # @CODE
159 # python_check_deps() {
160 #       has_version "dev-python/foo[${PYTHON_USEDEP}]"
161 # }
162 # @CODE
163 #
164 # Example value:
165 # @CODE
166 # python_targets_python2_7(-)?,python_single_target_python2_7(+)?
167 # @CODE
168
169 # @FUNCTION: python_gen_any_dep
170 # @USAGE: <dependency-block>
171 # @DESCRIPTION:
172 # Generate an any-of dependency that enforces a version match between
173 # the Python interpreter and Python packages. <dependency-block> needs
174 # to list one or more dependencies with verbatim '${PYTHON_USEDEP}'
175 # references (quoted!) that will get expanded inside the function.
176 #
177 # This should be used along with an appropriate python_check_deps()
178 # that checks which of the any-of blocks were matched.
179 #
180 # Example use:
181 # @CODE
182 # DEPEND="$(python_gen_any_dep '
183 #       dev-python/foo[${PYTHON_USEDEP}]
184 #       || ( dev-python/bar[${PYTHON_USEDEP}]
185 #               dev-python/baz[${PYTHON_USEDEP}] )')"
186 #
187 # python_check_deps() {
188 #       has_version "dev-python/foo[${PYTHON_USEDEP}]" \
189 #               && { has_version "dev-python/bar[${PYTHON_USEDEP}]" \
190 #                       || has_version "dev-python/baz[${PYTHON_USEDEP}]"; }
191 # }
192 # @CODE
193 #
194 # Example value:
195 # @CODE
196 # || (
197 #       (
198 #               dev-lang/python:2.7
199 #               dev-python/foo[python_targets_python2_7(-)?,python_single_target_python2_7(+)?]
200 #               || ( dev-python/bar[python_targets_python2_7(-)?,python_single_target_python2_7(+)?]
201 #                       dev-python/baz[python_targets_python2_7(-)?,python_single_target_python2_7(+)?] )
202 #       )
203 #       (
204 #               dev-lang/python:3.3
205 #               dev-python/foo[python_targets_python3_3(-)?,python_single_target_python3_3(+)?]
206 #               || ( dev-python/bar[python_targets_python3_3(-)?,python_single_target_python3_3(+)?]
207 #                       dev-python/baz[python_targets_python3_3(-)?,python_single_target_python3_3(+)?] )
208 #       )
209 # )
210 # @CODE
211 python_gen_any_dep() {
212         debug-print-function ${FUNCNAME} "${@}"
213
214         local depstr=${1}
215         [[ ${depstr} ]] || die "No dependency string provided"
216
217         local PYTHON_PKG_DEP out=
218         for i in "${_PYTHON_SUPPORTED_IMPLS[@]}"; do
219                 local PYTHON_USEDEP="python_targets_${i}(-),python_single_target_${i}(+)"
220                 python_export "${i}" PYTHON_PKG_DEP
221
222                 local i_depstr=${depstr//\$\{PYTHON_USEDEP\}/${PYTHON_USEDEP}}
223                 out="( ${PYTHON_PKG_DEP} ${i_depstr} ) ${out}"
224         done
225         echo "|| ( ${out})"
226 }
227
228 # @FUNCTION: _python_EPYTHON_supported
229 # @USAGE: <epython>
230 # @INTERNAL
231 # @DESCRIPTION:
232 # Check whether the specified implementation is supported by package
233 # (specified in PYTHON_COMPAT). Calls python_check_deps() if declared.
234 _python_EPYTHON_supported() {
235         debug-print-function ${FUNCNAME} "${@}"
236
237         local EPYTHON=${1}
238         local i=${EPYTHON/./_}
239
240         case "${i}" in
241                 python*|jython*|pypy*)
242                         ;;
243                 *)
244                         ewarn "Invalid EPYTHON: ${EPYTHON}"
245                         return 1
246                         ;;
247         esac
248
249         if has "${i}" "${_PYTHON_SUPPORTED_IMPLS[@]}"; then
250                 if python_is_installed "${i}"; then
251                         if declare -f python_check_deps >/dev/null; then
252                                 local PYTHON_USEDEP="python_targets_${i}(-),python_single_target_${i}(+)"
253                                 python_check_deps
254                                 return ${?}
255                         fi
256
257                         return 0
258                 fi
259         elif ! has "${i}" "${_PYTHON_ALL_IMPLS[@]}"; then
260                 ewarn "Invalid EPYTHON: ${EPYTHON}"
261         fi
262         return 1
263 }
264
265 # @FUNCTION: python_setup
266 # @DESCRIPTION:
267 # Determine what the best installed (and supported) Python
268 # implementation is, and set the Python build environment up for it.
269 #
270 # This function will call python_check_deps() if defined.
271 python_setup() {
272         debug-print-function ${FUNCNAME} "${@}"
273
274         # support developer override
275         if [[ ${PYTHON_COMPAT_OVERRIDE} ]]; then
276                 local impls=( ${PYTHON_COMPAT_OVERRIDE} )
277                 [[ ${#impls[@]} -eq 1 ]] || die "PYTHON_COMPAT_OVERRIDE must name exactly one implementation for python-any-r1"
278
279                 ewarn "WARNING: PYTHON_COMPAT_OVERRIDE in effect. The following Python"
280                 ewarn "implementation will be used:"
281                 ewarn
282                 ewarn " ${PYTHON_COMPAT_OVERRIDE}"
283                 ewarn
284                 ewarn "Dependencies won't be satisfied, and EPYTHON/eselect-python will be ignored."
285
286                 python_export "${impls[0]}" EPYTHON PYTHON
287                 python_wrapper_setup
288                 return
289         fi
290
291         # first, try ${EPYTHON}... maybe it's good enough for us.
292         if [[ ${EPYTHON} ]]; then
293                 if _python_EPYTHON_supported "${EPYTHON}"; then
294                         python_export EPYTHON PYTHON
295                         python_wrapper_setup
296                         return
297                 fi
298         fi
299
300         # then, try eselect-python
301         local variant i
302         for variant in '' '--python2' '--python3'; do
303                 i=$(eselect python --show ${variant} 2>/dev/null)
304
305                 if [[ ! ${i} ]]; then
306                         # no eselect-python?
307                         break
308                 elif _python_EPYTHON_supported "${i}"; then
309                         python_export "${i}" EPYTHON PYTHON
310                         python_wrapper_setup
311                         return
312                 fi
313         done
314
315         # fallback to best installed impl.
316         # (reverse iteration over _PYTHON_SUPPORTED_IMPLS)
317         for (( i = ${#_PYTHON_SUPPORTED_IMPLS[@]} - 1; i >= 0; i-- )); do
318                 python_export "${_PYTHON_SUPPORTED_IMPLS[i]}" EPYTHON PYTHON
319                 if _python_EPYTHON_supported "${EPYTHON}"; then
320                         python_wrapper_setup
321                         return
322                 fi
323         done
324
325         eerror "No Python implementation found for the build. This is usually"
326         eerror "a bug in the ebuild. Please report it to bugs.gentoo.org"
327         eerror "along with the build log."
328         echo
329         die "No supported Python implementation installed."
330 }
331
332 # @FUNCTION: python-any-r1_pkg_setup
333 # @DESCRIPTION:
334 # Runs python_setup during from-source installs.
335 #
336 # In a binary package installs is a no-op. If you need Python in pkg_*
337 # phases of a binary package, call python_setup directly.
338 python-any-r1_pkg_setup() {
339         debug-print-function ${FUNCNAME} "${@}"
340
341         [[ ${MERGE_TYPE} != binary ]] && python_setup
342 }
343
344 _PYTHON_ANY_R1=1
345 fi