Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
34 commits
Select commit Hold shift + click to select a range
5bfcf6f
Fixes
xban1x Feb 25, 2026
0dd70ed
Few more improvements
xban1x Feb 25, 2026
eacd562
Vite plugin
xban1x Feb 26, 2026
a44f56e
onError hook support for general error handling
xban1x Feb 26, 2026
45b6c41
Add re-export from CommonModels support
xban1x Feb 26, 2026
8cf4ef8
Switch build pipeline
xban1x Feb 26, 2026
434118a
chore: updated tsdown config
jurerotar Feb 26, 2026
07043e2
chore: updated tsdown config
jurerotar Feb 26, 2026
a8ad5ee
chore: converted to pnpm
jurerotar Feb 26, 2026
2e98261
chore: publish fix
jurerotar Feb 26, 2026
f5e2e08
fix: fixed actions
jurerotar Feb 26, 2026
7d1fe80
chore: removed generated tests
jurerotar Feb 26, 2026
118fbe1
chore: updated dts export names
jurerotar Feb 27, 2026
16190b5
fix: removed useQuery.onError
jurerotar Feb 27, 2026
95c5e5c
chore: bumped version, formatted project
jurerotar Feb 27, 2026
4e2e72d
chore: fixed openapi-types dep
jurerotar Feb 27, 2026
28f7fa1
Fixes
xban1x Feb 27, 2026
6b8a38c
Merge remote-tracking branch 'origin/improve/speed' into improve/speed
xban1x Feb 27, 2026
a6ff235
Fix
xban1x Mar 1, 2026
d22d725
Fixes
xban1x Mar 1, 2026
e4468e7
Improve
xban1x Mar 1, 2026
de72535
Fixes
xban1x Mar 1, 2026
bd52dcb
Fixes
xban1x Mar 2, 2026
7c8046b
Fixes
xban1x Mar 2, 2026
856cf1b
Remove useless imports
xban1x Mar 2, 2026
4ce6a44
Fixes
xban1x Mar 2, 2026
8fb4e26
Fixes
xban1x Mar 2, 2026
10bf705
Fixes
xban1x Mar 2, 2026
b858c21
Add prefetchQueries support
xban1x Mar 2, 2026
c5e07aa
Make it void
xban1x Mar 2, 2026
7924ce9
Fixes
xban1x Mar 2, 2026
f4d3492
Fixes
xban1x Mar 2, 2026
4d19579
Minor fix
xban1x Mar 2, 2026
e310a7d
Fixes
xban1x Mar 2, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
The diff you're trying to view is too large. We only load the first 3000 changed files.
6 changes: 3 additions & 3 deletions .github/workflows/publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -22,11 +22,11 @@ jobs:
- uses: actions/setup-node@v6
with:
node-version: 24
cache: "yarn"
cache: "pnpm"

- run: yarn install --immutable
- run: pnpm install --frozen-lockfile

- run: yarn build
- run: pnpm build

- run: npm pack

Expand Down
7 changes: 7 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
!.yarn/releases
!.yarn/sdks

/test/generated/
/output
/dist

Expand All @@ -19,3 +20,9 @@ node_modules
test/*
!test/petstore.yaml
!test/config.ts
!test/generated/
!test/generated/.gitkeep
!test/generated/base/
!test/generated/base/.gitkeep
!test/generated/next/
!test/generated/next/.gitkeep
2 changes: 1 addition & 1 deletion .oxfmtrc.json
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
{
"$schema": "./node_modules/oxfmt/configuration_schema.json",
"ignorePatterns": ["**/*.hbs", "node_modules", ".yarn"]
"ignorePatterns": ["**/*.hbs", "node_modules", ".yarn", "test/generated/**"]
}
1 change: 1 addition & 0 deletions .oxlintrc.json
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
{
"$schema": "node_modules/oxlint/configuration_schema.json",
"ignorePatterns": ["test/generated/**"],
"plugins": ["eslint", "typescript", "unicorn", "import", "oxc", "promise", "vitest"],
"categories": {
"correctness": "off",
Expand Down
63 changes: 63 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ yarn openapi-codegen generate --config my-config.ts
--config Path to TS config file (default: 'openapi-codegen.config.ts')
--input Path/URL to OpenAPI JSON/YAML document
--output Output directory path (default: 'output')
--incremental Skip generation when OpenAPI and config are unchanged (default: true)
--format Format the generated code using Oxfmt (default: true)
--verbose Display detailed log messages during execution (default: false)

Expand All @@ -84,11 +85,16 @@ yarn openapi-codegen generate --config my-config.ts
--tsPath (Requires `--importPath` to be 'ts') Typescript import path (default: '@/data')
--removeOperationPrefixEndingWith Remove operation name prefixes that end with the specified string (default: 'Controller_')
--extractEnums Extract enums into separate Zod schemas (default: true)
--modelsInCommon Keep all schema declarations in defaultTag models and emit per-module proxy exports (default: false)
--replaceOptionalWithNullish Replace `.optional()` chains with `.nullish()` in generated Zod schemas (default: false)

--axiosRequestConfig Include Axios request config parameters in query hooks (default: false)
--infiniteQueries Generate infinite queries for paginated API endpoints (default: false)
--mutationEffects Add mutation effects options to mutation hooks (default: true)
--workspaceContext Allow generated hooks to resolve path/ACL params from OpenApiWorkspaceContext (default: false)
--inlineEndpoints Inline endpoint implementations into generated query files (default: false)
--inlineEndpointsExcludeModules Comma-separated modules/tags to keep as separate API files while inlineEndpoints=true
--modelsOnly Generate only model files (default: false)
--parseRequestParams Add Zod parsing to API endpoints (default: true)

--acl Generate ACL related files (default: true)
Expand Down Expand Up @@ -186,6 +192,63 @@ const config: OpenAPICodegenConfig = {
export default config;
```

### OpenApiWorkspaceContext (Path + ACL defaults)

Enable `workspaceContext: true` in codegen config (or pass `--workspaceContext`) and wrap your app subtree with `OpenApiWorkspaceContext.Provider` if generated hooks frequently repeat workspace-scoped params (for example `officeId`).

```tsx
import { OpenApiWorkspaceContext } from "@povio/openapi-codegen-cli";
// openapi-codegen.config.ts -> { workspaceContext: true }

<OpenApiWorkspaceContext.Provider values={{ officeId: "office_123" }}>
<MyWorkspacePages />
</OpenApiWorkspaceContext.Provider>;
```

Generated query/mutation hooks can then omit matching path/ACL params and resolve them from `OpenApiWorkspaceContext`.

### Generation Modes

You can control whether API endpoint files are emitted, inlined into query files, or skipped entirely.

```ts
import type { OpenAPICodegenConfig } from "@povio/openapi-codegen-cli";

const config: OpenAPICodegenConfig = {
// 1) Default mode: separate *.api.ts files are generated
// 2) Inline mode: endpoint logic is generated inside *.queries.ts
// and can be used without separate api files:
// inlineEndpoints: true,
// inlineEndpointsExcludeModules: ["Users", "Billing"],
// 3) Models-only mode: generate only *.models.ts files
// modelsOnly: true,
// 4) Keep all model declarations in common.models and generate per-module model proxies
// modelsInCommon: true,
};
```

### Vite Plugin

You can run codegen directly from Vite config (without CLI config file):

```ts
import { defineConfig } from "vite";
import { openApiCodegen } from "@povio/openapi-codegen-cli/vite";

export default defineConfig({
plugins: [
openApiCodegen({
input: "./openapi.yaml",
output: "./src/data",
inlineEndpoints: true,
incremental: true,
}),
],
});
```

The plugin runs on both `vite serve` and `vite build`, and watches local OpenAPI files in dev mode.

### Enums

If you're using Enums in your backend DTOs with `@Expose()` and `@IsEnum`, they may still not appear correctly in the OpenAPI schema unless you also provide both `enum` **and** `enumName` to `@ApiProperty`.
Expand Down
27 changes: 0 additions & 27 deletions esbuild.mjs

This file was deleted.

11 changes: 11 additions & 0 deletions openapi-codegen.config.mjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
/** @type {import('./src/generators/types/config').OpenAPICodegenConfig} */
const config = {
input: "http://127.0.0.1:4000/docs-json",
output: "./test/generated/next",
excludeTags: ["auth"],
replaceOptionalWithNullish: true,
builderConfigs: true,
infiniteQueries: true,
};

export default config;
94 changes: 51 additions & 43 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@povio/openapi-codegen-cli",
"version": "2.0.8-rc.5",
"version": "2.0.8-rc.23",
"keywords": [
"codegen",
"openapi",
Expand All @@ -16,58 +16,72 @@
"url": "git+https://github.com/povio/openapi-codegen-cli.git"
},
"bin": {
"openapi-codegen": "./dist/sh.js"
"openapi-codegen": "./dist/sh.mjs"
},
"files": [
"README.md",
"dist/*",
"src/assets/**",
"src/generators/templates/**"
"src/assets/**"
],
"type": "module",
"main": "./dist/index.mjs",
"types": "./dist/index.d.ts",
"types": "./dist/index.d.mts",
"exports": {
".": {
"types": "./dist/index.d.ts",
"import": "./dist/index.mjs",
"require": "./dist/index.mjs"
"types": "./dist/index.d.mts",
"import": "./dist/index.mjs"
},
"./vite": {
"types": "./dist/vite.d.mts",
"import": "./dist/vite.mjs"
},
"./generator": {
"types": "./dist/generator.d.ts",
"import": "./dist/generator.js",
"require": "./dist/generator.js"
"types": "./dist/generator.d.mts",
"import": "./dist/generator.mjs"
},
"./acl": {
"types": "./dist/acl.d.ts",
"import": "./dist/acl.mjs",
"require": "./dist/acl.mjs"
"types": "./dist/acl.d.mts",
"import": "./dist/acl.mjs"
},
"./zod": {
"types": "./dist/zod.d.mts",
"import": "./dist/zod.mjs"
}
},
"scripts": {
"start": "node --import tsx ./src/sh.ts",
"test": "vitest run",
"test:watch": "vitest",
"build:clean": "rm -rf ./dist",
"build:client": "vite build",
"build:cli": "node ./esbuild.mjs && chmod +x ./dist/sh.js",
"build": "yarn build:clean && yarn build:cli && yarn build:client",
"start:dist": "node ./dist/sh.js",
"build": "tsdown",
"start:dist": "node ./dist/sh.mjs",
"gen:base": "rm -rf ./test/generated/base && mkdir -p ./test/generated/base && pnpm start generate --config ./test/config.mjs --output ./test/generated/base --no-prettier",
"gen:next": "rm -rf ./test/generated/next && mkdir -p ./test/generated/next && pnpm start generate --config ./test/config.mjs --output ./test/generated/next --no-prettier",
"test:generated-eq": "vitest run ./src/generators/generated-output-eq.test.ts",
"gen:verify": "pnpm gen:base && pnpm gen:next && pnpm test:generated-eq",
"typecheck": "tsc --noEmit",
"lint": "oxlint --type-aware --fix",
"lint:check": "oxlint --type-aware",
"format": "oxfmt",
"format:check": "oxfmt --check",
"check": "yarn typecheck && yarn lint && yarn test",
"push": "yarn exec ./scripts/publish.sh",
"dev:generate": "rm -rf ./output && yarn start generate --config ./test/config.ts",
"dev:check": "yarn start check --config ./test/config.ts"
"check": "pnpm typecheck && pnpm lint && pnpm test",
"push": "node ./scripts/publish.mjs",
"dev:generate": "rm -rf ./output && pnpm start generate --config ./test/config.mjs",
"dev:check": "pnpm start check --config ./test/config.mjs",
"snapshot:openapi-localhost": "node ./scripts/snapshot-openapi-localhost.mjs",
"bench:vite-codegen": "node ./scripts/benchmark-vite-codegen.mjs"
},
"dependencies": {
"i18next": "^25.8.11",
"import-fresh": "^3.3.1"
"@apidevtools/swagger-parser": "^10.1.0",
"i18next": "^25.8.13",
"import-fresh": "^3.3.1",
"prompt-sync": "^4.2.0",
"reflect-metadata": "^0.2.2",
"ts-pattern": "^5.9.0",
"typescript": "^5.9.3",
"yargs": "^18.0.0",
"openapi-types": "^12.1.3"
},
"devDependencies": {
"@apidevtools/swagger-parser": "^10.1.0",
"@casl/ability": "^6.8.0",
"@casl/react": "^5.0.1",
"@tanstack/react-query": "~5.90.21",
Expand All @@ -76,32 +90,24 @@
"@types/react": "^19.2.14",
"@types/yargs": "^17.0.35",
"@vitejs/plugin-react": "^5.1.4",
"axios": "^1.13.5",
"esbuild": "0.27.3",
"handlebars": "^4.7.8",
"openapi-types": "^12.1.3",
"oxfmt": "^0.34.0",
"oxlint": "^1.49.0",
"oxlint-tsgolint": "^0.14.1",
"prompt-sync": "^4.2.0",
"oxlint": "^1.50.0",
"oxlint-tsgolint": "^0.15.0",
"react": "^19.2.4",
"reflect-metadata": "^0.2.2",
"ts-pattern": "^5.9.0",
"tsdown": "^0.21.0-beta.1",
"tsx": "^4.21.0",
"type-fest": "^5.4.4",
"typescript": "^5.9.3",
"vite": "^7.3.1",
"vite": "npm:rolldown-vite@^7.3.1",
"vite-plugin-dts": "^4.5.4",
"vitest": "4.0.18",
"yargs": "^18.0.0",
"zod": "^4.3.6"
"vitest": "4.0.18"
},
"peerDependencies": {
"@casl/ability": "^6.7.3",
"@casl/react": "^5.0.0",
"@tanstack/react-query": "^5.90.21",
"axios": "^1.13.1",
"react": "^19.1.0",
"vite": "^6.0.0 || ^7.0.0",
"zod": "^4.1.12"
},
"peerDependenciesMeta": {
Expand All @@ -110,12 +116,14 @@
},
"@casl/react": {
"optional": true
},
"vite": {
"optional": true
}
},
"engines": {
"node": ">= 14",
"npm": ">= 8",
"yarn": ">= 3.2"
"pnpm": ">= 9"
},
"packageManager": "yarn@4.2.2"
"packageManager": "pnpm@10.4.0"
}
Loading