(mention spec2scl) |
|||
Line 1: | Line 1: | ||
== Naming the SCL == | == Naming the SCL == | ||
Every SCL '''must''' have a name which does not match name of any other package. This is implied by the fact that the SCL metapackage's name is the same as name of the whole SCL. It is therefore not a good idea to name an SCL "ruby", when there is a "ruby" package - the name has to be altered. Packager '''should''' include something specific to the SCL (usually a specific version of included library) into it's name. Therefore "ruby193" is a good name for a collection that contains Ruby 1.9.3, etc. | Every SCL '''must''' have a name which does not match name of any other package. This is implied by the fact that the SCL metapackage's name is the same as name of the whole SCL. It is therefore not a good idea to name an SCL "ruby", when there is a "ruby" package - the name has to be altered. Packager '''should''' include something specific to the SCL (usually a specific version of included library) into it's name. Therefore "ruby193" is a good name for a collection that contains Ruby 1.9.3, etc. | ||
{{admon/tip|Automation|'''spec2scl''' was written to automate the task of converting specfiles to scl-enabled specfiles as much as possible. Install it by <code>yum install spec2scl</code> or use upstream version from https://bitbucket.org/bkabrda/spec2scl.}} | |||
== SCL Metapackage == | == SCL Metapackage == | ||
Line 158: | Line 160: | ||
=== Inside RPM Scripts === | === Inside RPM Scripts === | ||
It is not possible to describe the general process of rewriting <code>%prep</code>, <code>%build</code>, <code>%install</code>, <code>%check</code> and the <code>%pre*</code> and <code>%post*</code> scripts. There are however some general rules: | It is not possible to describe the general process of rewriting <code>%prep</code>, <code>%build</code>, <code>%install</code>, <code>%check</code> and the <code>%pre*</code> and <code>%post*</code> scripts. There are however some general rules: | ||
* Substitute all | * Substitute all occur | ||
Revision as of 08:34, 3 September 2013
Naming the SCL
Every SCL must have a name which does not match name of any other package. This is implied by the fact that the SCL metapackage's name is the same as name of the whole SCL. It is therefore not a good idea to name an SCL "ruby", when there is a "ruby" package - the name has to be altered. Packager should include something specific to the SCL (usually a specific version of included library) into it's name. Therefore "ruby193" is a good name for a collection that contains Ruby 1.9.3, etc.
SCL Metapackage
Every SCL must have a so called metapackage. This metapackage must have a runtime
and build
subpackages (the build
subpackage is needed for Koji builds, but may be left out for local builds).
An example SCL metapackage follows:
%global scl ruby193 %scl_package %scl %_scl_prefix /opt/myorganization %global install_scl 1 Summary: Package that installs %scl Name: %scl_name Version: 1 Release: 1%{?dist} License: GPLv2+ Requires: %{scl_prefix}js Requires: %{scl_prefix}rubygem-sqlite3 Requires: %{scl_prefix}rubygem-rails BuildRequires: scl-utils-build %description This is the main package for %scl Software Collection. %package runtime Summary: Package that handles %scl Software Collection. Requires: scl-utils %description runtime Package shipping essential scripts to work with %scl Software Collection. %package build Summary: Package shipping basic build configuration Requires: scl-utils-build %description build Package shipping essential configuration macros to build %scl Software Collection. %install rm -rf %{buildroot} mkdir -p %{buildroot}%{_scl_scripts}/root cat >> %{buildroot}%{_scl_scripts}/enable << EOF export PATH=%{_bindir}\${PATH:+:\${PATH}} export LD_LIBRARY_PATH=%{_libdir}\${LD_LIBRARY_PATH:+:\${LD_LIBRARY_PATH}} export MANPATH=%{_mandir}:\${MANPATH} EOF %scl_install %files %files runtime %scl_files %files build %{_root_sysconfdir}/rpm/macros.%{scl}-config %changelog * Fri Mar 30 2012 Bohuslav Kabrda <bkabrda@redhat.com> - 1-1 - Initial package.
Things to note here:
- The
-build
subpackage should include Requires: scl-utils-build. - The enable scriptlet must contain certain path redefinitions, according to what packages SCL contains and what it is supposed to do. Most importantly, use these, if needed:
PATH=%{_bindir}\${PATH:+:\${PATH}}
to run SCL binariesLD_LIBRARY_PATH=%{_libdir}\${LD_LIBRARY_PATH:+:\${LD_LIBRARY_PATH}}
to properly link against SCL shared objectsMANPATH=%{_mandir}:\${MANPATH}
to be able to diplay manpages present in the SCLPKG_CONFIG_PATH=%{_libdir}/pkgconfig\${PKG_CONFIG_PATH:+:\${PKG_CONFIG_PATH}}
orPKG_CONFIG_PATH=%{_datadir}/pkgconfig\${PKG_CONFIG_PATH:+:\${PKG_CONFIG_PATH}}
to enable usingpkg-config
filesXDG_DATA_PATH=%{_datadir}\${XDG_DATA_PATH:+:\${XDG_DATA_PATH}}
to use systemtap tapsets from the SCL- If you use any of the above, that contains %{_libdir}, the metapackage must be arch specific, otherwise it may be noarch.
- The
macros.%{scl}-config
in%{scl}-build
package contains the%scl
macro definition (name of the SCL). If you need to use some more macros for this SCL, add them into this file. - Unlike in specfiles of normal SCL packages (see below), the metapackage doesn't need to conditionalize SCL specific macros, as it can only be used as a part of SCL (for example, instead of
Requires: %{?scl_prefix}foo
, use justRequires: %{scl_prefix}foo
- notice the missing questionmark, that makes the first macro conditional). - When user runs
yum install ruby193
, he expects that the whole SCL with all dependencies gets installed. Because of that, it should haveRequires
on all package of that SCL, that are essential for its runtime.
Converting Packages for SCL
This section sums up the steps needed to take in order to convert a normal specfile to SCL specfile step by step. The resulting package should be buildable even without SCL - that means both without %{scl}-build
in the buildroot and with it. Advantage of this approach is, that both non-SCL packages like rubygem-foo
and SCL packages %{scl_prefix}rubygem_foo (depending on the SCL) can be built from the same SRPM, depending on the buildroot.
Converting Tags and Macro Definitions
Every SCL specfile must have %scl_package
macro specified (like any other macro, it must be conditionalized). This macro does this:
- Rewrites the standard macros (like
%_libdir
, etc...). - Introduces some SCL specific macros (like
%pkg_name
,%scl_prefix
or%_root_*
set of macros, that contain values of the original RPM macros.
One of the important macros is %pkg_name
, which represents the original package name - the %name
macro stands for the name with SCL prefix during SCL build. Therefore it is a good practice to also define %pkg_name
macro for non-SCL builds, to be able to use it consistently throughout the whole specfile.
So here is what the first two lines should look like:
%{?scl:%scl_package foo} %{!?scl:%global pkg_name %{name}}
Usual steps to adapt tag definitions for SCL builds are these:
- Name must be modified like this:
-Name: foo +Name: %{?scl_prefix}foo
- Requires and BuildRequires have to be considered carefully. These depend on what you are building/linking with and it is your decision as a packager. The only rule here is, that if building/linking with other SCL packages, their names must be also prefixed with conditionalized macro
%{?scl_prefix}
like this:
-Requires: bar +Requires: %{?scl_prefix}bar
- For example you can build and link the package with one SCL and one non-SCL package. The dependencies then look like this:
Requires spam -Requires: bar +Requires: %{?scl_prefix}bar BuildRequires: spam-devel -BuildRequires: bar-devel +BuildRequires: %{?scl_prefix}bar-devel
- Obsoletes, Conflicts and BuildConflicts must always be prefixed with
%{?scl_prefix}
. This is extremely important, as the SCLs are often used for deploying new packages on older systems (that may contain old packages, now obsoleted by the new ones), but they shouldn't Obsolete or Conflict with the non-SCL RPMs installed on the system (that's the idea of SCL :) ). For example:
-Obsoletes: foobar < 1.0 +Obsoletes: %{?scl_prefix}foobar < 1.0
- Provides tag must always be prefixed with
%{?scl_prefix}
. For example:
-Provides: foo(bar) +Provides: %{?scl_prefix}foo(bar)
- All the other tag definitions should be unchanged, unless they contain
%{name}
macro, which may need to be substituted for%pkg_name
(for example in SourceN tag, where it may be a part of URL). - There are some additional tags you should add. The package must require
%{scl}-runtime
, unless it depends on another package that requires%{scl}-runtime
.- Here is a rule of thumb: If packaging SCL with a language interpreter, like Ruby or Python, typically all other packages in the SCL depend on the interpreter. Therefore it is sufficient when only the interpreter runtime package requires
%{scl}-runtime
. Generally, every SCL package that can be installed on its own (without other packages from this SCL) should require the%{scl}-runtime
package. - The line to add is:
- Here is a rule of thumb: If packaging SCL with a language interpreter, like Ruby or Python, typically all other packages in the SCL depend on the interpreter. Therefore it is sufficient when only the interpreter runtime package requires
%{?scl:Requires %{scl}-runtime}
Subpackages
The same rules as for normal tags apply for subpackages tags. The only thing needs to be changed:
If (and only if) a package define its name with -n
, the name must be prefixed with %{?scl_prefix}
like this:
-%package -n foo +%package -n %{?scl_prefix}foo
This applies not only to %package
macro, but also for %description
and %files
.
Inter-SCL Dependencies
Available from scl-utils version 20120613.
There are situations where packages from an SCL have to depend on packages from another SCL. While using simple [Build]Requires: ruby193-rubygem-rails
is possible, it is not the wisest thing to do, since it hardcodes the information about how %{?scl_prefix}
gets expanded. If the expansion of this macro was changed (for example from ruby193-
to scl-ruby-193
, all the packages using such dependencies would need to be manually altered and rebuilt.
The scl-utils package therefore provides two ways of inter-SCL dependencies using macros. Note that both of them are in fact functions, so they need to be invoked without the curly braces to work properly:
%scl_require foo
macro is used to depend on the whole SCL. This is used if you want to use a functionality of an SCL, no matter what packages that SCL will install along the way. For example, theruby193
SCL contains the whole Ruby on Rails stack in version 3.2.3. If packaging an SCL that requires the whole Rails stack, you can simply use%{?scl:Requires: %scl_require ruby193}
.%scl_require_package foo pkg
provides the ability to depend on a specific package from another SCL. For example, if your package needs rubygem-minitest package fromruby193
SCL, you can simply use%{?scl:BuildRequires: %scl_require_package ruby193 rubygem-minitest}
. Installing the whole Rails stack in this case would be useless (and since rubygem-minitest is only a build dependency, it's not drawn in by default).
Note that both of these macros abstract from the way that %{?scl_prefix}
expands. Therefore, if any changes were made, a simple rebuild with new versions of SCL utils would be sufficient.
When specifying inter-SCL dependencies, these macros must be used.
Inside RPM Scripts
It is not possible to describe the general process of rewriting %prep
, %build
, %install
, %check
and the %pre*
and %post*
scripts. There are however some general rules:
- Substitute all occur