Skip to content

Affirm#

The expression form of assert, and related helper functions.

Also see assert!.

Usage#

affirm allows asserting a value according to a predicate, returning the value if the assertion is satisfied, or raising an AssertionError with detailed information if not.

Similar to the builtin assert, the affirm function will be a no-op when Python is run with optimizations (the -O flag, or setting __debug__ to False).

Tip

Specifically, the AssertionError message will include the full expression passed to affirm, not just the evaluated value. Different predicates can customize the error message to provide more context.

>>> affirm(operator.mul(2, 3), lambda x: x % 2)
AssertionError: `operator.mul(2, 3)` evals to 6, which does not satisfy `lambda x: x % 2`.
>>> affirm(1 or None, type[bool, str])
AssertionError: `1 or None` evals to 1, which is of type int, expected one of [bool, str].

Some available forms of predicates:

  • Unspecified or None: evaluate the truthiness of the value.
    affirm(1)  # OK, 1
    affirm(0)  # raises AssertionError
    
  • Callable: a function that takes the value and returns a boolean. If a lambda function is used, its source code will be included in the error message.
    affirm(5, lambda x: x > 0)   # OK, 5
    affirm(-3, lambda x: x > 0)  # raises AssertionError
    
  • An AffirmPredicate: a more complex predicate that can customize the failure message.
    affirm(True, type[int])  # OK, True (bool is a subclass of int)
    affirm(True, type[str])  # raises AssertionError
    
  • Boolean: an expression that is directly evaluated to a boolean. Any value that can be converted to boolean is accepted.
    affirm(False, True)    # OK, False
    affirm(True, False)    # raises AssertionError
    

Tip

If you want to assert a value is not None, which is a much more common use case, use the apfel.not_none function instead.

If you do not want an exception to be raised, use apfel.container.Maybe:

just(value).filter(predicate)

AffirmPredicate #

An abstract base class for complex predicates within the affirm function.

__call__(value) #

Test if the value satisfies the predicate. This function enforces returning a boolean value.

Parameters:

Name Type Description Default
value T

The value to be tested.

required

Returns:

Name Type Description
bool bool

Whether the value satisfies the predicate.

fail_message(*, argument_expr, value) abstractmethod #

When the predicate fails, convert inputs to a formattable string explaining the reason.

Parameters:

Name Type Description Default
argument_expr expr | None

The AST expression of the argument passed to affirm, before evaluation. May be None if not available.

required
value T

The actual value being affirmed.

required

Returns:

Name Type Description
str str

A string explaining the reason for failure.

test(value) abstractmethod #

Test if the value satisfies the predicate.

Parameters:

Name Type Description Default
value T

The value to be tested.

required

Returns:

Name Type Description
bool bool

Whether the value satisfies the predicate.

affirm(value, predicate=None) #

affirm(value: Any, predicate: type[is_type[U]]) -> U
affirm(value: Any, predicate: type[type[T]]) -> T
affirm(value: T, predicate: AffirmPredicate[T]) -> T
affirm(value: T, predicate: Callable[[T], bool]) -> T
affirm(value: T, predicate: Callable[[T], Any]) -> T
affirm(value: T) -> T
affirm(value: T, predicate: bool) -> T
affirm(value: T, predicate: Any = None) -> T

Assert the value according to the predicate, return it if it is true. This is the expression form of assert.

See module-level documentation for detailed usage.

Parameters:

Name Type Description Default
value T

The value to be asserted.

required
predicate Callable[[T], bool] | bool | None

The predicate to be used for assertion. If None, evaluate the truthiness of the value.

None

Returns:

Name Type Description
value T

The value asserted.

Raises:

Type Description
AssertionError

If the value is not true.

is_type #

Assert whether the value is exactly the specified type.