tiangolo/fastapi · error · HTTPException

Item not found

Error message

Item not found

What it means

Same HTTP 404 "Item not found" as error 34 but with an additional custom response header `X-Error: There goes my error` attached via HTTPException(headers=...). FastAPI's default handler forwards those headers onto the response, letting clients/middleware read error metadata out-of-band. The 404 fires when item_id is not in `items`.

Source

Thrown at docs_src/handling_errors/tutorial002_py310.py:11

from fastapi import FastAPI, HTTPException

app = FastAPI()

items = {"foo": "The Foo Wrestlers"}


@app.get("/items-header/{item_id}")
async def read_item_header(item_id: str):
    if item_id not in items:
        raise HTTPException(
            status_code=404,
            detail="Item not found",
            headers={"X-Error": "There goes my error"},
        )
    return {"item": items[item_id]}

View on GitHub (pinned to 42a41db11f)

Solutions

  1. Request /items-header/foo to avoid the 404.
  2. If you maintain the API, keep the header contract stable and document it.
  3. Whitelist X-Error in CORS exposed headers so browsers can read it.
  4. Test that the header is present on the 404 response.

Example fix

# before
raise HTTPException(
    status_code=404,
    detail="Item not found",
    headers={"X-Error": "There goes my error"},
)

# after (centralized helper)
def not_found(extra_headers=None):
    raise HTTPException(status_code=404, detail="Item not found", headers=extra_headers or {})
not_found({"X-Error": "missing"})
Defensive patterns

Strategy: try-catch

Validate before calling

if item_id not in {"foo"}:
    # skip the call; expected 404 carries X-Error header
    raise KeyError(item_id)

Type guard

def is_known(item_id: str) -> bool:
    return item_id in {"foo"}

Try / catch

r = client.get(f"/items-header/{item_id}")
if r.status_code == 404:
    xerr = r.headers.get("X-Error")
    # branch on X-Error value if present
    ...

Prevention

When it happens

Trigger: GET /items-header/<anything-except-foo>; the response carries status 404, body {"detail":"Item not found"}, and header X-Error.

Common situations: Clients that rely on the X-Error header for branching; CORS/proxies that strip custom headers; forgetting to include headers when raising from other paths.

Related errors


AI-assisted analysis of tiangolo/fastapi@42a41db11f (2026-08-04). Data as JSON: /data/errors/eaed84acd326fa03.json. Report an issue: GitHub.