python 53 lines · 9 steps

Custom gzip middleware in FastAPI

A middleware that compresses responses with gzip only when the client accepts it and the body is large enough.

Explained by highlit
1import gzip
2from fastapi import FastAPI, Request, Response
3from starlette.middleware.base import BaseHTTPMiddleware
4from starlette.types import ASGIApp
5 
6 
7class ConditionalGZipMiddleware(BaseHTTPMiddleware):
8 def __init__(
9 self,
10 app: ASGIApp,
11 minimum_size: int = 1024,
12 compress_level: int = 6,
13 ) -> None:
14 super().__init__(app)
15 self.minimum_size = minimum_size
16 self.compress_level = compress_level
17 
18 async def dispatch(self, request: Request, call_next) -> Response:
19 response = await call_next(request)
20 
21 accepted = request.headers.get("accept-encoding", "")
22 if "gzip" not in accepted.lower():
23 return response
24 
25 if response.headers.get("content-encoding"):
26 return response
27 
28 body = b"".join([chunk async for chunk in response.body_iterator])
29 
30 if len(body) < self.minimum_size:
31 return Response(
32 content=body,
33 status_code=response.status_code,
34 headers=dict(response.headers),
35 media_type=response.media_type,
36 )
37 
38 compressed = gzip.compress(body, compresslevel=self.compress_level)
39 headers = dict(response.headers)
40 headers["content-encoding"] = "gzip"
41 headers["content-length"] = str(len(compressed))
42 headers["vary"] = "Accept-Encoding"
43 
44 return Response(
45 content=compressed,
46 status_code=response.status_code,
47 headers=headers,
48 media_type=response.media_type,
49 )
50 
51 
52app = FastAPI()
53app.add_middleware(ConditionalGZipMiddleware, minimum_size=2048)
01 / 01
STEP 01

Walkthrough

Space play step click any line
Three takeaways
  1. 1Subclassing BaseHTTPMiddleware lets you inspect and rewrite responses around the whole request cycle.
  2. 2Content negotiation means honoring the client's Accept-Encoding before applying any transformation.
  3. 3Compressing tiny payloads wastes CPU, so a minimum-size threshold keeps the optimization worthwhile.

Related explainers

Share this explainer

Here's the card — post it anywhere.

Custom gzip middleware in FastAPI — share card
Made with highlit — turn any snippet into a walkthrough like this in about a minute.
Explain your code