def is_special_target(right: ProperType) -> bool: """Whitelist some special cases for use in isinstance() with improper types.""" if isinstance(right, CallableType) and right.is_type_obj(): if right.type_object().fullname() == 'builtins.tuple': # Used with Union[Type, Tuple[Type, ...]]. return True if right.type_object().fullname() in ('mypy.types.Type', 'mypy.types.ProperType', 'mypy.types.TypeAliasType'): # Special case: things like assert isinstance(typ, ProperType) are always OK. return True if right.type_object().fullname() in ('mypy.types.UnboundType', 'mypy.types.TypeVarType', 'mypy.types.RawExpressionType', 'mypy.types.EllipsisType', 'mypy.types.StarType', 'mypy.types.TypeList', 'mypy.types.CallableArgument', 'mypy.types.PartialType', 'mypy.types.ErasedType'): # Special case: these are not valid targets for a type alias and thus safe. # TODO: introduce a SyntheticType base to simplify this? return True elif isinstance(right, TupleType): return all(is_special_target(t) for t in get_proper_types(right.items)) return False
def is_dangerous_target(typ: ProperType) -> bool: """Is this a dangerous target (right argument) for an isinstance() check?""" if isinstance(typ, TupleType): return any(is_dangerous_target(get_proper_type(t)) for t in typ.items) if isinstance(typ, CallableType) and typ.is_type_obj(): return typ.type_object().has_base('mypy.types.Type') return False