self.assertIsSubclass(B, Custom)
self.assertNotIsSubclass(A, Custom)
+ def test_builtin_protocol_whitelist(self):
+ with self.assertRaises(TypeError):
+ class CustomProtocol(TestCase, Protocol):
+ pass
+
+ class CustomContextManager(typing.ContextManager, Protocol):
+ pass
+
class GenericTests(BaseTestCase):
def test_basics(self):
return True
-_PROTO_WHITELIST = ['Callable', 'Awaitable',
- 'Iterable', 'Iterator', 'AsyncIterable', 'AsyncIterator',
- 'Hashable', 'Sized', 'Container', 'Collection', 'Reversible',
- 'ContextManager', 'AsyncContextManager']
+_PROTO_WHITELIST = {
+ 'collections.abc': [
+ 'Callable', 'Awaitable', 'Iterable', 'Iterator', 'AsyncIterable',
+ 'Hashable', 'Sized', 'Container', 'Collection', 'Reversible',
+ ],
+ 'contextlib': ['AbstractContextManager', 'AbstractAsyncContextManager'],
+}
class _ProtocolMeta(ABCMeta):
# ... otherwise check consistency of bases, and prohibit instantiation.
for base in cls.__bases__:
if not (base in (object, Generic) or
- base.__module__ == 'collections.abc' and base.__name__ in _PROTO_WHITELIST or
+ base.__module__ in _PROTO_WHITELIST and
+ base.__name__ in _PROTO_WHITELIST[base.__module__] or
issubclass(base, Generic) and base._is_protocol):
raise TypeError('Protocols can only inherit from other'
' protocols, got %r' % base)