Test observable behavior
A test should describe what a caller receives for a given input. Avoid asserting local variables or the exact sequence of private helper calls.
Cover boundaries
Zero, empty, maximum, duplicate, malformed, and unavailable inputs reveal more than ten ordinary examples.
Use realistic fixtures
A tiny input that resembles production data is better than a complicated mock that does not match reality.
Keep failures readable
One behavior per test makes the failure name useful. The test suite is part of the product documentation.
Working example
import pytest
def platform_fee(amount_cents: int) -> int:
if amount_cents < 0:
raise ValueError("amount cannot be negative")
return round(amount_cents * 0.029) + 30 if amount_cents else 0
def test_zero_purchase_has_no_fee():
assert platform_fee(0) == 0
def test_fee_uses_percentage_and_fixed_component():
assert platform_fee(10_000) == 320
def test_negative_amount_is_rejected():
with pytest.raises(ValueError, match="cannot be negative"):
platform_fee(-1)