Beta You're reading the docs for Kubb v5, which is currently in beta. View the stable v4 docs
Skip to content
Tags
openapiswaggerapi-specparserconverter
Details
  • Updated today
  • Created 3 months ago
Official v5.0.0-beta.74 MIT kubb >=5.0.0 node >=22

@kubb/adapter-oas

Parse and convert OpenAPI 2.0, 3.0, and 3.1 specifications into Kubb's universal AST. Handles discriminators, date formats, and server URL resolution.

Downloads
15.8k / mo
Stars
1.7k
Bundle size
593.5 kB
Updated
today

The OpenAPI adapter sits between your spec and every Kubb plugin. It reads the file at input.path, validates it, and converts each schema and operation into Kubb's universal AST that downstream plugins consume.

Configure it once on defineConfig. Its choices for date representation, integer width, and server URL apply to every plugin in the build.

Installation

shell
bun add -d @kubb/adapter-oas@beta
shell
pnpm add -D @kubb/adapter-oas@beta
shell
npm install --save-dev @kubb/adapter-oas@beta
shell
yarn add -D @kubb/adapter-oas@beta

Options

validate

Validates the OpenAPI spec with @readme/openapi-parser before parsing. Set to false only when you have a known-invalid spec that you still want to generate from.

Type: boolean
Required: false
Default: true

contentType

Preferred media type when extracting request and response schemas. Operations with multiple media types fall back to this one.

Defaults to the first JSON-compatible media type found in the spec (application/json, application/vnd.api+json, any *+json).

Type: 'application/json' | string
Required: false

server

Selects which entry in the spec's servers array becomes the base URL, and supplies values for its {variable} placeholders. Plugins that need a base URL read it from here (@kubb/plugin-axios, @kubb/plugin-fetch, @kubb/plugin-msw, ...).

server.index points at one of the spec's servers. Most projects pick 0 for the primary server, and use higher indices for staging or localhost. server.variables fills in any {variable} placeholders in the selected URL, falling back to each variable's default from the spec. Omit server to leave baseURL undefined.

Type: { index?: number; variables?: Record<string, string> }
Required: false

TIP

Plugins read baseURL from this server unless they override it explicitly.

Server variables substitute into the {variable} placeholders in the selected URL. With a spec server of https://api.{env}.example.com, setting server: { index: 0, variables: { env: 'prod' } } resolves baseURL to https://api.prod.example.com.

discriminator

How discriminator fields on oneOf/anyOf schemas are interpreted.

  • 'preserve' (default) keeps child schemas exactly as written. The discriminator narrows types at the call site, but child shapes stay the same.
  • 'propagate' pushes the discriminator property with its literal value into each child schema, so each branch's type field is precisely typed.
Type: 'preserve' | 'propagate'
Required: false
Default: 'preserve'
yaml
openapi: 3.0.3
components:
  schemas:
    Animal:
      required: [type]
      type: object
      oneOf:
        - $ref: '#/components/schemas/Cat'
        - $ref: '#/components/schemas/Dog'
      discriminator:
        propertyName: type
        mapping:
          cat: '#/components/schemas/Cat'
          dog: '#/components/schemas/Dog'
    Cat:
      type: object
      properties:
        type:
          type: string
        indoor:
          type: boolean
    Dog:
      type: object
      properties:
        type:
          type: string
        name:
          type: string
typescript
export type Cat = {
  type: string
  indoor?: boolean
}

export type Dog = {
  type: string
  name?: string
}

export type Animal = Cat | Dog
typescript
export type Cat = {
  type: 'cat'
  indoor?: boolean
}

export type Dog = {
  type: 'dog'
  name?: string
}

export type Animal = Cat | Dog

enums

Where inline enums live.

  • 'inline' (default) keeps each enum on the property that declares it.
  • 'root' lifts every inline enum to a reusable top-level schema named after its context (for example PetStatusEnum) and references it wherever it appears.
Type: 'inline' | 'root'
Required: false
Default: 'inline'
yaml
openapi: 3.0.3
components:
  schemas:
    Pet:
      type: object
      properties:
        status:
          type: string
          enum: [active, inactive]
typescript
export type Pet = {
  status?: 'active' | 'inactive'
}
typescript
export type PetStatusEnum = 'active' | 'inactive'

export type Pet = {
  status?: PetStatusEnum
}

dateType

How format: date-time schemas are represented downstream.

  • false falls through to a plain string with no validation.
  • 'string' (default) emits an ISO 8601 datetime string.
  • 'stringOffset' emits a datetime string with a timezone offset.
  • 'stringLocal' emits a local datetime string with no timezone.
  • 'date' emits a JavaScript Date. Best for client code, though JSON needs parsing to revive it.
Type: false | 'string' | 'stringOffset' | 'stringLocal' | 'date'
Required: false
Default: 'string'

The string variants all emit string at the TypeScript type level. The offset/local distinction surfaces in schema output such as Zod.

typescript
// false, 'string', 'stringOffset', 'stringLocal' → string
type CreatedAt = string
typescript
// format: date-time → JavaScript Date
type CreatedAt = Date

integerType

How type: integer (and format: int64) maps to TypeScript.

  • 'bigint' (default) is exact for 64-bit IDs, but JSON.stringify and JSON.parse cannot round-trip it. Use it only when you handle bigint serialization yourself.
  • 'number' fits most JSON APIs. It loses precision above Number.MAX_SAFE_INTEGER.
Type: 'number' | 'bigint'
Required: false
Default: 'bigint'
typescript
type Pet = {
  id: number
}
typescript
type Pet = {
  id: bigint
}

unknownType

AST type used when a schema's type cannot be inferred from the spec (additionalProperties: true, missing type, etc.).

Pick 'unknown' to force callers to narrow before using the value. 'any' is the loosest. 'void' matches some legacy APIs.

Type: 'any' | 'unknown' | 'void'
Required: false
Default: 'any'
typescript
type Pet = {
  extra: any
}
typescript
type Pet = {
  extra: unknown
}
typescript
type Pet = {
  extra: void
}

emptySchemaType

AST type used for fully empty schemas ({}). Defaults to the value of unknownType. Override only when empty schemas should be treated differently from unresolvable ones.

Type: 'any' | 'unknown' | 'void'
Required: false
Default: unknownType | 'any'

TIP

A common pairing sets unknownType: 'unknown' for safety and emptySchemaType: 'any' so empty 204 response bodies stay easy to use.

typescript
// empty schema {} → any
type EmptyModel = any
typescript
// empty schema {} → unknown
type EmptyModel = unknown

enumSuffix

Suffix appended to derived enum names when Kubb has to invent one (typically for inline enums on object properties).

Inline enums on a status property would be named statusEnum with the default. Change this to align with your project's naming convention.

Type: string
Required: false
Default: 'enum'
typescript
// Property `status` with inline enum values
const statusEnum = { available: 'available', pending: 'pending' } as const
type StatusEnum = (typeof statusEnum)[keyof typeof statusEnum]
typescript
const statusType = { available: 'available', pending: 'pending' } as const
type StatusType = (typeof statusType)[keyof typeof statusType]

Example

typescript
import {  } from 'kubb'
import {  } from '@kubb/adapter-oas'
import {  } from '@kubb/plugin-ts'

export default ({
  : { : './petStore.yaml' },
  : { : './src/gen' },
  : ({
    : true,
    : { : 0, : { : 'prod' } },
    : 'propagate',
    : 'root',
    : 'date',
    : 'number',
    : 'unknown',
    : 'unknown',
    : 'enum',
  }),
  : [()],
})

See Also