OpenAPI
Generate interactive API documentation from an OpenAPI 3.x or AsyncAPI spec using @publier/openapi.
@publier/openapi generates MDX pages and interactive components from your OpenAPI 3.x or AsyncAPI 2/3 spec. The API Reference section of this site was built with it.
Install
pnpm add @publier/openapiQuickstart
-
Place your spec at the project root:
openapi.yaml openapi: "3.1.0"info:title: My APIversion: "1.0.0"paths:/users:get:operationId: listUserssummary: List userstags: [Users]responses:"200":description: A list of users -
Write a generation script:
scripts/generate-api.ts import { generateFiles } from '@publier/openapi/generate';import { readFileSync } from 'node:fs';import { parse } from 'yaml';const spec = parse(readFileSync('./openapi.yaml', 'utf-8'));generateFiles({spec,outputDir: './src/content/docs/api',groupBy: 'tag', // group pages by tag (or 'path')per: 'operation', // one MDX file per operation}); -
Run the generator:
Terminal window bun run scripts/generate-api.tsThis writes one MDX file per operation plus a
meta.yamlthat orders them in the sidebar. -
Add an npm script for convenience:
package.json {"scripts": {"gen:api": "bun run scripts/generate-api.ts"}} -
Label and position the API group. The generator emits a
meta.yamlatsrc/content/docs/api/meta.yamlwith apages:list ordering the operation groups. Add atitle:to set the display label:src/content/docs/api/meta.yaml title: API Referencepages:- users # group slugs emitted by the generator- orders- webhooksTo control where the API group appears relative to other top-level sections, edit the parent
src/content/docs/meta.yaml— list directory slugs underpages:in the order you want them rendered. The sidebar is auto-generated from the filesystem, so noastro.config.tschanges are needed. -
Run
publier dev— generated pages render with interactive components for parameters, request bodies, and code samples.
Code samples
Request examples are generated automatically in six languages: cURL, JavaScript (fetch), Python (requests), Go (net/http), Java (HttpClient), and C#.
To provide your own, add x-codeSamples to the operation in your spec — the generator uses those instead.
Server-side API
For programmatic access at build time:
import { createOpenAPI } from '@publier/openapi/server';
const openapi = createOpenAPI({ input: ['./openapi.yaml'] });
const op = await openapi.getOperation('listUsers');const get = await openapi.getOperationByPath('/users', 'get');const tag = await openapi.getOperationsByTag('Users');const nav = await openapi.getNavigation({ slugPrefix: 'api' });Multi-spec merging just works:
const merged = createOpenAPI({ input: ['./public-api.yaml', './admin-api.yaml'],});AsyncAPI
AsyncAPI 2.x and 3.x specs are also supported. Point the generator at your AsyncAPI file the same way you would an OpenAPI spec — it emits channel pages with AsyncChannel and AsyncMessage components.
Components
| Component | Purpose |
|---|---|
APIReference | Single endpoint — params, body, responses |
APIPage | Full page layout for an operation |
APIPlayground | Interactive “try it” panel |
SchemaView | JSON Schema renderer |
CodeSamples | Multi-language request examples |
AsyncChannel | AsyncAPI channel view |
AsyncMessage | AsyncAPI message schema |
Import from subpath exports:
import { APIReference } from '@publier/openapi/components/api-reference';