Hide navigation sidebar
Hide table of contents sidebar
Skip to content
Back to top
View this page
Toggle table of contents sidebar

# Extending tox

## Extensions points

tox uses pluggy to customize the default behavior. It provides an extension mechanism for plugin management by calling hooks.

Pluggy discovers a plugin by looking up for entry-points named `tox`, for example in a pyproject.toml:

    [project.entry-points.tox]
    your_plugin = "your_plugin.hooks"

Therefore, to start using a plugin, you solely need to install it in the same environment tox is running in and it will be discovered via the defined entry-point (in the example above, tox will load `your_plugin.hooks`).

A plugin is created by implementing extension points in the form of hooks. For example the following code snippet would define a new `--magic` command line interface flag the user can specify:

    from tox.config.cli.parser import ToxParser
    from tox.plugin import impl

    @impl
    def tox_add_option(parser: ToxParser) -> None:
        parser.add_argument("--magic", action="store_true", help="magical flag")

You can define such hooks either in a package installed alongside tox or within a `toxfile.py` found alongside your tox configuration file (root of your project).

tox.plugin.NAME = 'tox'

  the name of the tox hook

tox.plugin.impl

  decorator to mark tox plugin hooks

tox.plugin.spec.tox_add_core_config(core_conf, state)

  Called when the core configuration is built for a tox environment.

  Parameters:

    - core_conf (`ConfigSet`) – the core configuration object

    - state (`State`) – the global tox state object

  Return type:

    `None`

tox.plugin.spec.tox_add_env_config(env_conf, state)

  Called when configuration is built for a tox environment.

  Parameters:

    - env_conf (`EnvConfigSet`) – the core configuration object

    - state (`State`) – the global tox state object

  Return type:

    `None`

tox.plugin.spec.tox_add_option(parser)

  Add a command line argument. This is the first hook to be called, right after the logging setup and config source discovery.

  Parameters:

    parser (`ToxParser`) – the command line parser

  Return type:

    `None`

tox.plugin.spec.tox_after_run_commands(tox_env, exit_code, outcomes)

  Called after the commands set is executed.

  Parameters:

    - tox_env (`ToxEnv`) – the tox environment being executed

    - exit_code (`int`) – exit code of the command

    - outcomes (`list`[`Outcome`]) – outcome of each command execution

  Return type:

    `None`

tox.plugin.spec.tox_before_run_commands(tox_env)

  Called before the commands set is executed.

  Parameters:

    tox_env (`ToxEnv`) – the tox environment being executed

  Return type:

    `None`

tox.plugin.spec.tox_env_teardown(tox_env)

  Called after a tox environment has been teared down.

  Parameters:

    tox_env (`ToxEnv`) – the tox environment

  Return type:

    `None`

tox.plugin.spec.tox_on_install(tox_env, arguments, section, of_type)

  Called before executing an installation command.

  Parameters:

    - tox_env (`ToxEnv`) – the tox environment where the command runs in

    - arguments (`Any`) – installation arguments

    - section (`str`) – section of the installation

    - of_type (`str`) – type of the installation

  Return type:

    `None`

tox.plugin.spec.tox_register_tox_env(register)

  Register new tox environment type. You can register:

  - run environment: by default this is a local subprocess backed virtualenv Python

  - packaging environment: by default this is a PEP-517 compliant local subprocess backed virtualenv Python

  Parameters:

    register (`ToxEnvRegister`) – a object that can be used to register new tox environment types

  Return type:

    `None`

A plugin can define its plugin module a:

    def tox_append_version_info() -> str:
        return "magic"

and this message will be appended to the output of the `--version` flag.

## Adoption of a plugin under tox-dev Github organization

You’re free to host your plugin on your favorite platform, however the core tox development is happening on Github, under the `tox-dev` org organization. We are happy to adopt tox plugins under the `tox-dev` organization if:

- we determine it’s trying to solve a valid use case and it’s not malicious (e.g. no plugin that deletes the users home directory),

- it’s released on PyPI with at least 100 downloads per month (to ensure it’s a plugin used by people).

What’s in for you in this:

- you get owner rights on the repository under the tox-dev organization,

- exposure of your plugin under the core umbrella,

- backup maintainers from other tox plugin development.

How to apply:

- create an issue under the `tox-dev/tox` Github repository with the title Adopt plugin <name>,

- wait for the green light by one of our maintainers (see Current maintainers),

- follow the guidance by Github,

- (optionally) add at least one other people as co-maintainer on PyPI.

## Migration from tox 3

This section explains how the plugin interface changed between tox 3 and 4, and provides guidance for plugin developers on how to migrate.

### `tox_get_python_executable`

With tox 4 the Python discovery is performed `tox.tox_env.python.virtual_env.api._get_python` that delegates the job to `virtualenv`. Therefore first define a new virtualenv discovery mechanism and then set that by setting the `VIRTUALENV_DISCOVERY` environment variable.

### `tox_package`

Register new packager types via `tox_register_tox_env`.

### `tox_addoption`

Renamed to `tox_add_option`.