1
1
import structlog
2
2
import time
3
- from fastapi import Request , Response
3
+ from fastapi import Request , Response , status
4
4
from uvicorn .protocols .utils import get_path_with_query_string
5
5
6
+ from .common import LogHTTPInfo , LogNetworkInfo , LogNetworkClientInfo , log_access
7
+
6
8
__all__ = [
7
9
"build_structlog_fastapi_middleware" ,
8
10
]
@@ -24,40 +26,27 @@ async def access_log_middleware(request: Request, call_next) -> Response:
24
26
start_time = time .perf_counter_ns ()
25
27
26
28
# To return if an exception occurs while calling the next in the middleware chain
27
- response : Response = Response (status_code = 500 )
29
+ response : Response = Response (status_code = status . HTTP_500_INTERNAL_SERVER_ERROR )
28
30
29
31
try :
30
32
response = await call_next (request )
31
33
except Exception as e : # pragma: no cover
32
34
await service_logger .aexception ("uncaught exception" , exc_info = e )
33
35
finally :
34
36
# When the response has finished or errored out, write the access log message:
35
-
36
- duration = time .perf_counter_ns () - start_time
37
-
38
- status_code = response .status_code
39
37
# noinspection PyTypeChecker
40
- url = get_path_with_query_string (request .scope )
41
- client_host = request .client .host
42
- client_port = request .client .port
43
- http_method = request .method
44
- http_version = request .scope ["http_version" ]
45
-
46
- await access_logger .ainfo (
47
- # The message format mirrors the original uvicorn access message, which we aim to replace here with
48
- # something more structured.
49
- f'{ client_host } :{ client_port } - "{ http_method } { url } HTTP/{ http_version } " { status_code } ' ,
50
- # HTTP information, extracted from the request and response objects:
51
- http = {
52
- "url" : url ,
53
- "status_code" : status_code ,
54
- "method" : http_method ,
55
- "version" : http_version ,
56
- },
57
- # Network information, extracted from the request object:
58
- network = {"client" : {"host" : client_host , "port" : client_port }},
59
- # Duration in nanoseconds, computed in-middleware:
60
- duration = duration ,
38
+ await log_access (
39
+ access_logger ,
40
+ start_time ,
41
+ http_info = LogHTTPInfo (
42
+ url = get_path_with_query_string (request .scope ),
43
+ status_code = response .status_code ,
44
+ method = request .method ,
45
+ version = request .scope ["http_version" ],
46
+ ),
47
+ network_info = LogNetworkInfo (
48
+ client = LogNetworkClientInfo (host = request .client .host , port = request .client .port )
49
+ ),
61
50
)
62
51
63
52
return response
0 commit comments