Fading Coder

One Final Commit for the Last Sprint

Home > Tech > Content

Resolving Uvicorn Worker Access Log Formatting Issues in FastAPI

Tech 1

Deploying a FastAPI application using Gunicorn with Uvicorn workers typically involves a command such as:

gunicorn app_core:web_app --workers 2 --worker-class uvicorn.workers.UvicornWorker --bind 127.0.0.1:8000 --access-logfile '-'

By default, the generated access logs lack timestamps, outputting only basic request details:

176.123.7.11:0 - "GET / HTTP/1.0" 200

Attempting to append request times using Gunicorn's native --access-logformat argument or a gunicorn.conf.py configuration file has no effect. This happens because the Uvicorn worker class overrides Gunicorn's access log formatting mechanisms, rendering standard Gunicorn logging configurations ineffective.

A previously suggested workaround required patching the Gunicorn source code (glogging.py), but a cleaner approach exists by configuring the uvicorn.access logger directly within FastAPI.

First, remove the --access-logfile '-' parameter from the Gunicorn startup command. Then, inject a custom logging handler during the FastAPI application lifespan setup.

import logging
from contextlib import asynccontextmanager
from fastapi import FastAPI

CUSTOM_LOG_PATTERN = "%(asctime)s - %(levelname)s - %(message)s"

def setup_custom_access_logger():
    access_logger = logging.getLogger("uvicorn.access")
    console_handler = logging.StreamHandler()
    console_handler.setFormatter(logging.Formatter(CUSTOM_LOG_PATTERN))
    access_logger.addHandler(console_handler)

@asynccontextmanager
async def application_startup(web_application):
    setup_custom_access_logger()
    yield

web_app = FastAPI(lifespan=application_startup)

After applying this configuration, the access logs will correctly output timestamps alongside the request details:

2024-02-25 16:02:48,435 - INFO - 127.0.0.1:52872 - "GET /docs HTTP/1.1" 418
2024-02-25 16:09:56,785 - INFO - 127.0.0.1:46822 - "POST /close_pid?pid=-1 HTTP/1.1" 200

Note: This lifespan approach requires FastAPI version 0.100 or later.

Related Articles

Understanding Strong and Weak References in Java

Strong References Strong reference are the most prevalent type of object referencing in Java. When an object has a strong reference pointing to it, the garbage collector will not reclaim its memory. F...

Comprehensive Guide to SSTI Explained with Payload Bypass Techniques

Introduction Server-Side Template Injection (SSTI) is a vulnerability in web applications where user input is improper handled within the template engine and executed on the server. This exploit can r...

Implement Image Upload Functionality for Django Integrated TinyMCE Editor

Django’s Admin panel is highly user-friendly, and pairing it with TinyMCE, an effective rich text editor, simplifies content management significantly. Combining the two is particular useful for bloggi...

Leave a Comment

Anonymous

◎Feel free to join the discussion and share your thoughts.