Web frameworks
LLM observability for Django
One MIDDLEWARE entry; the authenticated request.user becomes the trace’s user id.
Set up Django
The snippet is copied from the SDK README, not paraphrased. Keys shown as tk_live_... are the environment key from Settings › Environments.
# Django: add to MIDDLEWARE
"evalkit.EvalKitDjangoMiddleware"Copied from sdk-py/README.md § Web frameworks
Install → first trace
- 01
Install the SDK
pip install syntropylabs-evalkit or npm install syntropylabs-evalkit.
- 02
Call init() once
At the top of your entrypoint, with your environment key and a service name.
- 03
Add the middleware to MIDDLEWARE
Each incoming request becomes a root trace with downstream model, database and HTTP calls nested underneath.
- 04
Send one request and open its trace
The request appears in Traces as a root span; Services shows the endpoint.
What a turn looks like
Sample data in the product’s own table. Hover, focus or tap a claim to see the columns it points at.
Sample run
| Operation | Service | Status | Model | Latency | Tokens | ≈Cost | Score |
|---|---|---|---|---|---|---|---|
| support_agent.turn8f3a1c0d94e2session sess_4b1e | support-api | ok | gpt-4o-mini | 1.84 s | 3,412 | $0.0006 | 92%auto |
| refund_agent.turnc21d7e5a30b8session sess_9a02tool loop | refund-worker | ok | claude-sonnet-4 | 4.31 s | 7,905 | $0.0389 | 68%auto |
| claude-code.turn5be04f7d1a96session sess_f77c | Claude Code | unset | claude-sonnet-4 | 48.20 s | 61,208 | $0.19 | |
| rag.answere9a2b6c4d015error | docs-bot | error | gpt-4o | 6.02 s | 9,880 | $0.0312 | 41%auto |
| voice.turn17c8d3f2a4e0session sess_20d1 | ivr-agent | ok | gpt-4o-realtime | 0.92 s | 1,104 | $0.0071 |
fig. 1 · the traces table this integration fills · sample data
What you see
Taken from the SDK READMEs’ coverage tables. with flag means the signal leaves your machine only when you opt in.
| Signal | Captured | Detail |
|---|---|---|
| Each incoming request becomes a root trace | yes | — |
| Model, database and HTTP calls nested under the request | yes | — |
| End-user identity from the request | yes | user_id from request.user when the user is authenticated |
| Sessions and agents | with flag | with evalkit.session("conv_55"): groups a conversation; evalkit.set_agent("support-bot") names the agent |
| Request and response headers | yes | credential header values recorded as *** |
| Your own functions | yes | the public module-level functions of your app’s source tree, on by default; class methods with @evalkit.traced |
Limitations
- List the middleware after AuthenticationMiddleware: user_id is filled only when request.user is known and authenticated; anything you set yourself wins.
- A StreamingHttpResponse is iterated after the middleware ends, so model calls made while streaming are not nested under the request span.
Next steps
Trace Django today
Tracing is free for one project on every plan, coding-agent traces included. Evaluations, datasets and simulation are on paid plans.
More in Web frameworks