Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions apps/web/src/app/api/v1/openapi.json/route.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import { buildOpenApiDocument } from "@pointup/core/contracts";
import { NextResponse } from "next/server";

/**
* Public OpenAPI 3.1 document for the v1 API, generated from the zod contracts.
* Lets third parties integrate (or generate clients) without the TS package.
*/
export function GET() {
return NextResponse.json(buildOpenApiDocument());
}
4 changes: 4 additions & 0 deletions docs/api.md
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,10 @@ Every surface — web app, mobile, browser extension — talks to the same versi

Unauthenticated liveness check used by the ALB. Returns `{ "status": "ok" }`.

### `GET /api/v1/openapi.json`

Public OpenAPI 3.1 document for this API, generated from the same zod contracts the server validates against (component schemas via `z.toJSONSchema`). Point Swagger UI or a client generator at it, or fetch via `client.getOpenApiDocument()`.

### `GET /api/v1/providers`

The catalog of supported loyalty programs. Public — surfaces use it to render link forms before sign-in. `kind` is one of `airline`, `hotel`, `credit_card`, `rail`, or `shopping`, covering airlines, hotels, transferable credit card currencies (Chase Ultimate Rewards, Amex Membership Rewards, Capital One, Citi ThankYou, Bilt), rail (Amtrak Guest Rewards), and shopping portals (Rakuten).
Expand Down
5 changes: 5 additions & 0 deletions packages/api-client/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,11 @@ export class PointUpClient {
return this.request("GET", "/api/v1/providers");
}

/** The OpenAPI 3.1 document describing this API (public). */
getOpenApiDocument(): Promise<Record<string, unknown>> {
return this.request("GET", "/api/v1/openapi.json");
}

listLoyaltyAccounts(): Promise<LoyaltyAccountDto[]> {
return this.request("GET", "/api/v1/loyalty-accounts");
}
Expand Down
3 changes: 3 additions & 0 deletions packages/core/src/contracts/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -794,3 +794,6 @@ export function toIngestDealPageResultDto(
markdownExcerpt: result.markdownExcerpt,
};
}

// OpenAPI 3.1 document generated from the schemas above.
export * from "./openapi";
Loading
Loading