Testing in Python
Write automated tests to validate behavior and prevent regressions. Popular tools: unittest (stdlib) and pytest.
Project structure
Keep tests close to code or in a top-level tests/ package.
src/
app/
core.py
tests/
test_core.py
unittest (stdlib)
unittest provides xUnit-style test cases and assertions.
import unittest
from app.core import add
class TestCore(unittest.TestCase):
def test_add(self):
self.assertEqual(add(2, 3), 5)
if __name__ == "__main__":
unittest.main()
Run with python -m unittest -v.
pytest (concise)
pytest discovers tests by naming conventions and simplifies assertions.
# tests/test_core.py
from app.core import add
def test_add():
assert add(2, 3) == 5
Run with pytest -q.
Fixtures
Fixtures set up reusable state.
import pytest
@pytest.fixture
def tmp_user():
return {"name": "Ada"}
def test_user(tmp_user):
assert tmp_user["name"] == "Ada"
Parametrization
Test many inputs succinctly.
import pytest
@pytest.mark.parametrize("a,b,sum_", [(1,2,3), (0,0,0), (-1,1,0)])
def test_add(a, b, sum_):
assert a + b == sum_
Mocking
Isolate units with doubles.
from unittest.mock import patch
with patch("app.core.now", return_value=0):
...
Coverage
Measure coverage with coverage.py.
coverage run -m pytest
coverage html
Best practices
- Test behavior, not implementation details
- Keep tests independent and deterministic
- Use fixtures/factories to reduce duplication
- Run tests in CI; enforce coverage thresholds sensibly
Summary
unittestandpytestare the main tools- Use fixtures, parametrization, and mocking to write clear, robust tests