# pytest ## code #### basic ``` code=python def inc(x): return x + 1 def test_answer(): assert inc(3) == 4 ``` #### dynamically adding parameters ##### `simple2.py` ``` code=python import argparse def test_answer(cmdopt): if cmdopt == 'type1': print('first') elif cmdopt == 'type2': print('second') assert 0 ``` ##### `conftest.py` ```code=python import pytest def pytest_addoption(parser): parser.addoption( "--cmdopt", action="store", default="type1", help="my option: type1 or type2" ) def pytest_load_initial_conftests(args): if "xdist" in sys.modules: # pytest-xdist plugin import multiprocessing num = max(multiprocessing.cpu_count() / 2, 1) args[:] = ["-n", str(num)] + args @pytest.fixture def cmdopt(request): return request.config.getoption("--cmdopt") ``` ##### `command line` ```code=bash pytest ``` #### Control skipping of tests according to command line option ##### `test_module.py` ``` code=python import pytest def test_func_fast(): pass @pytest.mark.slow def test_func_slow(): pass ``` ##### `conftest.py` ```code=python import pytest # adding runslow to run pytest.mark.slow def pytest_addoption(parser): parser.addoption( "--runslow", action="store_true", default=False, help="run slow tests" ) def pytest_collection_modifyitems(config, items): if config.getoption("--runslow"): # --runslow given in cli: do not skip slow tests return skip_slow = pytest.mark.skip(reason="need --runslow option to run") for item in items: if "slow" in item.keywords: item.add_marker(skip_slow) ``` #### Writing well integrated assertion helpers (and hide tracestack) ```code=python # content of test_checkconfig.py import pytest def checkconfig(x): __tracebackhide__ = True if not hasattr(x, "config"): pytest.fail("not configured: %s" % (x,)) def test_something(): checkconfig(42) ``` ```code=bash pytest -q test_checkconfig.py ``` #### Writing well integrated assertion helpers (and hide only certain tracestack) ```code=python import pytest import operator class ConfigException(Exception): pass def checkcfg(x): # Just hide certain exception __tracebackhide__ = operator.methodcaller("errisinstance", ConfigException) if not hasattr(x, 'config'): raise ConfigException("not configured: %s" % (x,)) def test_something(): checkcfg(42) ``` ```code=bash pytest -q test_checkconfig.py ``` #### Detect if running from within a pytest run and Adding info to test report header ##### `simple.py` ``` code=python import argparse import sys def test_answer(cmdopt): print("sys._called_from_test: ", sys._called_from_test) if cmdopt == 'type1': print('first') elif cmdopt == 'type2': print('second') assert 0 ``` ##### `conftest.py` ```code=python import pytest import sys def pytest_addoption(parser): parser.addoption( "--cmdopt", action="store", default="type1", help="my option: type1 or type2" ) def pytest_load_initial_conftests(args): if "xdist" in sys.modules: # pytest-xdist plugin import multiprocessing num = max(multiprocessing.cpu_count() / 2, 1) args[:] = ["-n", str(num)] + args def pytest_configure(config): import sys sys._called_from_test = True def pytest_unconfigure(config): import sys del sys._called_from_test def pytest_report_header(config): return "project deps: mylib-1.1" @pytest.fixture def cmdopt(request): return request.config.getoption("--cmdopt") ``` ``` pytest -q simple.py --cmdopt=type1 ``` #### profiling test duration (slowest) ##### `simple.py` ``` code=python # content of test_some_are_slow.py import time def test_funcfast(): time.sleep(0.1) def test_funcslow1(): time.sleep(0.2) def test_funcslow2(): time.sleep(0.3) ``` ``` pytest --durations=3 ``` #### Package/Directory-level fixtures (setups) ##### `a/conftest.py` ``` code=python import pytest class DB(object): pass @pytest.fixture(scope="session") def db(): return DB() ``` ##### `a/test_db1.py` ``` code=python def test_a1(db): assert 0, db # to show value ``` ##### `a/test_db2.py` ``` code=python def test_a2(db): assert 0, db # to show value ``` ##### `b/test_error.py` ``` code=python def test_root(db): # no db here, will error out pass ``` ## Reference * [pytest documentation](https://docs.pytest.org/en/latest/contents.html) * [Talk and Video](https://docs.pytest.org/en/latest/talks.html) * [Testing Flask Applications](http://flask.pocoo.org/docs/1.0/testing/#the-testing-skeleton)
{"metaMigratedAt":"2023-06-14T20:07:30.448Z","metaMigratedFrom":"YAML","title":"pytest","breaks":true,"contributors":"[{\"id\":\"9c79a496-5a74-4ff1-852a-b129de67d2b0\",\"add\":5336,\"del\":602}]"}
    309 views