For ease of use, both `buildPythonPackage` and `buildPythonApplication` will
automatically add `pythonRelaxDepsHook` if either `pythonRelaxDeps` or
`pythonRemoveDeps` is specified.
#### Using unittestCheckHook {#using-unittestcheckhook}
`unittestCheckHook` is a hook which will set up (or configure) a [`checkPhase`](#ssec-check-phase) to run `python -m unittest discover`:
```nix
{
nativeCheckInputs = [ unittestCheckHook ];
unittestFlags = [
"-s"
"tests"
"-v"
];
}
```
`pytest` is compatible with `unittest`, so in most cases you can use `pytestCheckHook` instead.
#### Using sphinxHook {#using-sphinxhook}
The `sphinxHook` is a helpful tool to build documentation and manpages
using the popular Sphinx documentation generator.
It is setup to automatically find common documentation source paths and
render them using the default `html` style.
```nix
{
outputs = [
"out"
"doc"
];
nativeBuildInputs = [ sphinxHook ];
}
```
The hook will automatically build and install the artifact into the
`doc` output, if it exists. It also provides an automatic diversion
for the artifacts of the `man` builder into the `man` target.
```nix
{
outputs = [
"out"
"doc"
"man"
];
# Use multiple builders
sphinxBuilders = [
"singlehtml"
"man"
];
}
```
Overwrite `sphinxRoot` when the hook is unable to find your
documentation source root.
```nix
{
# Configure sphinxRoot for uncommon paths
sphinxRoot = "weird/docs/path";
}
```
The hook is also available to packages outside the python ecosystem by
referencing it using `sphinxHook` from top-level.
### Organising your packages {#organising-your-packages}
So far we discussed how you can use Python on Nix, and how you can develop with
it. We've looked at how you write expressions to package Python packages, and we
looked at how you can create environments in which specified packages are
available.
At some point you'll likely have multiple packages which you would
like to be able to use in different projects. In order to minimise unnecessary
duplication we now look at how you can maintain a repository with your
own packages. The important functions here are `import` and `callPackage`.
### Including a derivation using `callPackage` {#including-a-derivation-using-callpackage}
Earlier we created a Python environment using [`withPackages`](#python.withpackages-function), and included the
`toolz` package via a `let` expression.
Let's split the package definition from the environment definition.
We first create a function that builds `toolz` in `~/path/to/toolz/release.nix`
```nix
{
lib,
buildPythonPackage,
fetchPypi,
setuptools,
}:
buildPythonPackage rec {
pname = "toolz";
version = "0.10.0";
pyproject = true;
src = fetchPypi {
inherit pname version;
hash = "sha256-CP3V73yWSArRHBLUct4hrNMjWZlvaaUlkpm1QP66RWA=";
};
build-system = [ setuptools ];
meta = {
changelog = "https://github.com/pytoolz/toolz/releases/tag/${version}";
homepage = "https://github.com/pytoolz/toolz/";
description = "List processing tools and functional utilities";
license = lib.licenses.bsd3;
};
}
```
It takes an argument [`buildPythonPackage`](#buildpythonpackage-function). We now call this function using
`callPackage` in the definition of our environment
```nix
with import <nixpkgs> { };
(
let
toolz = callPackage /path/to/toolz/release.nix {
buildPythonPackage = python3Packages.buildPythonPackage;
};
in
python3.withPackages (ps: [
ps.numpy
toolz
])
).env
```
Important to remember is that the Python version for which the package is made
depends on the `python` derivation that is passed to [`buildPythonPackage`](#buildpythonpackage-function). Nix
tries to automatically pass arguments when possible, which is why generally you
don't explicitly define which `python` derivation should be used. In the above
example we use [`buildPythonPackage`](#buildpythonpackage-function) that is part of the set `python3Packages`,