What you’ll build
An authenticated chat where every Supabase user has filterable Polpo sessions and analytics. Your Next.js app verifies the Supabase session on the server, then forwards the user’s ID to Polpo on every chat call. You get:- Per-user session history and filtering
- Per-user analytics (filter dashboard by
user) - Audit trail (every session, task, run carries the user id)
- A stable external identifier for downstream metering
Prerequisites
1
Supabase project with auth enabled
Email/password, OAuth, magic links — any Supabase auth method works. You only need the server-side helper to read the current user.
2
Polpo project + API key
Follow the quickstart to create a project and grab a service-role API key (
sk_live_...). Server-side only — never ship it to the browser.3
Next.js 14+ App Router
Examples below use Route Handlers and Client Components. The same pattern works in Hono, Express, or any server you control.
How it fits together
user field.
Step 1 — Install
Step 2 — Verify the session and call Polpo
Server-side route handler. Reads the Supabase session via cookies, rejects unauthenticated requests, and streams the chat completion back to the browser withuser: user.id attached.
app/api/chat/route.ts
Step 3 — Stream the response in your client
Plainfetch + the standard SSE parsing pattern. Replace this with @polpo-ai/react’s useChat hook once you wire PolpoProvider against /api/chat.
app/chat/page.tsx
Step 4 (optional) — List a user’s past sessions
Polpo auto-creates a session per chat and tags it with theuser field. You can list a single user’s sessions from your server.
The typed
polpo.getSessions() helper doesn’t currently take a user filter parameter. Until it does, hit the underlying endpoint directly — GET /v1/chat/sessions?user=<id> does support the filter server-side. We’ll add a typed param to the SDK in a later release.app/api/sessions/route.ts
What this gives you
- Per-user session history. Sessions can be filtered by the exact
user.idvalue. - Per-user analytics. Filter completions, tasks, and runs by
userin the dashboard. - Audit trail. Every session, task, and run row stores the user id — useful for support, abuse review, and compliance.
- Metering identifier. The same
uservalue can be correlated with your own billing and usage records.
What we deliberately don’t do
- Polpo never verifies the Supabase JWT. Your API key is the trust anchor. Verify the session in your server, then forward
user.id— Polpo trusts the caller because the caller has the API key. - We don’t compete with Supabase Auth. Bring your auth — we run the agents.
Troubleshooting
401 Unauthorized from Polpo
Check POLPO_API_KEY is set in the server environment and not prefixed with NEXT_PUBLIC_. The SDK sends it as Authorization: Bearer <key>.
user field shows up as null in the dashboard
The user field must be passed in the request body, not as a header. With the SDK, that’s polpo.chatCompletionsStream({ ..., user: user.id }). With raw fetch, include "user": "<id>" as a top-level body field.
Sessions aren’t being scoped per user
Confirm both@polpo-ai/sdk and the target runtime are on 0.15.35. Run pnpm why @polpo-ai/sdk to verify.
Shared and per-agent memory endpoints remain project-scoped; the user field does not isolate /v1/memory content. Keep authorization and tenant isolation in your application server.