@@ -42,8 +42,11 @@ def is_api_request(request: web.Request, api_version: str) -> bool:
4242 return bool (request .path .startswith (base_path ))
4343
4444
45- def _handle_unexpected_error (
46- request : web .BaseRequest , exception : Exception , * , skip_internal_error_details : bool
45+ def _handle_unexpected_exception_as_500 (
46+ request : web .BaseRequest ,
47+ exception : Exception ,
48+ * ,
49+ skip_internal_error_details : bool ,
4750) -> web .HTTPInternalServerError :
4851 """Process unexpected exceptions and return them as HTTP errors with proper formatting."""
4952 error_code = create_error_code (exception )
@@ -102,97 +105,97 @@ def _handle_http_error(
102105def _handle_http_successful (
103106 request : web .Request ,
104107 exception : web .HTTPSuccessful ,
105- * ,
106- skip_internal_error_details : bool ,
107108) -> web .HTTPSuccessful :
108109 """Handle successful HTTP responses, ensuring they're properly enveloped."""
110+ assert request # nosec
111+
109112 exception .content_type = MIMETYPE_APPLICATION_JSON
110113 if exception .reason :
111114 exception .set_status (
112115 exception .status , safe_status_message (message = exception .reason )
113116 )
114117
115118 if exception .text :
116- try :
117- payload = json_loads (exception .text )
118- if not is_enveloped_from_map (payload ):
119- payload = wrap_as_envelope (data = payload )
120- exception .text = json_dumps (payload )
121- except Exception as other_error : # pylint: disable=broad-except
122- return _handle_unexpected_error (
123- request ,
124- other_error ,
125- skip_internal_error_details = skip_internal_error_details ,
126- )
119+ payload = json_loads (exception .text )
120+ if not is_enveloped_from_map (payload ):
121+ payload = wrap_as_envelope (data = payload )
122+ exception .text = json_dumps (payload )
127123
128124 return exception
129125
130126
131- def _handle_not_implemented (
127+ def _handle_not_implemented_error (
132128 request : web .Request ,
133129 exception : NotImplementedError ,
134130 * ,
135131 skip_internal_error_details : bool ,
136132) -> web .HTTPNotImplemented :
137133 """Handle NotImplementedError by converting to appropriate HTTP error."""
138- http_error = create_http_error (
134+ assert request # nosec
135+
136+ return create_http_error (
139137 exception ,
140138 f"{ exception } " ,
141139 web .HTTPNotImplemented ,
142140 skip_internal_error_details = skip_internal_error_details ,
143141 )
144- return http_error
145142
146143
147- def _handle_timeout (
148- request : web .Request , exception : TimeoutError , * , skip_internal_error_details : bool
144+ def _handle_timeout_error (
145+ request : web .Request ,
146+ exception : TimeoutError ,
147+ * ,
148+ skip_internal_error_details : bool ,
149149) -> web .HTTPGatewayTimeout :
150150 """Handle TimeoutError by converting to appropriate HTTP error."""
151- http_error = create_http_error (
151+ assert request # nosec
152+ return create_http_error (
152153 exception ,
153154 f"{ exception } " ,
154155 web .HTTPGatewayTimeout ,
155156 skip_internal_error_details = skip_internal_error_details ,
156157 )
157- return http_error
158158
159159
160- def error_middleware_factory ( # noqa: C901
161- api_version : str ,
162- ) -> Middleware :
160+ def error_middleware_factory (api_version : str ) -> Middleware :
163161 _is_prod : bool = is_production_environ ()
164162
165163 @web .middleware
166- async def _middleware_handler (request : web .Request , handler : Handler ): # noqa: C901
164+ async def _middleware_handler (request : web .Request , handler : Handler ):
167165 """
168166 Ensure all error raised are properly enveloped and json responses
169167 """
170168 if not is_api_request (request , api_version ):
171169 return await handler (request )
172170
173- # FIXME: review when to send info to client and when not!
174171 try :
175- result = await handler (request )
176- except web .HTTPError as exc :
177- result = _handle_http_error (request , exc )
178- except web .HTTPSuccessful as exc :
179- result = _handle_http_successful (
180- request , exc , skip_internal_error_details = _is_prod
181- )
182- except web .HTTPRedirection as exc :
183- _logger .debug ("Redirected to %s" , exc )
184- raise # We still raise redirection exceptions directly
172+ try :
173+ result = await handler (request )
185174
186- except NotImplementedError as exc :
187- result = _handle_not_implemented (
188- request , exc , skip_internal_error_details = _is_prod
189- )
175+ except web .HTTPError as exc : # 4XX and 5XX raised as exceptions
176+ result = _handle_http_error (request , exc )
177+
178+ except web .HTTPSuccessful as exc : # 2XX rased as exceptions
179+ result = _handle_http_successful (request , exc )
180+
181+ except web .HTTPRedirection as exc : # 3XX raised as exceptions
182+ _logger .debug ("Redirected to %s" , exc )
183+ result = exc
190184
191- except TimeoutError as exc :
192- result = _handle_timeout (request , exc , skip_internal_error_details = _is_prod )
185+ except NotImplementedError as exc :
186+ result = _handle_not_implemented_error (
187+ request , exc , skip_internal_error_details = _is_prod
188+ )
189+ except TimeoutError as exc :
190+ result = _handle_timeout_error (
191+ request , exc , skip_internal_error_details = _is_prod
192+ )
193193
194194 except Exception as exc : # pylint: disable=broad-except
195- result = _handle_unexpected_error (
195+ #
196+ # Last resort for unexpected exceptions (including those in handlers!)
197+ #
198+ result = _handle_unexpected_exception_as_500 (
196199 request , exc , skip_internal_error_details = _is_prod
197200 )
198201
0 commit comments