Coverage for /var/srv/projects/api.amasfac.comuna18.com/tmp/venv/lib/python3.9/site-packages/corsheaders/checks.py: 61%

56 statements  

« prev     ^ index     » next       coverage.py v6.4.4, created at 2023-07-17 14:22 -0600

1from __future__ import annotations 

2 

3import re 

4from collections.abc import Sequence 

5from typing import Any 

6from urllib.parse import urlparse 

7 

8from django.apps import AppConfig 

9from django.conf import settings 

10from django.core.checks import Error 

11 

12from corsheaders.conf import conf 

13 

14re_type = type(re.compile("")) 

15 

16 

17def check_settings(app_configs: list[AppConfig], **kwargs: Any) -> list[Error]: 

18 errors = [] 

19 

20 if not is_sequence(conf.CORS_ALLOW_HEADERS, str): 20 ↛ 21line 20 didn't jump to line 21, because the condition on line 20 was never true

21 errors.append( 

22 Error( 

23 "CORS_ALLOW_HEADERS should be a sequence of strings.", 

24 id="corsheaders.E001", 

25 ) 

26 ) 

27 

28 if not is_sequence(conf.CORS_ALLOW_METHODS, str): 28 ↛ 29line 28 didn't jump to line 29, because the condition on line 28 was never true

29 errors.append( 

30 Error( 

31 "CORS_ALLOW_METHODS should be a sequence of strings.", 

32 id="corsheaders.E002", 

33 ) 

34 ) 

35 

36 if not isinstance(conf.CORS_ALLOW_CREDENTIALS, bool): 36 ↛ 37line 36 didn't jump to line 37, because the condition on line 36 was never true

37 errors.append( # type: ignore [unreachable] 

38 Error("CORS_ALLOW_CREDENTIALS should be a bool.", id="corsheaders.E003") 

39 ) 

40 

41 if ( 41 ↛ 45line 41 didn't jump to line 45

42 not isinstance(conf.CORS_PREFLIGHT_MAX_AGE, int) 

43 or conf.CORS_PREFLIGHT_MAX_AGE < 0 

44 ): 

45 errors.append( 

46 Error( 

47 ( 

48 "CORS_PREFLIGHT_MAX_AGE should be an integer greater than " 

49 + "or equal to zero." 

50 ), 

51 id="corsheaders.E004", 

52 ) 

53 ) 

54 

55 if not isinstance(conf.CORS_ALLOW_ALL_ORIGINS, bool): 55 ↛ 56line 55 didn't jump to line 56, because the condition on line 55 was never true

56 if hasattr(settings, "CORS_ALLOW_ALL_ORIGINS"): # type: ignore [unreachable] 

57 allow_all_alias = "CORS_ALLOW_ALL_ORIGINS" 

58 else: 

59 allow_all_alias = "CORS_ORIGIN_ALLOW_ALL" 

60 errors.append( 

61 Error( 

62 f"{allow_all_alias} should be a bool.", 

63 id="corsheaders.E005", 

64 ) 

65 ) 

66 

67 if hasattr(settings, "CORS_ALLOWED_ORIGINS"): 67 ↛ 70line 67 didn't jump to line 70, because the condition on line 67 was never false

68 allowed_origins_alias = "CORS_ALLOWED_ORIGINS" 

69 else: 

70 allowed_origins_alias = "CORS_ORIGIN_WHITELIST" 

71 

72 if not is_sequence(conf.CORS_ALLOWED_ORIGINS, str): 72 ↛ 73line 72 didn't jump to line 73, because the condition on line 72 was never true

73 errors.append( 

74 Error( 

75 f"{allowed_origins_alias} should be a sequence of strings.", 

76 id="corsheaders.E006", 

77 ) 

78 ) 

79 else: 

80 special_origin_values = ( 

81 # From 'security sensitive' contexts 

82 "null", 

83 # From files on Chrome on Android 

84 # https://bugs.chromium.org/p/chromium/issues/detail?id=991107 

85 "file://", 

86 ) 

87 for origin in conf.CORS_ALLOWED_ORIGINS: 

88 if origin in special_origin_values: 88 ↛ 89line 88 didn't jump to line 89, because the condition on line 88 was never true

89 continue 

90 parsed = urlparse(origin) 

91 if parsed.scheme == "" or parsed.netloc == "": 91 ↛ 92line 91 didn't jump to line 92, because the condition on line 91 was never true

92 errors.append( 

93 Error( 

94 "Origin {} in {} is missing scheme or netloc".format( 

95 repr(origin), allowed_origins_alias 

96 ), 

97 id="corsheaders.E013", 

98 hint=( 

99 "Add a scheme (e.g. https://) or netloc (e.g. " 

100 + "example.com)." 

101 ), 

102 ) 

103 ) 

104 else: 

105 # Only do this check in this case because if the scheme is not 

106 # provided, netloc ends up in path 

107 for part in ("path", "params", "query", "fragment"): 

108 if getattr(parsed, part) != "": 108 ↛ 109line 108 didn't jump to line 109, because the condition on line 108 was never true

109 errors.append( 

110 Error( 

111 "Origin {} in {} should not have {}".format( 

112 repr(origin), allowed_origins_alias, part 

113 ), 

114 id="corsheaders.E014", 

115 ) 

116 ) 

117 

118 if hasattr(settings, "CORS_ALLOWED_ORIGIN_REGEXES"): 118 ↛ 119line 118 didn't jump to line 119, because the condition on line 118 was never true

119 allowed_regexes_alias = "CORS_ALLOWED_ORIGIN_REGEXES" 

120 else: 

121 allowed_regexes_alias = "CORS_ORIGIN_REGEX_WHITELIST" 

122 if not is_sequence(conf.CORS_ALLOWED_ORIGIN_REGEXES, (str, re_type)): 122 ↛ 123line 122 didn't jump to line 123, because the condition on line 122 was never true

123 errors.append( 

124 Error( 

125 "{} should be a sequence of strings and/or compiled regexes.".format( 

126 allowed_regexes_alias 

127 ), 

128 id="corsheaders.E007", 

129 ) 

130 ) 

131 

132 if not is_sequence(conf.CORS_EXPOSE_HEADERS, str): 132 ↛ 133line 132 didn't jump to line 133, because the condition on line 132 was never true

133 errors.append( 

134 Error("CORS_EXPOSE_HEADERS should be a sequence.", id="corsheaders.E008") 

135 ) 

136 

137 if not isinstance(conf.CORS_URLS_REGEX, (str, re_type)): 137 ↛ 138line 137 didn't jump to line 138, because the condition on line 137 was never true

138 errors.append( 

139 Error("CORS_URLS_REGEX should be a string or regex.", id="corsheaders.E009") 

140 ) 

141 

142 if not isinstance(conf.CORS_REPLACE_HTTPS_REFERER, bool): 142 ↛ 143line 142 didn't jump to line 143, because the condition on line 142 was never true

143 errors.append( # type: ignore [unreachable] 

144 Error("CORS_REPLACE_HTTPS_REFERER should be a bool.", id="corsheaders.E011") 

145 ) 

146 

147 if hasattr(settings, "CORS_MODEL"): 147 ↛ 148line 147 didn't jump to line 148, because the condition on line 147 was never true

148 errors.append( 

149 Error( 

150 ( 

151 "The CORS_MODEL setting has been removed - see " 

152 + "django-cors-headers' HISTORY." 

153 ), 

154 id="corsheaders.E012", 

155 ) 

156 ) 

157 

158 return errors 

159 

160 

161def is_sequence(thing: Any, type_or_types: type[Any] | tuple[type[Any], ...]) -> bool: 

162 return isinstance(thing, Sequence) and all( 

163 isinstance(x, type_or_types) for x in thing 

164 )