Package: pypi2pkgbuild
Convert PyPI packages to Arch Linux packages, inspired frompip2arch.Handles packages of all sizes, from the simplest (pure Python, no dependencies)
to the most complex (C-level dependencies, external C libraries, etc., e.g.
most of the scientific Python stack, or GUI toolkits such as PyGObject and
wxPython)[1].[1]… with a bit of help.Dependencies and installationUsageUsage notesBuild-time dependencies of packagesVendored packagesHandling Python upgradesComparison with other toolsDependencies and installationpypi2pkgbuild.pydepends on the Arch Linux packagesnamcap,pkgfile, andpython-pip[2].[2]Officially, only the latest releases of pacman and pip are supported.
In practice, the hard requirements that I am aware of are pacman≥5.1
(which changed the behavior ofmakepkg--printsrcinfo) and pip≥10
(which changed the default format ofpip--list).The script can be installed withpip install[--user]., or can also be run
directly.One can even runpypi2pkgbuild.pyon itself to create a proper Arch package
(pypi2pkgbuild.pygit+https://github.com/anntzer/pypi2pkgbuild).A minimal test suite (checking thatpypi2pkgbuild.pycan indeed package
itself) can by run with pytest≥3.9 (pytest-sto keep the output to the
terminal).Usagepypi2pkgbuild.py PYPINAMEcreates a PKGBUILD for the latest version of the
given PyPI package and the current version of the Python interpreter (Python 3
only).  Prereleases are considered if the--preflag is passed.  Because
PyPI’s dependency information is somewhat unreliable, it installs the package
in a venv to figure out the dependencies.  Note that thanks topip’s wheel
cache, the build is later reused; i.e. the procedure entails very little extra
work.A-gitpackage can be built withpypi2pkgbuild.pygit+https://....The package is then built and verified withnamcap.The goal is to make this tool as automated as possible: if all the information
to build a package is (reasonably) accessible, this tool should be able to
build it.In order to provide additional information tomakepkg, editPKGBUILD_EXTRAS(which can also be done with the--pkgbuild-extrasflag).  This file is sourced at theendofPKGBUILD.  For ease of
patching, thebuild,package, and, where applicable,pkgverfunctions are defined by forwarding to_build,_package, and_pkgver.  A_checkfunction is also available, but not used (due to the
lack of standard testing CLI).  Some useful examples ofPKGBUILD_EXTRASare
listed in thepkgbuild-extrasdirectory.Usage notesIt is suggested to create an alias with standard options set, e.g.aliaspypi2pkgbuild.py='PKGEXT=.pkg.tar pypi2pkgbuild.py -g cython -b /tmp/pypi2pkgbuild/ -f'By default, thepkgrelof (standard) packages is set to00.  This
allows automatic upgrading into official packages (and AUR ones, if an AUR
helper is used) whenever the repositories are updated.  Additionally, the use
of00rather than0serves as a (weak) marker that the package was
automatically generated by this tool.  In order to prevent such an upgrade,
one can use the--pkgrelflag to setpkgrelto, e.g.,99.If one wishes to completely bypass AUR Python packages while maintaining the
use of an AUR helper for non-Python packages, one can define a shell function
that excludespypi2pkgbuild.py-generated packages that do not appear in
the official repositories, e.g., forpacaur:pacaur(){if[["$1"="-Syu"]];then# Update, in case some packages moved in or out of the official repos.sudopacman-Sy# Upgrade everything except python packages with pkgver=00 or 99.PKGEXT=.pkg.tarcommandpacaur-Su--ignore\"$(pacman-Qm|grep'^python-.*-\(00\|99\)$'|cut-d' '-f1|paste-sd,)"elsecommandpacaur"$@"fi}This function will not bypass Python packages explicitly installed from the
AUR, as the user may have done so to bypass some incorrect packaging bypypi2pkgbuild.py.  It is recommended to use the-iflag to calls
topypi2pkgbuild.py(e.g. in an alias) to exclude packages that are
mishandled bypypi2pkgbuild.py(seemispackaged packages).  The-iflag can be passed multiple times; passing an empty argument to it will clear
the ignore list defined so far.In order to package a locally available git repository, use$pypi2pkgbuild.pygit+file://$absolute_path_to_repo# (e.g. file:///home/...)In order to package a locally available sdist or wheel, use$pypi2pkgbuild.pyfile://$absolute_path_to_file# (e.g. file:///home/...)Note that in both casesabsolutepaths are necessary.Building packages from local repos or wheels needs to be done in topological
order of the dependencies (so thatpypi2pkgbuild.pycan find that
the dependencies are actually present), or by passing the-dflag
(“do not build dependencies”); if it is used, the Arch package may
not use the correct dependency names (if they are not of the formpython-pep503-normalized-name).By default,pypi2pkgbuild.pyignorespipconfig files such as~/.config/pip/pip.conf.  An explicitly setPIP_CONFIG_FILEwill be
respected, but may causepypi2pkgbuild.pyto fail as somepipcalls
will be unexpectedly modified.Likewise, user-site packages are ignored unlessPYTHONNOUSERSITEis
explicitly set to an empty value.Build-time dependencies of packagespypi2pkgbuild.pyattempts to guess whetherCythonandSWIGare
build-time dependencies by checking for the presence of.pyxand.ifiles, respectively.  If this is not desired, set the--guess-makedependsoption accordingly.pypi2pkgbuild.pyguesses whethernumpyis a build-time dependency by
attempting a build withoutnumpy, then, in case of failure, a build withnumpy.Additional Python build-time dependencies (i.e.,setup_requires) can be
specified (as PyPI names) using the--setup-requiresflag, or just as
normal entries using--pkgbuild-extras(they will be installed into the
build virtualenv).Additional non-Python build-time dependencies can be set asmakedependsusing--pkgbuild-extras; they will be installedbeforepypi2pkgbuild.pyattempts to build a wheel for the package.Vendored packagesSome Arch packages (e.g.ipython) include a number of smaller PyPI
packages.Because it is not possible to assign a meaningful version automatically,pypi2pkgbuild.pyinstead creates an independent Arch package for each of
the PyPI packages (with two dashes in the name, to prevent name conflicts) and
a master package that depends on all of them.  Thepkgrelof the master
package is set to$official_pkgrel.99, so that the package appears more
recent than the current official version but older than any future official
version.  All these packagesconflictwith all versions of the official
package (except the newly created package), so upgrading should work fine when
the official package is actually updated.However, dependencies are still expressed using the master package (to avoid
breakage on upgrade into an official package), so internal dependencies will
appear be circular.All the packages are placed in a subfolder namedmeta:$pkgname, so one can
easily install everything bycd’ing there and running$sudopacman-U--asdeps**/*.xz$sudopacman-D--asexplicit$pkgname/$pkgname.tar.xzHandling Python upgradesWhen the Python minor version (xin3.x) is upgraded, it is necessary
to regenerate all self-built packages.  This can be done e.g. with$pypi2pkgbuild.py$(ls/usr/lib/python3.$oldver/site-packages|grep-Po'.*(?=-.*.dist-info)')Comparison with other toolsOther similar tools includepip2arch,pip2pkgbuild, andfpm.  To the best
of my knowledge, the features below are unique to PyPI2PKGBUILD; please let me
know if this is incorrect.Supports wheels (the default is to preferany-platform wheels, thensdists, thenmanylinux1wheels, but this can be changed using--pkgtypes).Resolves Python dependencies via installation in a temporary virtualenv, and
also creates PKGBUILDs for those that are not available as official packages.Resolves binary dependencies vianamcapand adds them to thedependsarray if they are installed (thus, it is suggested to first install
them as--asdepsand then let the generated PKGBUILD pick them up as
dependencies).  Note that some packages are distributed with a copy of the
required libraries; in this case,pypi2pkgbuild.py’s behavior will depend
on whether the package defaults to using the system-wide library or its own
copy.Automatically tries to fetch a missing license file from Github, if
applicable.Automatically builds the package (with options given in--makepkg=...)
and runnamcap.Automatically builds all outdated dependencies via-u.