Install/Build from source
=========================
.. note::
The instructions here are for building ``python-flint`` from source. For
most users it is recommended to install prebuilt binaries from ``PyPI`` or
``conda-forge`` instead. The instructions here are only needed if a binary
is not available for the platform. See :ref:`install_pip_conda`.
.. _simple_build_instructions:
Simple build instructions
-------------------------
The simple explanation of how to build ``python-flint`` from source is that
there are two steps:
- Install ``FLINT >= 3.0`` (see :ref:`installing_the_dependencies` below).
- Run ``pip install --no-binary python-flint python-flint``.
For example on Ubuntu 24.04 (but not older versions of Ubuntu) and when installing
``python-flint >= 0.7.0`` these two steps are::
sudo apt-get install libflint-dev
pip install --no-binary python-flint python-flint
The first command installs ``FLINT 3.0.1`` system-wide. With the second command
``pip`` will download the source code for the latest release of
``python-flint`` from PyPI, build it and install it into the active Python
environment. When building, ``pip`` will create a temporary isolated build
environment and will install the Python build dependencies (``Cython``,
``meson``, ...) into this environment so it is not necessary to install them
manually before running ``pip install``.
If you have the source code locally then you can build and install with::
pip install path/to/python-flint-directory-or-archive
After installing from source it is recommended to run the tests to check that
everything is working correctly as described in :ref:`test_installation`.
The remainder of this page provides more detailed instructions for:
- :ref:`supported_versions`.
- :ref:`building_from_source`.
- :ref:`building_older_versions`.
- :ref:`installing_the_dependencies`.
- :ref:`building_on_windows`.
- :ref:`non_standard_location`.
- :ref:`editable_install`.
.. note::
If you have more than one Python environment in your system then you need to
ensure that you are installing ``python-flint`` into the correct one. This
may require using the full path to ``pip`` or something like ``python3 -m
pip`` or you may need to activate the environment first.
.. _supported_versions:
Compatibility and supported versions
------------------------------------
.. note::
The compatibility information here is mostly only relevant when building
``python-flint`` from source. For most users it is recommended to install
pre-built binaries from ``PyPI`` or ``conda-forge``. See
:ref:`install_pip_conda`.
Generally each release of python-flint will be compatible with a range of
Python versions as described in `SPEC 0
`_. Since python-flint 0.5.0
the minimum supported FLINT version is ``3.0`` and each release of python-flint
supports all versions of ``FLINT >= 3.0`` available at the time of release.
Compatible versions (note that 0.7.0 is not yet released):
.. list-table:: python-flint compatibility
:header-rows: 1
* - python-flint
- Release date
- CPython
- FLINT
- Cython
* - 0.7.0
- Not yet
- 3.10-3.13
- 3.0-3.2?
- 3.0-3.1?
* - 0.6.0
- 1st Feb 2024
- 3.9-3.12
- 3.0
- 3.0
* - 0.5.0
- 22nd Oct 2023
- 3.9-3.12
- 3.0
- 3.0
* - 0.4.0
- 8th Aug 2023
- 3.9-3.11
- ``2.9.0`` (``Arb 2.23.0``)
- 3.0
* - 0.3.0
- 7th Dec 2018
- older Python versions
- ``< 3.0``
- ``< 3.0``
The minimum and maximum versions of Python represent the versions that are
tested in CI and for which binaries are provided on PyPI. It is likely that
``python-flint`` will work with other versions of Python (particularly older
Python versions) but this is not tested. It is possible that ``conda-forge``
may provide binaries for other versions of Python.
The minimum versions of Cython and FLINT are needed because it is known that
python-flint will not even build with older versions of these libraries. The
maximum versions of all dependencies are speculative and are based on the
versions that are known to work at the time of release. It is possible that
newer versions of Cython and FLINT will work but unlikely. During the year
following the release of ``python-flint 0.4.0`` every non-patch release of
Cython, FLINT, or CPython has required changes to the ``python-flint`` source
code to be able to build at all. In particular the following releases of
Cython, FLINT and CPython had changes that would prevent building all versions
of ``python-flint`` existing at the time:
- Flint 3.0 (Arb and Flint merged, lots of changes)
- Flint 3.1 (Function signature for ``fmpz_mod_mat`` changed)
- Flint 3.2 (``flint_randinit`` function name changed)
- Cython 3.0 (Handling of dunders changed)
- Cython 3.1 (Removal of ``PyInt_*`` functions)
- CPython 3.12 (Removal of distutils)
It is expected then that any future untested ``3.x`` version of Cython, FLINT,
or CPython will not be compatible with past versions of ``python-flint`` which
is why the table above lists the versions that were known to work at the time
of release.
As of python-flint 0.7.0, CPython ``3.13t`` free-threaded builds are tested in
CI but wheels are not provided on PyPI. There are no known issues related to
using python-flint in a `PEP 703 `_
free-threaded build but it is likely that mutating objects shared by multiple
threads is not safe.
It is also possible to build and use python-flint for PyPy. Other Python
implementations may work but are not tested.
.. _building_from_source:
Installing python-flint from source
-----------------------------------
.. note::
The instructions here are for building ``python-flint`` from source. For
most users it is recommended to install prebuilt binaries from ``PyPI`` or
``conda-forge`` instead. The instructions here are only needed if a binary
is not available for the platform. See :ref:`install_pip_conda`.
Also if you are working on ``python-flint`` itself then it is not
recommended to install the package as described here. Instead see the
:ref:`development_workflow` page for how to work on ``python-flint``.
The source code for ``python-flint`` is available on `GitHub
`_ and source distributions can
be downloaded from PyPI.
To build from source you must first install the dependencies (see
:ref:`installing_the_dependencies` below for instructions). Once the
dependencies are installed the following command will download the
``python-flint`` source code from PyPI, then build and install it into the
active Python environment::
pip install python-flint
This will try to install a binary first but will otherwise download, build and
install the latest release of ``python-flint`` from PyPI. If you definitely
want to build from source then you can use the ``--no-binary`` option::
pip install --no-binary python-flint python-flint
To install a specific version of ``python-flint`` from PyPI use e.g.::
pip install python-flint==0.7.0a4
To build and install the latest ``python-flint`` from git master you can
use::
pip install git+https://github.com/flintlib/python-flint.git@master
If you already have the source code downloaded or checked out from git, you can
``cd`` in and build and install with::
pip install .
Alternatively if you would like to build a wheel you can use
``pypa/build`` (first ``pip install build``)::
python -m build
Note that wheels built in this way will not include the dependencies (unlike
those distributed on PyPI) and cannot generally be installed on other systems.
Since ``python-flint 0.7.0`` the build system is ``meson`` and the build
requirements and version constraints are listed in ``pyproject.toml``. When
using build isolation the build requirements are installed in a temporary
virtual environment and so it should not be necessary to install them in the
active Python environment before running ``pip install``.
To build without build isolation with ``python-flint >= 0.7.0`` the
dependencies should first be installed in the active Python environment::
pip install Cython==3.0 meson meson-python ninja
pip install --no-build-isolation .
The ``meson`` build system will detect the versions of ``FLINT`` and Cython
installed in the system and will fail if they are not versions that were known
to be compatible at the time of the release of ``python-flint``. To build
against new, untested versions of ``FLINT`` or Cython you can pass the
``-Dflint_version_check=false`` option to the ``meson`` build system::
pip install --config-settings=setup-args="-Dflint_version_check=false" .
This is useful for testing new versions of ``FLINT`` with ``python-flint`` for
example if you want to build ``python-flint`` against the latest git version of
``FLINT``. See :ref:`supported_versions` above for the versions of ``FLINT``
and Cython that are supported by each version of ``python-flint``.
.. _building_older_versions:
Installing older versions from source
-------------------------------------
For ``python-flint < 0.6.0`` the source distribution did not include
``pyproject.toml`` and did not list the build requirements. Also for
``python-flint < 0.7.0`` the build requirements were different and there were
no version constraints listed on the dependencies. An list of the build
requirements for older versions of ``python-flint`` is given above in
:ref:`supported_versions`.
For ``python-flint < 0.7.0`` you will need to install the build requirements
manually, pin the version of Cython, and disable build isolation::
pip install Cython==3.0 setuptools numpy
pip install --no-build-isolation .
For ``python-flint < 0.4.0`` older versions of Cython are needed (``<= 0.29``).
If the build fails during the Cython step then it is likely that a different
version of Cython is needed.
.. _installing_the_dependencies:
Installing the dependencies
---------------------------
.. note::
It is not necessary to install the dependencies manually if you install
from PyPI or conda-forge as is recommended. When installing with ``conda``
the packages for the dependencies will also be installed from conda-forge
automatically. The binaries on PyPI are built with the dependencies bundled
in the wheel so that they do not need to be installed separately.
The following instructions are only for when building ``python-flint`` from
source if needed because a binary is not available for your platform. See
:ref:`install_pip_conda`.
The dependencies for building ``python-flint`` have changed over time. See
:ref:`supported_versions` above for the versions of the dependencies that are
supported by each version of ``python-flint``.
As of ``python-flint 0.7.0`` the runtime dependencies are Python and FLINT (at
least version 3.0) and the build-time dependencies are a C compiler,
``Cython``, ``meson``, ``meson-python`` and ``ninja``. Commands shown above
such as ``pip install .`` will install dependencies like ``Cython``, ``meson``
etc automatically. If you already have Python and a C compiler then what needs
to be installed before building ``python-flint`` is ``FLINT``.
At the time of writing, few Linux distributions provide ``FLINT >= 3.0`` in
their package repositories but for example on ``Ubuntu 24.04`` (but not any
earlier Ubuntu versions) you can install ``FLINT 3.0.1`` with::
sudo apt-get install libflint-dev
On MacOS you can install FLINT from homebrew with::
brew install flint
Other package managers may also provide ``FLINT`` but make sure that it is at
least version ``3.0``.
Once ``FLINT`` is installed it should be possible to build ``python-flint``
with any of the commands shown above e.g.::
pip install .
If it is not possible to install FLINT from a package manager then you need to
install GMP and MPFR and then build FLINT. You may still be able to install GMP
and MPFR from a package manager for example on Ubuntu::
sudo apt-get install libgmp-dev libmpfr-dev
The python-flint git repo has a script `bin/install_flint_ubuntu.sh
`_
that uses ``apt-get`` to install all dependencies needed to build ``FLINT``,
then builds ``FLINT`` from git using a specified git ref, and then installs
``FLINT`` system-wide::
bin/install_flint_ubuntu.sh v3.0.1 # version 3.0.1
bin/install_flint_ubuntu.sh main # latest git
The script can be adapted for other Linux distributions or MacOS to use
something other than ``apt-get`` to install dependencies.
If the whole stack needs to be built from source then download the source for
all three (`GMP `_, `MPFR
`_, `FLINT
`_) and build each with the standard::
./configure
make
make install
Adapt the ``configure`` commands as needed. Once these are installed you should
again be able to install ``python-flint`` with::
pip install .
.. _building_on_windows:
Installing from source on Windows
---------------------------------
.. note::
Building from source is not the recommended way for most users to install
``python-flint``, especially on Windows. For most users it is recommended to
use the binaries from ``PyPI`` or ``conda-forge`` except in cases where a
binary is not available for the platform. See :ref:`install_pip_conda`.
The instructions in :ref:`installing_the_dependencies` above are for Unix-like systems
(e.g. Linux or MacOS). On Windows the dependencies can be built in a similar
way using MSYS2 or under WSL. It is also possible to build ``python-flint`` and
its dependencies using MSVC but we do not currently provide instructions for
this. The `conda-forge recipe
`_ for ``python-flint``
builds on Windows using MSVC.
The `MSYS2 `_ project provides a Unix-like environment
for Windows and a package manager that can be used to install the dependencies.
The git repo for ``python-flint`` has a script `bin/cibw_before_all_windows.sh
`_
that installs the dependencies under MSYS2 and builds ``GMP``, ``MPFR``,
``FLINT``. This script is used for building the Windows binaries for PyPI. We
use the ``MinGW64`` (``mingw-w64-x86_64``) toolchain for building on Windows
rather than MSVC because it makes it possible to have a fat build of ``GMP``
(``--enable-fat``) which bundles micro-architecture specific optimisations for
``x86_64`` in a redistributable shared library. This is important for
performance on modern ``x86_64`` CPUs and is not possible if building ``GMP``
with MSVC. Since we need to use ``MinGW64`` for building ``GMP`` it is simplest
to use it for building ``MPFR``, ``FLINT`` and ``python-flint`` as well and
means that the same Unix-style build scripts can be used for all platforms.
The ``python-flint`` project does not have much experience using MSVC. Possibly
it would be better to build ``GMP`` using ``MinGW64`` and then build ``MPFR``,
``FLINT`` and ``python-flint`` using MSVC. It is also possible that it would be
better to build ``GMP``, ``MPFR``, ``FLINT`` using MinGW64 and then build
``python-flint`` using MSVC. Someone with more experience with MSVC would need
to help with this. We would welcome contributions that explain how to build
``python-flint`` and its dependencies using MSVC and/or that improve the build
process for distributed binaries on Windows.
.. _non_standard_location:
Using ``FLINT`` from a non-standard location
--------------------------------------------
.. note::
This section is only relevant when building ``python-flint`` from source.
For most users it is recommended to use the binaries from ``PyPI`` or
``conda-forge``. See :ref:`install_pip_conda`. The instructions here are
also not needed if you have installed ``FLINT`` and its dependencies
system-wide (e.g. using a package manager like ``apt-get`` or ``brew``).
If you have installed ``FLINT`` in a non-standard location then you will need
to instruct the ``python-flint`` build system where to find it and ensure that
the ``FLINT`` shared library can be found at runtime.
Since ``python-flint 0.7.0`` the build system is `meson
`_ and uses `pkg-config
`_ to find the
dependencies ``FLINT``, ``GMP`` and ``MPFR``. If these are installed in a
non-standard location then you can set the ``PKG_CONFIG_PATH`` environment
variable to point to the directory containing the ``.pc`` files for these
libraries. For example if you have installed ``FLINT`` in ``~/.local`` then you
can set the environment variable like this::
export PKG_CONFIG_PATH=$(pwd)/.local/lib/pkgconfig
Note that in some systems the ``lib/pkgconfig`` directory may be in a different
location e.g. ``lib64/pkgconfig``. It is also possible to pass the path to the
``pkg-config`` files to the ``meson-python`` build backend. For example if
building with ``pip``::
pip install \
--config-settings=setup-args="--pkg-config-path=$(pwd)/.local/lib/pkgconfig" \
python-flint
Setting the path to the ``pkg-config`` files in this way will allow the
``python-flint`` build system to find the ``FLINT`` library at build time. At
runtime the ``GMP``, ``MPFR`` and ``FLINT`` shared libraries must be in a
location where the dynamic linker can find them. On Linux the environment
variable ``LD_LIBRARY_PATH`` can be used to add the directory containing the
shared libraries to the search path. On MacOS the environment variable is
``DYLD_LIBRARY_PATH`` and on Windows it is ``PATH``. For example on Linux if
``FLINT`` is installed in ``~/.local/lib`` then you can set the environment
variable::
export LD_LIBRARY_PATH=$(pwd)/.local/lib
Using the environment variable like this means that it needs to be set every
time you run Python and use ``python-flint`` (the git repo provides ``source
bin/activate`` for doing this). A better option on Unix-like systems is to
install ``RPATH`` entries into the ``python-flint`` extension modules. On some
platforms this is done automatically by the ``meson`` build system but on
others it needs to be enabled explicitly. This can be done by passing the
``-Dadd_flint_rpath=true`` option to the ``meson`` build system::
pip install \
--config-settings=setup-args="--pkg-config-path=$(pwd)/.local/lib/pkgconfig" \
--config-settings=setup-args="-Dadd_flint_rpath=true" \
python-flint
For versions of ``python-flint`` before ``0.7.0`` the build system is
``setuptools`` (or ``numpy.distutils`` for ``Python < 3.12``). In this case
``pkg-config`` is not used. The following environment variables can be used to
set the location of the ``FLINT`` and other shared libraries at build time or
runtime::
C_INCLUDE_PATH=$(pwd)/.local/include # build-time
LIBRARY_PATH=$(pwd)/.local/lib # build-time
LDFLAGS=-Wl,-rpath=$(pwd)/.local/lib # build-time Linux or MacOS
LD_LIBRARY_PATH=$(pwd)/.local/lib # run-time Linux
DYLD_LIBRARY_PATH=$(pwd)/.local/lib # run-time MacOS
PATH=$(pwd)/.local/bin:$PATH # run-time Windows
A future improvement for ``python-flint`` could be if the meson build system
could build all dependencies (``GMP``, ``MPFR``, ``FLINT``) as shared libraries
and bundle them into ``python-flint`` although `this is not currently possible
with meson-python
`_. Otherwise
perhaps it could be possible to link ``FLINT`` and the other libraries
statically into ``python-flint``.
.. _editable_install:
Installing in editable mode
---------------------------
.. note::
For working on ``python-flint`` itself it is not recommended to install the
package into the active Python environment. Instead the development workflow
uses ``spin`` and ``meson`` to manage a local build of ``python-flint``. See
the :ref:`development_workflow` page for more information on how to develop
``python-flint``.
If you are building and testing ``python-flint`` while working on another
project then it may be useful to install ``python-flint`` in editable mode.
This allows making changes to the code of ``python-flint`` and seeing the
changes reflected in the other environment without needing to reinstall
``python-flint`` each time. This might be useful for example if you are using
``git bisect`` to find a change in ``python-flint`` (although it will not work
if you go back to versions before ``0.7.0``).
Since ``0.7.0`` it is possible to install ``python-flint`` as a
`meson-python editable install
`_.
To install ``python-flint`` in editable mode, first install ``FLINT`` and
then::
git clone https://github.com/flintlib/python-flint.git
cd python-flint
pip install meson meson-python cython ninja
pip install --no-build-isolation --editable .
python -m flint.test # recommended if you have made changes
This requires ``--no-build-isolation`` so that the build directory is not
deleted after install. Once installed in editable mode, each time Python is
restarted and ``python-flint`` is imported (``import flint``) an import hook
will check if the source code has changed and if so will rebuild the extension
modules and update the Python files. The rebuild uses ``meson`` for fast,
parallel, incremental rebuilds. Note that for the rebuild to happen and for the
changes to take effect it is necessary to start a new Python process e.g. by
running ``python`` again or by restarting the Jupyter kernel.
If you have installed ``FLINT`` in a non-standard location then you should set
the ``pkg-config`` path as described in :ref:`non_standard_location` above::
pip install
--no-build-isolation \
--config-settings=setup-args="--pkg-config-path=$(pwd)/.local/lib/pkgconfig" \
--editable .
To fully remove the editable install you can run::
pip uninstall python-flint
and then delete the ``build`` directory that was created in the root of the
``python-flint`` git repo.