We shouldn't rely on assertions for logic-critical things; they can be stripped in optimized settings.
Instead, we should use branching with dedicated Exception classes.
Related: https://discuss.python.org/t/stop-ignoring-asserts-when-running-in-optimized-mode/13132