{"id":17083587,"url":"https://github.com/gnikonorov/pytest-dynamicrerun","last_synced_at":"2025-03-23T13:51:01.238Z","repository":{"id":62584048,"uuid":"282079582","full_name":"gnikonorov/pytest-dynamicrerun","owner":"gnikonorov","description":"A pytest plugin to rerun tests dynamically based off of test outcome and output.","archived":false,"fork":false,"pushed_at":"2020-08-16T02:10:17.000Z","size":124,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-03-01T10:03:08.577Z","etag":null,"topics":["dynamic","plugin","pytest","rerun","testing"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gnikonorov.png","metadata":{"files":{"readme":"README.rst","changelog":"CHANGES.rst","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2020-07-23T23:43:53.000Z","updated_at":"2020-08-16T02:10:19.000Z","dependencies_parsed_at":"2022-11-03T21:48:06.969Z","dependency_job_id":null,"html_url":"https://github.com/gnikonorov/pytest-dynamicrerun","commit_stats":null,"previous_names":[],"tags_count":7,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnikonorov%2Fpytest-dynamicrerun","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnikonorov%2Fpytest-dynamicrerun/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnikonorov%2Fpytest-dynamicrerun/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gnikonorov%2Fpytest-dynamicrerun/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gnikonorov","download_url":"https://codeload.github.com/gnikonorov/pytest-dynamicrerun/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":245111928,"owners_count":20562511,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["dynamic","plugin","pytest","rerun","testing"],"created_at":"2024-10-14T13:02:57.005Z","updated_at":"2025-03-23T13:51:01.203Z","avatar_url":"https://github.com/gnikonorov.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"===================\npytest-dynamicrerun\n===================\n\n.. image:: https://img.shields.io/pypi/v/pytest-dynamicrerun.svg\n    :target: https://pypi.org/project/pytest-dynamicrerun\n    :alt: PyPI version\n\n.. image:: https://travis-ci.org/gnikonorov/pytest-dynamicrerun.svg?branch=master\n    :target: https://travis-ci.org/gnikonorov/pytest-dynamicrerun\n    :alt: See Build Status on Travis CI\n\npytest-dynamicrerun is a `pytest`_ plugin to rerun tests dynamically based off of test outcome and output.\n\nSupported versions\n------------------\n\nThis plugin is tested against the following Python and pytest versions. Each Python version is tested against all pytest versions. Please `file an issue`_ to request additional targets.\n\n:Python Versions:\n    python 3.5,\n    python 3.6,\n    python 3.7,\n    python 3.8,\n    pypy3\n:Pytest Versions:\n    5.4.0,\n    5.4.1,\n    5.4.2,\n    5.4.3,\n    6.0.0,\n    6.0.1\n\n\nInstallation\n------------\n\nInstall this plugin from `PyPI`_ by running the following::\n\n    $ pip install pytest-dynamicrerun\n\n\nUsage\n-----\n\nSpecifying how many times to rerun\n##################################\n\nBy default, one rerun attempt is made. You can set the amount of times to attempt a rerun by passing the ``--dynamic-rerun-attempts`` flag when invoking pytest or including the ``dynamic_rerun_attempts`` INI key.\n\nTo pass the flag::\n\n    python3 -m pytest --dynamic-rerun-attempts=3\n\nTo set the INI key add the following to your config file's ``[pytest]`` section::\n\n    [pytest]\n    dynamic_rerun_attempts = 123\n\nPassing a non positive integer value will set the number of rerun attempts to the default.\n\nSpecifying what to rerun on\n###########################\n\nBy default, all failed tests are rerun. You can change this behavior by either passing the ``--dynamic-rerun-triggers`` flag when invoking ``pytest`` or including the ``dynamic_rerun_triggers`` INI key. Note that regular expressions are allowed.\n\nTo pass the flag::\n\n    python3 -m pytest --dynamic-rerun-triggers=\"a triggering trace\"\n\nTo set the INI key add the following to your config file's ``[pytest]`` section::\n\n    [pytest]\n    dynamic_rerun_triggers = a triggering trace\n\nYou can accumulate values by either providing the flag multiple times or appending to the INI key. For example, the below two snippets would cause this plugin to trigger on both ``foo`` and ``bar``::\n\n    python3 -m pytest --dynamic-rerun-triggers=\"foo\" --dynamic-rerun-triggers=\"bar\"\n\n    [pytest]\n    dynamic_rerun_triggers = foo\n        bar\n\nNote that at this time only ``stdout``, ``stderr``, and exceptions are checked.\n\nSpecifying a rerun interval\n###########################\n\nYou can specify an interval to rerun tests on by either passing the ``--dynamic-rerun-schedule`` flag to python when invoking ``pytest`` or including the ``dyanmic_rerun_schedule`` INI key.\n\nInternally, this plugin uses `croniter`_ to schedule wait times. Because of this, we are able to schedule wait times with second level granularity. Visit the croniter repository ``README`` to find out more information on this.\n\nTo pass the flag::\n\n    python3 -m pytest --dynamic-rerun-schedule=\"* * * * * *\"\n\nTo set the INI key add the following to your config file's ``[pytest]`` section::\n\n    [pytest]\n    dynamic_rerun_schedule = * * * * * *\n\nNote that any valid cron schedule is accepted. If this flag is not passed or set in the INI file, this plugin will not take effect. Passing an invalid value will force the interval to default to ``* * * * * *`` ( every second ).\n\nIgnoring this plugin\n####################\n\nYou can ignore this plugin by passing the ``--dynamic-rerun-disabled`` flag to python when invoking ``pytest`` or including the ``dynamic_rerun_disabled`` INI key.\n\nTo pass the flag::\n\n    python3 -m pytest --dynamic-rerun-disabled=\"True\"\n\nTo set the INI key add the following to your config file's ``[pytest]`` section::\n\n    [pytest]\n    dynamic_rerun_disabled = True\n\n\nNote that if this flag is omitted, we do not disable the plugin ( so it is equivalent to passing ``--dynamic-rerun-disabled=False`` )\n\nUsing markers to rerun tests\n############################\n\nWe can achieve the above functionality through markers as well. This plugin defines the ``dynamicrerun`` mark, which can be used as follows::\n\n    @pytest.mark.dynamicrerun(attempts=10, disabled=False, schedule=\"* * * * * *\", triggers=\"foo\")\n    def test_print_foo():\n        print(\"foo\")\n\nMark arguments correspond to INI keys as follows:\n\n* ``attempts`` corresponds to ``dynamic_rerun_attempts``\n* ``disabled`` corresponds to ``dynanic_rerun_disabled``\n* ``schedule`` corresponds to ``dynamic_rerun_schedule``\n* ``triggers`` corresponds to ``dynamic_rerun_triggers``\n\nTo pass multiple values to the ``triggers`` argument, provide a list as so::\n\n    @pytest.mark.dynamicrerun(attempts=10, disabled=False, schedule=\"* * * * * *\", triggers=[\"foo\", \"bar\", \"baz\"])\n    def test_print_foo():\n        print(\"foo\")\n\nIn the above example, reruns will be triggered on ``foo``, ``bar``, and ``baz``.\n\nArgument precedence\n###################\n\nNote that first we check for arguments in markers, then command line switches, and only then do we check in INI files. Values found at lower levels ( those checked first ) take precedence over values defined at a higher level ( those checked later ).\n\nFor example, if we define the number of rerun attempts as 10 when invoking ``pytest`` from the command line, but later in a marker define the number of rerun attempts as 3, 3 would take precedence over 10 since we check markers before we check command line flags.\n\nDeveloping against this plugin\n------------------------------\nThis plugin exposes the following attributes on the ``item`` object:\n\n* ``dynamic_rerun_run_times ( list )``: The list of times this item was run by the plugin. Note this includes the original non dynamically rerun run.\n* ``dynamic_rerun_schedule(string)``: The schedule to rerun this item on. See the section ``Specifying a rerun interval`` above for more details.\n* ``dynamic_rerun_sleep_times (list)``: A list of `timedelta objects`_ representing the time slept in between reruns for the item\n* ``dynamic_rerun_triggers (list)``: The rerun triggers for this specific item. See the section ``Specifying what to rerun on`` above for more details.\n* ``max_allowed_dynamic_rerun_attempts(int)``: The maximum amount of times we are allowed to rerun this item. See the section ``Specifying how many times to rerun`` above for more details.\n* ``num_dynamic_reruns_kicked_off (int)``: The amount of reruns launched at the moment of inspection for this item.\n\nThis plugin exposes the following attributes on the ``session`` object:\n\n* ``dynamic_rerun_items (list)``: The list of items that are set to be dynamically rerun on the next iteration\n\n\nContributing\n------------\nContributions are always welcome. Tests can be run with `tox`_.\n\nPlease remember to add a `changelog`_ entry when adding a non-trivial feature.\n\n`pre-commit`_ is used to ensure basic checks pass.\n\nLicense\n-------\n\nDistributed under the terms of the `MIT`_ license, \"pytest-dynamicrerun\" is free and open source software\n\nIssues\n------\n\nIf you encounter any problems, please `file an issue`_ along with a detailed description.\n\n.. _`MIT`: http://opensource.org/licenses/MIT\n.. _`PyPI`: https://pypi.org/\n.. _`croniter`: https://github.com/kiorky/croniter/\n.. _`changelog`: https://github.com/gnikonorov/pytest-dynamicrerun/blob/master/CHANGES.rst\n.. _`file an issue`: https://github.com/gnikonorov/pytest-dynamicrerun/issues\n.. _`pre-commit`: https://pre-commit.com/\n.. _`pytest`: https://github.com/pytest-dev/pytest\n.. _`timedelta objects`: https://docs.python.org/3/library/datetime.html#timedelta-objects\n.. _`tox`: https://tox.readthedocs.io/en/latest/\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgnikonorov%2Fpytest-dynamicrerun","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgnikonorov%2Fpytest-dynamicrerun","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgnikonorov%2Fpytest-dynamicrerun/lists"}