Hide keyboard shortcuts

Hot-keys on this page

r m x p   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

1import sys 

2 

3 

4__all__ = ['install', 'NullFinder', 'PyPy_repr', 'Protocol'] 

5 

6 

7try: 

8 from typing import Protocol 

9except ImportError: # pragma: no cover 

10 """ 

11 pytest-mypy complains here because: 

12 error: Incompatible import of "Protocol" (imported name has type 

13 "typing_extensions._SpecialForm", local name has type "typing._SpecialForm") 

14 """ 

15 from typing_extensions import Protocol # type: ignore 

16 

17 

18def install(cls): 

19 """ 

20 Class decorator for installation on sys.meta_path. 

21 

22 Adds the backport DistributionFinder to sys.meta_path and 

23 attempts to disable the finder functionality of the stdlib 

24 DistributionFinder. 

25 """ 

26 sys.meta_path.append(cls()) 

27 disable_stdlib_finder() 

28 return cls 

29 

30 

31def disable_stdlib_finder(): 

32 """ 

33 Give the backport primacy for discovering path-based distributions 

34 by monkey-patching the stdlib O_O. 

35 

36 See #91 for more background for rationale on this sketchy 

37 behavior. 

38 """ 

39 

40 def matches(finder): 

41 return getattr( 

42 finder, '__module__', None 

43 ) == '_frozen_importlib_external' and hasattr(finder, 'find_distributions') 

44 

45 for finder in filter(matches, sys.meta_path): # pragma: nocover 

46 del finder.find_distributions 

47 

48 

49class NullFinder: 

50 """ 

51 A "Finder" (aka "MetaClassFinder") that never finds any modules, 

52 but may find distributions. 

53 """ 

54 

55 @staticmethod 

56 def find_spec(*args, **kwargs): 

57 return None 

58 

59 # In Python 2, the import system requires finders 

60 # to have a find_module() method, but this usage 

61 # is deprecated in Python 3 in favor of find_spec(). 

62 # For the purposes of this finder (i.e. being present 

63 # on sys.meta_path but having no other import 

64 # system functionality), the two methods are identical. 

65 find_module = find_spec 

66 

67 

68class PyPy_repr: 

69 """ 

70 Override repr for EntryPoint objects on PyPy to avoid __iter__ access. 

71 Ref #97, #102. 

72 """ 

73 

74 affected = hasattr(sys, 'pypy_version_info') 

75 

76 def __compat_repr__(self): # pragma: nocover 

77 def make_param(name): 

78 value = getattr(self, name) 

79 return '{name}={value!r}'.format(**locals()) 

80 

81 params = ', '.join(map(make_param, self._fields)) 

82 return 'EntryPoint({params})'.format(**locals()) 

83 

84 if affected: # pragma: nocover 

85 __repr__ = __compat_repr__ 

86 del affected