Notifications, Stats & Analytics
Three smaller surfaces round out the platform-api.
Notifications
Per-user notifications. Both routes are guarded and scoped to the token’s user.
| Action | Method & path |
|---|---|
| List my notifications | GET /api/notifications |
| Mark one as read | PATCH /api/notifications/:id/read |
curl http://localhost:3111/api/notifications \
-H "Authorization: Bearer $PAT"Stats
Aggregate usage metrics and access logs. Guarded routes.
| Action | Method & path | Query params |
|---|---|---|
| Time-series stats | GET /api/stats | startDate, endDate, interval (default daily) |
| Advanced stats | GET /api/stats/advanced | startDate, endDate |
| Access logs | GET /api/stats/logs | page (default 1), limit (default 20) |
curl "http://localhost:3111/api/stats?startDate=2026-06-01&endDate=2026-06-19&interval=daily" \
-H "Authorization: Bearer $PAT"interval accepts the bucketing granularity (e.g. daily). startDate / endDate are ISO date strings.
Analytics ingest
A public (no-auth) ingest endpoint for client-side events, tightly throttled.
POST /api/analytics/events — public, throttled 120/min
{ "name": "resume_exported", "properties": { "format": "pdf" } }Returns { "accepted": true } (inside the envelope). The server enriches each event with request metadata (IP, user agent) before storing it.
Because this route is @Public(), don’t send a token to it and don’t put anything sensitive in properties — treat it like any browser-facing analytics beacon.
Webhooks (not for direct calls)
/api/webhooks/* receives Svix-signed events (e.g. Clerk user lifecycle). main.ts preserves the raw request body on this prefix so signature verification works. These are inbound integrations from third parties — you don’t call them, and you shouldn’t move routes off the /api/webhooks/ prefix or the raw-body capture (and thus signature check) breaks.