Skip to main content

API Reference

The PensionPortal.ai API is a REST API that exposes the same backend used by the web application. All IORP II compliance data — schemes, members, contributions, KFH appointments, ORA reports, and documents — is accessible programmatically via this API.
The API is the same service as the PensionPortal.ai web app. There is no separate API gateway. All endpoints share the same authentication, authorisation, and tenant isolation logic.

Base URL

https://your-deployment.vercel.app
For local development:
http://localhost:3000

Authentication

All endpoints (except /api/health/*) require an authenticated session. See Authentication for details.

Content Type

All request and response bodies use application/json unless the endpoint accepts multipart file uploads (noted per-endpoint).

Versioning

The API is currently unversioned. Breaking changes will be announced via the Changelog before deployment.

Rate Limits

TierRequests/minuteBurst
Standard (authenticated)120 req/min200
AI endpoints (/api/ai/*)20 req/min30
File upload (/api/contributions, /api/documents)10 req/min15
Health probesUnlimited
Rate limit headers are included in every response:
X-RateLimit-Limit: 120
X-RateLimit-Remaining: 118
X-RateLimit-Reset: 1709123456
When the limit is exceeded, the API returns 429 Too Many Requests.

Error Format

All error responses follow a consistent structure:
{
  "error": "Human-readable error message",
  "details": { }
}
StatusMeaning
400Bad request — validation failed
401Unauthenticated — session required
403Forbidden — insufficient role or wrong tenant
404Resource not found
409Conflict — duplicate or state violation
422Unprocessable — business logic rejection (e.g. empty CSV)
429Rate limited
500Internal server error
503Service unavailable — dependency down

Health Probes

Health endpoints do not require authentication and are safe to poll from load balancers:
EndpointPurpose
GET /api/health/liveLiveness — is the process up?
GET /api/health/readyReadiness — are required env vars configured?
GET /api/health/dbDatabase connectivity check

Tenant Isolation

Every authenticated request runs in a tenant context. You cannot access data belonging to another tenant — this is enforced server-side regardless of what IDs you pass in the request. See Tenancy Conventions for full details.