|
| 1 | +.. _how-to-handle-failures: |
| 2 | + |
| 3 | +How to handle test failures |
| 4 | +============================= |
| 5 | + |
| 6 | +.. _maxfail: |
| 7 | + |
| 8 | +Stopping after the first (or N) failures |
| 9 | +--------------------------------------------------- |
| 10 | + |
| 11 | +To stop the testing process after the first (N) failures: |
| 12 | + |
| 13 | +.. code-block:: bash |
| 14 | +
|
| 15 | + pytest -x # stop after first failure |
| 16 | + pytest --maxfail=2 # stop after two failures |
| 17 | +
|
| 18 | +
|
| 19 | +.. _pdb-option: |
| 20 | + |
| 21 | +Using PDB_ (Python Debugger) with pytest |
| 22 | +---------------------------------------------------------- |
| 23 | + |
| 24 | +Dropping to PDB_ (Python Debugger) on failures |
| 25 | +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 26 | + |
| 27 | +.. _PDB: http://docs.python.org/library/pdb.html |
| 28 | + |
| 29 | +Python comes with a builtin Python debugger called PDB_. ``pytest`` |
| 30 | +allows one to drop into the PDB_ prompt via a command line option: |
| 31 | + |
| 32 | +.. code-block:: bash |
| 33 | +
|
| 34 | + pytest --pdb |
| 35 | +
|
| 36 | +This will invoke the Python debugger on every failure (or KeyboardInterrupt). |
| 37 | +Often you might only want to do this for the first failing test to understand |
| 38 | +a certain failure situation: |
| 39 | + |
| 40 | +.. code-block:: bash |
| 41 | +
|
| 42 | + pytest -x --pdb # drop to PDB on first failure, then end test session |
| 43 | + pytest --pdb --maxfail=3 # drop to PDB for first three failures |
| 44 | +
|
| 45 | +Note that on any failure the exception information is stored on |
| 46 | +``sys.last_value``, ``sys.last_type`` and ``sys.last_traceback``. In |
| 47 | +interactive use, this allows one to drop into postmortem debugging with |
| 48 | +any debug tool. One can also manually access the exception information, |
| 49 | +for example:: |
| 50 | + |
| 51 | + >>> import sys |
| 52 | + >>> sys.last_traceback.tb_lineno |
| 53 | + 42 |
| 54 | + >>> sys.last_value |
| 55 | + AssertionError('assert result == "ok"',) |
| 56 | + |
| 57 | + |
| 58 | +.. _trace-option: |
| 59 | + |
| 60 | +Dropping to PDB_ at the start of a test |
| 61 | +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 62 | + |
| 63 | +``pytest`` allows one to drop into the PDB_ prompt immediately at the start of each test via a command line option: |
| 64 | + |
| 65 | +.. code-block:: bash |
| 66 | +
|
| 67 | + pytest --trace |
| 68 | +
|
| 69 | +This will invoke the Python debugger at the start of every test. |
| 70 | + |
| 71 | +.. _breakpoints: |
| 72 | + |
| 73 | +Setting breakpoints |
| 74 | +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 75 | + |
| 76 | +.. versionadded: 2.4.0 |
| 77 | +
|
| 78 | +To set a breakpoint in your code use the native Python ``import pdb;pdb.set_trace()`` call |
| 79 | +in your code and pytest automatically disables its output capture for that test: |
| 80 | + |
| 81 | +* Output capture in other tests is not affected. |
| 82 | +* Any prior test output that has already been captured and will be processed as |
| 83 | + such. |
| 84 | +* Output capture gets resumed when ending the debugger session (via the |
| 85 | + ``continue`` command). |
| 86 | + |
| 87 | + |
| 88 | +.. _`breakpoint-builtin`: |
| 89 | + |
| 90 | +Using the builtin breakpoint function |
| 91 | +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 92 | + |
| 93 | +Python 3.7 introduces a builtin ``breakpoint()`` function. |
| 94 | +Pytest supports the use of ``breakpoint()`` with the following behaviours: |
| 95 | + |
| 96 | + - When ``breakpoint()`` is called and ``PYTHONBREAKPOINT`` is set to the default value, pytest will use the custom internal PDB trace UI instead of the system default ``Pdb``. |
| 97 | + - When tests are complete, the system will default back to the system ``Pdb`` trace UI. |
| 98 | + - With ``--pdb`` passed to pytest, the custom internal Pdb trace UI is used with both ``breakpoint()`` and failed tests/unhandled exceptions. |
| 99 | + - ``--pdbcls`` can be used to specify a custom debugger class. |
| 100 | + |
| 101 | + |
| 102 | +.. _faulthandler: |
| 103 | + |
| 104 | +Fault Handler |
| 105 | +------------- |
| 106 | + |
| 107 | +.. versionadded:: 5.0 |
| 108 | + |
| 109 | +The `faulthandler <https://docs.python.org/3/library/faulthandler.html>`__ standard module |
| 110 | +can be used to dump Python tracebacks on a segfault or after a timeout. |
| 111 | + |
| 112 | +The module is automatically enabled for pytest runs, unless the ``-p no:faulthandler`` is given |
| 113 | +on the command-line. |
| 114 | + |
| 115 | +Also the :confval:`faulthandler_timeout=X<faulthandler_timeout>` configuration option can be used |
| 116 | +to dump the traceback of all threads if a test takes longer than ``X`` |
| 117 | +seconds to finish (not available on Windows). |
| 118 | + |
| 119 | +.. note:: |
| 120 | + |
| 121 | + This functionality has been integrated from the external |
| 122 | + `pytest-faulthandler <https://github.com/pytest-dev/pytest-faulthandler>`__ plugin, with two |
| 123 | + small differences: |
| 124 | + |
| 125 | + * To disable it, use ``-p no:faulthandler`` instead of ``--no-faulthandler``: the former |
| 126 | + can be used with any plugin, so it saves one option. |
| 127 | + |
| 128 | + * The ``--faulthandler-timeout`` command-line option has become the |
| 129 | + :confval:`faulthandler_timeout` configuration option. It can still be configured from |
| 130 | + the command-line using ``-o faulthandler_timeout=X``. |
| 131 | + |
| 132 | + |
| 133 | +.. _unraisable: |
| 134 | + |
| 135 | +Warning about unraisable exceptions and unhandled thread exceptions |
| 136 | +------------------------------------------------------------------- |
| 137 | + |
| 138 | +.. versionadded:: 6.2 |
| 139 | + |
| 140 | +.. note:: |
| 141 | + |
| 142 | + These features only work on Python>=3.8. |
| 143 | + |
| 144 | +Unhandled exceptions are exceptions that are raised in a situation in which |
| 145 | +they cannot propagate to a caller. The most common case is an exception raised |
| 146 | +in a :meth:`__del__ <object.__del__>` implementation. |
| 147 | + |
| 148 | +Unhandled thread exceptions are exceptions raised in a :class:`~threading.Thread` |
| 149 | +but not handled, causing the thread to terminate uncleanly. |
| 150 | + |
| 151 | +Both types of exceptions are normally considered bugs, but may go unnoticed |
| 152 | +because they don't cause the program itself to crash. Pytest detects these |
| 153 | +conditions and issues a warning that is visible in the test run summary. |
| 154 | + |
| 155 | +The plugins are automatically enabled for pytest runs, unless the |
| 156 | +``-p no:unraisableexception`` (for unraisable exceptions) and |
| 157 | +``-p no:threadexception`` (for thread exceptions) options are given on the |
| 158 | +command-line. |
| 159 | + |
| 160 | +The warnings may be silenced selectively using the :ref:`pytest.mark.filterwarnings ref` |
| 161 | +mark. The warning categories are :class:`pytest.PytestUnraisableExceptionWarning` and |
| 162 | +:class:`pytest.PytestUnhandledThreadExceptionWarning`. |
0 commit comments