Python packaging policy

From Mandriva Community Wiki

Jump to: navigation, search
This page is a draft. It requires improvements.
If you want to contribute, simply click on the edit tab. View the other pages to improve and maintain.

Contents

Tools

bdist_rpm5

The fastest way to pack a Python module for Mandriva is to use bdist_rpm5 class extending standard bdist_rpm and intended to create RPMv5 packages for Mandriva.

To use it, you should specify bdistr_rpm5 option for setup.py:

python setup.py bdist_rpm5

If everything goes fine, you will find ready-to-use SRPM inside the dist folder which contains spec file conforming to Mandriva Python policy.

If the tool fails to automatically detect values for some tags (license, description, etc.), it will set these fields to 'UNKNOWN' value.

Please look for 'UNKNOWN' words in the generated spec and fix them manually.

Py2pack

Py2pack script can be used to generate RPM spec file from Python modules using Python Package Index (PyPI). Currently py2pack can only generate spec files for OpenSUSE and Fedora, but one may use generated spec as a basis for the Mandriva one.

Rules

Naming

The name of a Python module 'foo' that provides an extension for Python library must be of the form 'python-foo', with foo being lower case.

Rationale: using a prefix is serving as a name space, and clearly shows how to find python modules.

Having everything in lower case is easier to read, and offers a consistent sorting.

Note: User-level applications written in Python do not need to follow these naming rules.

Tags

  • Group should be Development/Python
  • BuildArch must be noarch for pure Python packages

Build Requires

  • 'python' requirement is added automatically; if spec file is created using bdist_rpm5, python-setuptool dependency is also added.
  • All other dependencies should be added manually.
  • Arch dependent packages (compiled extensions) should require (at least) Python-devel.

Requires

  • Mandatory requirement python(abi) = VERSION is added automatically (by pythondeps.sh script)

Rpm macro

The following macros are available for Python packagers:

Marcro Description
 %py_ver Get Python version (as reported by invoking 'python -V')
 %py_incdir Path to Python include files (necessary to compile C extensions)
 %py_puresitedir Directory for the installation of third-party extensions which are platform-independent (written in pure Python)
 %py_platsitedir Directory for the installation of third-party extensions which are platform-dependent (C extensions)
 %py_platlibdir Platform-dependent directory for the installation for the standard library
 %py_purelibdir Platform-independent directory for the installation for the standard library
 %py_prefix Site-specific directory prefix where the platform independent Python files are installed (sys.prefix)
 %py_compile(O) Create .pyc files, dropping existing ones, if any. If -O option is specified, the same is performed for .pyo files.

%py_(pure|plat)(site|lib)dir are intended to be used instead of single %py_(site|lib)dir in order to place pure Python modules (that are architecture independent) in the same place on all hardware platforms, while putting compiled C extensions to arch-specific folders. For example, pure Python modules will go to /usr/lib/python on both x86 and x86-64, while compiled extensions will go to /usr/lib/python/ on x86 and /usr/lib64/python/ on x86-64. This allows packaging software consisting of pure Python modules only as noarch packages suitable for installing on all platforms.

For those familiar with Python distutils - %py_(pure|plat)(site|lib)dir correspond to results of distutils.sysconfig.get_python_lib() with appropriate parameter (plat_specific, standard _lib).

See http://archives.mandrivalinux.com/cooker/2006-01/msg01404.php for more discussions.

Obsolete Macros

The following macros are also available but marked as obsolete and not recommended:

Marcro Description
 %py_libdir The same as %py_purelibdir
 %py_sitedir The same as %py_puresitedir
 %python_sitearch The same as %py_platsitedir
 %python_sitelib The same as %py_puresitedir
 %python_version The same as %py_ver
 %py_requires(d) Insert build dependency on python; if '-d' option is specified then add build dependency on python-devel, as well.
For now, it is recommended to explicitly specify BuildRequires: python and BuildRequires: python-devel.

pyc/pyo policy

Files should be compiled before rpm creation and includes as they will otherwise be created if a package is run as root, and therefore created weird bug ( ie, module removed but still here, unowned files ).

To compile the .py moudles, add the following macros to the beginning of the spec:

%define python_compile_opt python -O -c "import compileall; compileall.compile_dir('.')"
%define python_compile     python -c "import compileall; compileall.compile_dir('.')"

Then in the %install section:

dir -d %{buildroot}%{py_platsitedir}/%{name}
%python_compile_opt
%python_compile
install *.pyc *.pyo %{buildroot}%{py_platsitedir}/%{name}

This will create a directory for the software under the platform sitedir, compile the python modules, then copy them to the directory created before. You may use 'pushd directory' before that code and 'popd' after the code if the python modules are in a directory below the root of the tarball.

And finally in the %files section:

%{py_platsitedir}/%{name}/*.pyc
%{py_platsitedir}/%{name}/*.pyo

egg-info

If egg-info files or directories are generated by the module's build scripts they must be included in the package because they might be needed by other applications and modules at runtime. So the %files section should contain something like this:

%{py_platsitedir}/%{name}-*.egg-info

Automated setup

If you use automated setup and invoke something like 'python setup.py install', you may set PYTHONDONTWRITEBYTECODE to zero or empty value to keep all files generated during installation. In addition, you may ask python to record names of installed files and then use the recorded list in the %files section:

%install
...
PYTHONDONTWRITEBYTECODE= python setup.py install --root=%{buildroot} --record=FILELIST
...

%files -f FILELIST
...


Example spec file

%define module	mymodule
%define name	python-%{module}
%define version 1.0
%define release 1

Summary: 	Example module
Name: 	 	%{name}
Version: 	%{version}
Release: 	%{release}
Source:         %{module}-%{version}.tar.gz
URL:		http://mypage.org/mymodule
License:	Apache License
Group:		Development/Python
BuildRoot:	%{_tmppath}/%{name}-%{version}-%{release}-buildroot
BuildRequires:	python-devel
BuildArch:	noarch

%description
Example Python module

%prep
%setup -q -n %{module}-%{version}

%install
rm -rf %{buildroot}
PYTHONDONTWRITEBYTECODE=  python setup.py install --root=%{buildroot} --record=FILELIST

%clean
rm -rf %{buildroot}

%files -f FILELIST
%defattr(-,root,root)
%doc *.txt

%changelog
* Tue Dec 05 2011 Author 1.0-1mdv2011.0
- Creation

Rebuild policy


Policy of other distribution

Personal tools