assert

Added in v3.0 · Updated March 15, 2026 · Keywords
keyword debugging error testing

The assert statement is a debugging aid in Python. It tests a condition, and if the condition is false, it raises an AssertionError. Assert statements are meant to catch programmer errors, not handle runtime errors.

Syntax

assert condition
assert condition, "optional error message"

How It Works

When Python encounters an assert statement, it evaluates the condition:

  1. If the condition is truthy, nothing happens — execution continues
  2. If the condition is falsy, an AssertionError is raised
  3. If a message is provided, it’s included in the exception
# Basic assert
x = 5
assert x > 0
# No output - assertion passed

# This will fail
y = -1
assert y > 0
# Traceback (most recent call last):
#   File "<stdin>", line 1, in <module>
# AssertionError

# With error message
z = 0
assert z != 0, "z must not be zero"
# Traceback (most recent call last):
#   File "<stdin>", line 1, in <module>
# AssertionError: z must not be zero

Common Use Cases

Debugging during development

def divide(a, b):
    # This catches impossible states during development
    assert b != 0, "Cannot divide by zero"
    return a / b

# During development, this helps catch bugs
result = divide(10, 0)
# AssertionError: Cannot divide by zero

Validating function inputs

def factorial(n):
    assert n >= 0, "Factorial undefined for negative numbers"
    assert isinstance(n, int), "n must be an integer"
    
    if n <= 1:
        return 1
    return n * factorial(n - 1)

print(factorial(5))
# 120

print(factorial(-1))
# AssertionError: Factorial undefined for negative numbers

Checking intermediate results

def process_data(data):
    # Validate data structure
    assert isinstance(data, list), "Data must be a list"
    assert len(data) > 0, "Data cannot be empty"
    
    # Process each item
    results = []
    for item in data:
        # Check intermediate state
        assert item >= 0, f"Negative value found: {item}"
        results.append(item * 2)
    
    return results

print(process_data([1, 2, 3]))
# [2, 4, 6]

print(process_data([-1, 2]))
# AssertionError: Negative value found: -1

Documenting invariants

class BankAccount:
    def __init__(self, balance):
        assert balance >= 0, "Initial balance cannot be negative"
        self._balance = balance
    
    def withdraw(self, amount):
        assert amount > 0, "Withdrawal amount must be positive"
        assert amount <= self._balance, "Insufficient funds"
        self._balance -= amount
        return self._balance
    
    def deposit(self, amount):
        assert amount > 0, "Deposit amount must be positive"
        self._balance += amount
        return self._balance

Assertions vs Exceptions

Use assert for programmer errors, raise for runtime errors:

# WRONG: Using assert for user input validation
def parse_age(input_str):
    age = int(input_str)  # This can still raise ValueError
    assert age >= 0  # Wrong - users can provide bad input
    return age

# RIGHT: Use proper exceptions for user input
def parse_age(input_str):
    try:
        age = int(input_str)
    except ValueError:
        raise ValueError(f"Invalid age: {input_str}")
    
    if age < 0:
        raise ValueError(f"Age cannot be negative: {age}")
    return age

Disabling Assertions

In production, Python runs with optimizations (-O flag), which disables all assert statements:

# Running with python -O disables all asserts
python -O script.py

This is useful for:

  • Production deployments (assertions slow down code slightly)
  • Testing that your code handles errors without assertion checks
# test_production.py
def validate_config(config):
    assert "database" in config, "Missing database config"
    # More assertions...

# Run normally - assertions active
python test_production.py  # AssertionError if config invalid

# Run with optimization - assertions disabled
python -O test_production.py  # No assertion checks

Assert with Complex Conditions

# Checking multiple conditions
def calculate_average(numbers):
    assert numbers, "List cannot be empty"
    assert all(isinstance(n, (int, float)) for n in numbers), "All values must be numeric"
    
    return sum(numbers) / len(numbers)

# Checking state after operation
def sort_list(items):
    result = sorted(items)
    assert result == items, "Original list was modified!"  # Fails if sorted() modified in-place
    return result

See Also