Source code for validx.py.bools

from .. import exc
from .. import contracts
from . import abstract


[docs]class Bool(abstract.Validator): """ Boolean Validator :param bool nullable: accept ``None`` as a valid value. :param bool coerce_str: * accept values ``["1", "true", "yes", "y", "on"]`` as ``True``; * accept values ``["0", "false", "no", "n", "off"]`` as ``False``. :param bool coerce_int: accept ``int`` as valid value. :raises InvalidTypeError: * if ``value is None`` and ``not self.nullable``; * if ``isinstance(value, str)`` and ``not self.coerce_str``; * if ``isinstance(value, int)`` and ``not self.coerce_int``; * if ``not isinstance(value, bool)``. :raises OptionsError: when string value is not valid name, see ``coerce_str``. """ TRUE = ("1", "true", "yes", "y", "on") FALSE = ("0", "false", "no", "n", "off") __slots__ = ("nullable", "coerce_str", "coerce_int") def __init__( self, nullable=False, coerce_str=False, coerce_int=False, alias=None, replace=False, ): nullable = contracts.expect_flag(self, "nullable", nullable) coerce_str = contracts.expect_flag(self, "coerce_str", coerce_str) coerce_int = contracts.expect_flag(self, "coerce_int", coerce_int) setattr = object.__setattr__ setattr(self, "nullable", nullable) setattr(self, "coerce_str", coerce_str) setattr(self, "coerce_int", coerce_int) self._register(alias, replace) def __call__(self, value, __context=None): if value is None and self.nullable: return value if not isinstance(value, bool): if isinstance(value, str) and self.coerce_str: value = value.lower() if value in self.TRUE: return True if value in self.FALSE: return False raise exc.OptionsError(expected=self.TRUE + self.FALSE, actual=value) elif isinstance(value, int) and self.coerce_int: return bool(value) raise exc.InvalidTypeError(expected=bool, actual=type(value)) return value