@kubb/swagger-ts 2.0.0-beta.6 → 2.0.0-beta.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components.cjs +80 -43
- package/dist/components.cjs.map +1 -1
- package/dist/components.d.cts +66 -17
- package/dist/components.d.ts +66 -17
- package/dist/components.js +85 -46
- package/dist/components.js.map +1 -1
- package/dist/index.cjs +82 -38
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +414 -12
- package/dist/index.d.ts +414 -12
- package/dist/index.js +83 -40
- package/dist/index.js.map +1 -1
- package/dist/infer.d.ts +381 -0
- package/dist/infer.js +5 -0
- package/dist/infer.js.map +1 -0
- package/package.json +14 -8
- package/src/OperationGenerator.tsx +15 -3
- package/src/components/Oas.tsx +84 -0
- package/src/components/index.ts +1 -0
- package/src/infer/index.ts +7 -0
- package/src/infer/mappers.ts +93 -0
- package/src/infer/model.ts +38 -0
- package/src/infer/parse.ts +58 -0
- package/src/infer/requestParams.ts +170 -0
- package/src/infer/response.ts +39 -0
- package/src/infer/security.ts +158 -0
- package/src/plugin.ts +10 -25
- package/src/types.ts +26 -11
@@ -0,0 +1,38 @@
|
|
1
|
+
/* eslint-disable @typescript-eslint/no-namespace */
|
2
|
+
import type { OasTypes } from '@kubb/swagger'
|
3
|
+
import type {
|
4
|
+
FromSchema,
|
5
|
+
JSONSchema,
|
6
|
+
} from 'json-schema-to-ts'
|
7
|
+
|
8
|
+
namespace Checks {
|
9
|
+
export type ModelWithSchemas = {
|
10
|
+
components: {
|
11
|
+
schemas: Record<string, JSONSchema>
|
12
|
+
}
|
13
|
+
}
|
14
|
+
export type ModelWithSchemasNamed<TName extends string | number | symbol> = {
|
15
|
+
components: {
|
16
|
+
schemas: {
|
17
|
+
[TModelName in TName]: JSONSchema
|
18
|
+
}
|
19
|
+
}
|
20
|
+
}
|
21
|
+
export type ModelWithDefinitions = {
|
22
|
+
definitions: Record<string, JSONSchema>
|
23
|
+
}
|
24
|
+
export type ModelWithDefinitionsNamed<TName extends string | number | symbol = never> = {
|
25
|
+
definitions: {
|
26
|
+
[TModelName in TName]: JSONSchema
|
27
|
+
}
|
28
|
+
}
|
29
|
+
}
|
30
|
+
|
31
|
+
export type Model<
|
32
|
+
TOAS extends OasTypes.OASDocument,
|
33
|
+
TName extends TOAS extends Checks.ModelWithSchemas ? keyof TOAS['components']['schemas']
|
34
|
+
: TOAS extends Checks.ModelWithDefinitions ? keyof TOAS['definitions']
|
35
|
+
: never,
|
36
|
+
> = TOAS extends Checks.ModelWithSchemasNamed<TName> ? FromSchema<TOAS['components']['schemas'][TName]>
|
37
|
+
: TOAS extends Checks.ModelWithDefinitionsNamed<TName> ? FromSchema<TOAS['definitions'][TName]>
|
38
|
+
: never
|
@@ -0,0 +1,58 @@
|
|
1
|
+
/* eslint-disable @typescript-eslint/no-namespace */
|
2
|
+
import type { Booleans, Call, Objects, Strings, Tuples } from 'hotscript'
|
3
|
+
import type { Object } from 'ts-toolbelt'
|
4
|
+
|
5
|
+
namespace Checks {
|
6
|
+
export type AllOFf = { allOf: any[] }
|
7
|
+
export type Object = {
|
8
|
+
type: 'object'
|
9
|
+
properties: any
|
10
|
+
}
|
11
|
+
export type Properties = { properties: any }
|
12
|
+
export type PropertiesRequired = {
|
13
|
+
properties: Record<string, any>
|
14
|
+
required: string[]
|
15
|
+
}
|
16
|
+
}
|
17
|
+
|
18
|
+
type FixAdditionalPropertiesForAllOf<T> = T extends Checks.AllOFf ? Omit<T, 'allOf'> & {
|
19
|
+
allOf: Call<Tuples.Map<Objects.Omit<'additionalProperties'>>, T['allOf']>
|
20
|
+
}
|
21
|
+
: T
|
22
|
+
|
23
|
+
type FixMissingAdditionalProperties<T> = T extends Checks.Object ? Omit<T, 'additionalProperties'> & { additionalProperties: false }
|
24
|
+
: T
|
25
|
+
type FixMissingTypeObject<T> = T extends Checks.Properties ? T & { type: 'object' } : T
|
26
|
+
|
27
|
+
type FixExtraRequiredFields<T> = T extends Checks.PropertiesRequired ? Omit<T, 'required'> & {
|
28
|
+
required: Call<Tuples.Filter<Booleans.Extends<keyof T['properties']>>, T['required']>
|
29
|
+
}
|
30
|
+
: T
|
31
|
+
|
32
|
+
// Later suggest using json-machete
|
33
|
+
type FixJSONSchema<T> = FixAdditionalPropertiesForAllOf<
|
34
|
+
FixMissingAdditionalProperties<FixMissingTypeObject<FixExtraRequiredFields<T>>>
|
35
|
+
>
|
36
|
+
|
37
|
+
type Mutable<Type> = FixJSONSchema<
|
38
|
+
{
|
39
|
+
-readonly [Key in keyof Type]: Mutable<Type[Key]>
|
40
|
+
}
|
41
|
+
>
|
42
|
+
|
43
|
+
type RefToPath<T extends string> = T extends `#/${infer Ref}` ? Call<Strings.Split<'/'>, Ref>
|
44
|
+
: never
|
45
|
+
|
46
|
+
type ResolveRef<TObj, TRef extends string> = {
|
47
|
+
$id: TRef
|
48
|
+
} & Object.Path<TObj, RefToPath<TRef>>
|
49
|
+
|
50
|
+
type ResolveRefInObj<T, TBase> = T extends { $ref: infer Ref } ? Ref extends string ? ResolveRef<TBase, Ref>
|
51
|
+
: T
|
52
|
+
: T
|
53
|
+
|
54
|
+
type ResolveRefsInObj<T, TBase = T> = {
|
55
|
+
[K in keyof T]: ResolveRefsInObj<ResolveRefInObj<T[K], TBase>, TBase>
|
56
|
+
}
|
57
|
+
|
58
|
+
export type Parse<TOAS> = Mutable<ResolveRefsInObj<TOAS>>
|
@@ -0,0 +1,170 @@
|
|
1
|
+
/* eslint-disable @typescript-eslint/no-namespace */
|
2
|
+
/* eslint-disable @typescript-eslint/ban-types */
|
3
|
+
|
4
|
+
import type { OasTypes } from '@kubb/swagger'
|
5
|
+
import type { SplitByDelimiter, TupleToUnion } from '@kubb/types'
|
6
|
+
import type { Pipe, Strings, Tuples } from 'hotscript'
|
7
|
+
import type {
|
8
|
+
FromSchema,
|
9
|
+
JSONSchema,
|
10
|
+
} from 'json-schema-to-ts'
|
11
|
+
import type { MethodMap, ParamMap, PathMap } from './mappers.ts'
|
12
|
+
import type { SecurityParamsBySecurityRef } from './security.ts'
|
13
|
+
|
14
|
+
namespace Checks {
|
15
|
+
export type RequestBodyJson = {
|
16
|
+
requestBody: { content: { 'application/json': { schema: JSONSchema } } }
|
17
|
+
}
|
18
|
+
export type RequestBodyFormData = {
|
19
|
+
requestBody: {
|
20
|
+
content: { 'multipart/form-data': { schema: JSONSchema } }
|
21
|
+
}
|
22
|
+
}
|
23
|
+
export type RequestBodyFormEncoded = {
|
24
|
+
requestBody: {
|
25
|
+
content: {
|
26
|
+
'application/x-www-form-urlencoded': { schema: JSONSchema }
|
27
|
+
}
|
28
|
+
}
|
29
|
+
}
|
30
|
+
export type Parameters = {
|
31
|
+
parameters: { name: string; in: string }[]
|
32
|
+
}
|
33
|
+
export type PathBrackets = `${string}{${string}}${string}`
|
34
|
+
export type PathPattern = `${string}:${string}${string}`
|
35
|
+
export type Required = { required: true }
|
36
|
+
}
|
37
|
+
|
38
|
+
type ExtractPathParamsWithPattern<TPath extends string> = Pipe<
|
39
|
+
TPath,
|
40
|
+
[
|
41
|
+
Strings.Split<'/'>,
|
42
|
+
Tuples.Filter<Strings.StartsWith<':'>>,
|
43
|
+
Tuples.Map<Strings.Trim<':'>>,
|
44
|
+
Tuples.ToUnion,
|
45
|
+
]
|
46
|
+
>
|
47
|
+
|
48
|
+
type IsPathParameter<T extends string> = T extends `{${infer U}}` ? U : never
|
49
|
+
|
50
|
+
type ExtractPathParameters<T extends any[]> = {
|
51
|
+
[K in keyof T]: IsPathParameter<T[K]>
|
52
|
+
}
|
53
|
+
|
54
|
+
type ExtractSegments<TPath extends string> = SplitByDelimiter<TPath, '/'>
|
55
|
+
|
56
|
+
type ExtractSubSegments<T extends any[]> = {
|
57
|
+
[K in keyof T]: SplitByDelimiter<T[K], ';'>
|
58
|
+
}
|
59
|
+
|
60
|
+
type ExtractPathParamsWithBrackets<TPath extends string> = TupleToUnion<
|
61
|
+
ExtractPathParameters<ExtractSubSegments<ExtractSegments<TPath>>[number]>
|
62
|
+
>
|
63
|
+
|
64
|
+
export type RequestParams<
|
65
|
+
TOAS extends OasTypes.OASDocument,
|
66
|
+
TPath extends keyof PathMap<TOAS>,
|
67
|
+
TMethod extends keyof MethodMap<TOAS, TPath>,
|
68
|
+
> =
|
69
|
+
& (MethodMap<TOAS, TPath>[TMethod] extends Checks.RequestBodyJson ? MethodMap<TOAS, TPath>[TMethod]['requestBody'] extends Checks.Required ? {
|
70
|
+
/**
|
71
|
+
* The request body in JSON is required for this request.
|
72
|
+
*
|
73
|
+
* The value of `json` will be stringified and sent as the request body with `Content-Type: application/json`.
|
74
|
+
*/
|
75
|
+
json: FromSchema<
|
76
|
+
MethodMap<TOAS, TPath>[TMethod]['requestBody']['content']['application/json']['schema']
|
77
|
+
>
|
78
|
+
}
|
79
|
+
: {
|
80
|
+
/**
|
81
|
+
* The request body in JSON is optional for this request.
|
82
|
+
*
|
83
|
+
* The value of `json` will be stringified and sent as the request body with `Content-Type: application/json`.
|
84
|
+
*/
|
85
|
+
json?: FromSchema<
|
86
|
+
MethodMap<TOAS, TPath>[TMethod]['requestBody']['content']['application/json']['schema']
|
87
|
+
>
|
88
|
+
}
|
89
|
+
: MethodMap<TOAS, TPath>[TMethod] extends Checks.RequestBodyFormData ? MethodMap<TOAS, TPath>[TMethod]['requestBody'] extends Checks.Required ? {
|
90
|
+
/**
|
91
|
+
* The request body in multipart/form-data is required for this request.
|
92
|
+
*
|
93
|
+
* The value of `formData` will be sent as the request body with `Content-Type: multipart/form-data`.
|
94
|
+
*/
|
95
|
+
formData: FromSchema<
|
96
|
+
MethodMap<
|
97
|
+
TOAS,
|
98
|
+
TPath
|
99
|
+
>[TMethod]['requestBody']['content']['multipart/form-data']['schema']
|
100
|
+
>
|
101
|
+
}
|
102
|
+
: {
|
103
|
+
/**
|
104
|
+
* The request body in multipart/form-data is optional for this request.
|
105
|
+
*
|
106
|
+
* The value of `formData` will be sent as the request body with `Content-Type: multipart/form-data`.
|
107
|
+
*/
|
108
|
+
formData?: FromSchema<
|
109
|
+
MethodMap<
|
110
|
+
TOAS,
|
111
|
+
TPath
|
112
|
+
>[TMethod]['requestBody']['content']['multipart/form-data']['schema']
|
113
|
+
>
|
114
|
+
}
|
115
|
+
: MethodMap<TOAS, TPath>[TMethod] extends Checks.RequestBodyFormEncoded ? MethodMap<TOAS, TPath>[TMethod]['requestBody'] extends Checks.Required ? {
|
116
|
+
/**
|
117
|
+
* The request body in application/x-www-form-urlencoded is required for this request.
|
118
|
+
*
|
119
|
+
* The value of `formUrlEncoded` will be sent as the request body with `Content-Type: application/x-www-form-urlencoded`.
|
120
|
+
*/
|
121
|
+
formUrlEncoded: FromSchema<
|
122
|
+
MethodMap<
|
123
|
+
TOAS,
|
124
|
+
TPath
|
125
|
+
>[TMethod]['requestBody']['content']['application/x-www-form-urlencoded']['schema']
|
126
|
+
>
|
127
|
+
}
|
128
|
+
: {
|
129
|
+
/**
|
130
|
+
* The request body in application/x-www-form-urlencoded is optional for this request.
|
131
|
+
*
|
132
|
+
* The value of `formUrlEncoded` will be sent as the request body with `Content-Type: application/x-www-form-urlencoded`.
|
133
|
+
*/
|
134
|
+
formUrlEncoded?: FromSchema<
|
135
|
+
MethodMap<
|
136
|
+
TOAS,
|
137
|
+
TPath
|
138
|
+
>[TMethod]['requestBody']['content']['application/x-www-form-urlencoded']['schema']
|
139
|
+
>
|
140
|
+
}
|
141
|
+
: {})
|
142
|
+
& (MethodMap<TOAS, TPath>[TMethod] extends Checks.Parameters ? ParamMap<MethodMap<TOAS, TPath>[TMethod]['parameters']>
|
143
|
+
: {})
|
144
|
+
& // If there is any parameters defined in path but not in the parameters array, we should add them to the params
|
145
|
+
(TPath extends Checks.PathBrackets ? {
|
146
|
+
/**
|
147
|
+
* Parameters defined in the path are required for this request.
|
148
|
+
*
|
149
|
+
* The value of `params` will be used to replace the path parameters.
|
150
|
+
*
|
151
|
+
* For example if path is `/todos/{id}` and `params` is `{ id: '1' }`, the path will be `/todos/1`
|
152
|
+
*/
|
153
|
+
params: Record<ExtractPathParamsWithBrackets<TPath>, string | number | bigint | boolean>
|
154
|
+
}
|
155
|
+
: {})
|
156
|
+
& (TPath extends Checks.PathPattern ? {
|
157
|
+
/**
|
158
|
+
* Parameters defined in the path are required for this request.
|
159
|
+
*
|
160
|
+
* The value of `params` will be used to replace the path parameters.
|
161
|
+
*
|
162
|
+
* For example if path is `/todos/:id` and `params` is `{ id: '1' }`, the path will be `/todos/1`.
|
163
|
+
*/
|
164
|
+
params: Record<ExtractPathParamsWithPattern<TPath>, string | number | bigint | boolean>
|
165
|
+
}
|
166
|
+
: {})
|
167
|
+
& // Respect security definitions in path object
|
168
|
+
SecurityParamsBySecurityRef<TOAS, MethodMap<TOAS, TPath>[TMethod]>
|
169
|
+
& // Respect global security definitions
|
170
|
+
SecurityParamsBySecurityRef<TOAS, TOAS>
|
@@ -0,0 +1,39 @@
|
|
1
|
+
/* eslint-disable @typescript-eslint/no-namespace */
|
2
|
+
import type { OasTypes } from '@kubb/swagger'
|
3
|
+
import type {
|
4
|
+
FromSchema,
|
5
|
+
} from 'json-schema-to-ts'
|
6
|
+
import type { MethodMap, PathMap, StatusMap } from './mappers.ts'
|
7
|
+
|
8
|
+
namespace Checks {
|
9
|
+
export type Content = { content: any }
|
10
|
+
}
|
11
|
+
|
12
|
+
type ResponseSchemas<
|
13
|
+
TOAS extends OasTypes.OASDocument,
|
14
|
+
TPath extends keyof PathMap<TOAS>,
|
15
|
+
TMethod extends keyof MethodMap<TOAS, TPath>,
|
16
|
+
TStatus extends keyof StatusMap<TOAS, TPath, TMethod>,
|
17
|
+
> = StatusMap<TOAS, TPath, TMethod>[TStatus]['content']
|
18
|
+
|
19
|
+
type JSONResponseSchema<
|
20
|
+
TOAS extends OasTypes.OASDocument,
|
21
|
+
TPath extends keyof PathMap<TOAS>,
|
22
|
+
TMethod extends keyof MethodMap<TOAS, TPath>,
|
23
|
+
TStatus extends keyof StatusMap<TOAS, TPath, TMethod>,
|
24
|
+
> = StatusMap<TOAS, TPath, TMethod>[TStatus] extends Checks.Content ? ResponseSchemas<TOAS, TPath, TMethod, TStatus>[
|
25
|
+
keyof ResponseSchemas<
|
26
|
+
TOAS,
|
27
|
+
TPath,
|
28
|
+
TMethod,
|
29
|
+
TStatus
|
30
|
+
>
|
31
|
+
]['schema']
|
32
|
+
: StatusMap<TOAS, TPath, TMethod>[TStatus]['schema']
|
33
|
+
|
34
|
+
export type Response<
|
35
|
+
TOAS extends OasTypes.OASDocument,
|
36
|
+
TPath extends keyof PathMap<TOAS>,
|
37
|
+
TMethod extends keyof MethodMap<TOAS, TPath>,
|
38
|
+
TStatusCode extends keyof StatusMap<TOAS, TPath, TMethod> = 200,
|
39
|
+
> = FromSchema<JSONResponseSchema<TOAS, TPath, TMethod, TStatusCode>>
|
@@ -0,0 +1,158 @@
|
|
1
|
+
/* eslint-disable @typescript-eslint/no-namespace */
|
2
|
+
/* eslint-disable @typescript-eslint/ban-types */
|
3
|
+
|
4
|
+
import type { Call, Objects, Tuples } from 'hotscript'
|
5
|
+
|
6
|
+
namespace Checks {
|
7
|
+
export type Security = { security: { [key: string]: any }[] }
|
8
|
+
|
9
|
+
export namespace AuthParams {
|
10
|
+
export type Basic =
|
11
|
+
| {
|
12
|
+
type: 'http'
|
13
|
+
scheme: 'basic'
|
14
|
+
}
|
15
|
+
| { type: 'basic' }
|
16
|
+
export type Bearer =
|
17
|
+
| {
|
18
|
+
type: 'http'
|
19
|
+
scheme: 'bearer'
|
20
|
+
}
|
21
|
+
| { type: 'bearer' }
|
22
|
+
|
23
|
+
export type OAuth2 = {
|
24
|
+
type: 'oauth2'
|
25
|
+
}
|
26
|
+
export type ApiKey = {
|
27
|
+
type: 'apiKey'
|
28
|
+
in: 'header'
|
29
|
+
}
|
30
|
+
}
|
31
|
+
|
32
|
+
export namespace AuthName {
|
33
|
+
export type Basic = `basic${string}`
|
34
|
+
export type Bearer = `bearer${string}`
|
35
|
+
export type OAuth2 = `oauth${string}`
|
36
|
+
}
|
37
|
+
}
|
38
|
+
|
39
|
+
type SecuritySchemeName<T extends Checks.Security> = Call<
|
40
|
+
Tuples.Map<Objects.Keys>,
|
41
|
+
T['security']
|
42
|
+
>[number]
|
43
|
+
|
44
|
+
namespace AuthParams {
|
45
|
+
export type Basic<TSecurityScheme> = TSecurityScheme extends Checks.AuthParams.Basic ? {
|
46
|
+
headers: {
|
47
|
+
/**
|
48
|
+
* `Authorization` header is required for basic authentication
|
49
|
+
* @see https://en.wikipedia.org/wiki/Basic_access_authentication
|
50
|
+
*
|
51
|
+
* It contains the word `Basic` followed by a space and a base64-encoded string `username:password`
|
52
|
+
*
|
53
|
+
* @example
|
54
|
+
* ```
|
55
|
+
* Authorization: Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ==
|
56
|
+
* ```
|
57
|
+
*/
|
58
|
+
Authorization: `Basic ${string}`
|
59
|
+
}
|
60
|
+
}
|
61
|
+
: {}
|
62
|
+
|
63
|
+
export type Bearer<TSecurityScheme> = TSecurityScheme extends Checks.AuthParams.Bearer ? {
|
64
|
+
/**
|
65
|
+
* `Authorization` header is required for bearer authentication
|
66
|
+
* @see https://swagger.io/docs/specification/authentication/bearer-authentication/
|
67
|
+
*/
|
68
|
+
headers: {
|
69
|
+
/**
|
70
|
+
* It contains the word `Bearer` followed by a space and the token
|
71
|
+
*
|
72
|
+
* @example
|
73
|
+
* ```
|
74
|
+
* Authorization: Bearer {token}
|
75
|
+
* ```
|
76
|
+
*/
|
77
|
+
Authorization: `Bearer ${string}`
|
78
|
+
}
|
79
|
+
}
|
80
|
+
: {}
|
81
|
+
|
82
|
+
export type ApiKey<TSecurityScheme> = TSecurityScheme extends Checks.AuthParams.ApiKey & { name: infer TApiKeyHeaderName } ? {
|
83
|
+
headers: {
|
84
|
+
/**
|
85
|
+
* Header required for API key authentication
|
86
|
+
*/
|
87
|
+
[THeaderName in TApiKeyHeaderName extends string ? TApiKeyHeaderName : never]: string
|
88
|
+
}
|
89
|
+
}
|
90
|
+
: TSecurityScheme extends {
|
91
|
+
type: 'apiKey'
|
92
|
+
in: 'query'
|
93
|
+
name: infer TApiKeyQueryName
|
94
|
+
} ? {
|
95
|
+
query: {
|
96
|
+
/**
|
97
|
+
* Query parameter required for API key authentication
|
98
|
+
*/
|
99
|
+
[TQueryName in TApiKeyQueryName extends string ? TApiKeyQueryName : never]: string
|
100
|
+
}
|
101
|
+
}
|
102
|
+
: {}
|
103
|
+
|
104
|
+
export type OAuth2<TSecurityScheme> = TSecurityScheme extends Checks.AuthParams.OAuth2 ? {
|
105
|
+
/**
|
106
|
+
* `Authorization` header is required for OAuth2.
|
107
|
+
*/
|
108
|
+
headers: {
|
109
|
+
/**
|
110
|
+
* The access token string as issued by the authorization server.
|
111
|
+
* @example `Authorization: Bearer <access_token>`
|
112
|
+
*/
|
113
|
+
Authorization: `Bearer ${string}`
|
114
|
+
}
|
115
|
+
}
|
116
|
+
: {}
|
117
|
+
}
|
118
|
+
|
119
|
+
type OASSecurityParams<TSecurityScheme> =
|
120
|
+
& AuthParams.Basic<TSecurityScheme>
|
121
|
+
& AuthParams.Bearer<TSecurityScheme>
|
122
|
+
& AuthParams.ApiKey<TSecurityScheme>
|
123
|
+
& AuthParams.OAuth2<TSecurityScheme>
|
124
|
+
|
125
|
+
export type SecurityParamsBySecurityRef<TOAS, TSecurityObj> = TSecurityObj extends Checks.Security ? TOAS extends
|
126
|
+
| {
|
127
|
+
components: {
|
128
|
+
securitySchemes: {
|
129
|
+
[
|
130
|
+
TSecuritySchemeNameKey in SecuritySchemeName<TSecurityObj> extends string ? SecuritySchemeName<TSecurityObj>
|
131
|
+
: never
|
132
|
+
]: infer TSecurityScheme
|
133
|
+
}
|
134
|
+
}
|
135
|
+
}
|
136
|
+
| {
|
137
|
+
securityDefinitions: {
|
138
|
+
[
|
139
|
+
TSecuritySchemeNameKey in SecuritySchemeName<TSecurityObj> extends string ? SecuritySchemeName<TSecurityObj>
|
140
|
+
: never
|
141
|
+
]: infer TSecurityScheme
|
142
|
+
}
|
143
|
+
} ? OASSecurityParams<TSecurityScheme>
|
144
|
+
// OAS may have a bad reference to a security scheme
|
145
|
+
// So we can assume it
|
146
|
+
: SecuritySchemeName<TSecurityObj> extends Checks.AuthName.Basic ? AuthParams.Basic<{
|
147
|
+
type: 'http'
|
148
|
+
scheme: 'basic'
|
149
|
+
}>
|
150
|
+
: SecuritySchemeName<TSecurityObj> extends Checks.AuthName.Bearer ? AuthParams.Bearer<{
|
151
|
+
type: 'http'
|
152
|
+
scheme: 'bearer'
|
153
|
+
}>
|
154
|
+
: SecuritySchemeName<TSecurityObj> extends Checks.AuthName.OAuth2 ? AuthParams.OAuth2<{
|
155
|
+
type: 'oauth2'
|
156
|
+
}>
|
157
|
+
: {}
|
158
|
+
: {}
|
package/src/plugin.ts
CHANGED
@@ -16,7 +16,7 @@ export const pluginKey: PluginOptions['key'] = [pluginName] satisfies PluginOpti
|
|
16
16
|
|
17
17
|
export const definePlugin = createPlugin<PluginOptions>((options) => {
|
18
18
|
const {
|
19
|
-
output = 'types',
|
19
|
+
output = { path: 'types' },
|
20
20
|
group,
|
21
21
|
exclude = [],
|
22
22
|
include,
|
@@ -25,9 +25,9 @@ export const definePlugin = createPlugin<PluginOptions>((options) => {
|
|
25
25
|
dateType = 'string',
|
26
26
|
optionalType = 'questionToken',
|
27
27
|
transformers = {},
|
28
|
-
|
28
|
+
oasType = false,
|
29
29
|
} = options
|
30
|
-
const template = group?.output ? group.output : `${output}/{{tag}}Controller`
|
30
|
+
const template = group?.output ? group.output : `${output.path}/{{tag}}Controller`
|
31
31
|
|
32
32
|
return {
|
33
33
|
name: pluginName,
|
@@ -36,20 +36,21 @@ export const definePlugin = createPlugin<PluginOptions>((options) => {
|
|
36
36
|
dateType,
|
37
37
|
enumType,
|
38
38
|
optionalType,
|
39
|
+
oasType,
|
39
40
|
// keep the used enumnames between TypeBuilder and OperationGenerator per plugin(pluginKey)
|
40
41
|
usedEnumNames: {},
|
41
42
|
},
|
42
43
|
pre: [swaggerPluginName],
|
43
44
|
resolvePath(baseName, directory, options) {
|
44
45
|
const root = path.resolve(this.config.root, this.config.output.path)
|
45
|
-
const mode = FileManager.getMode(path.resolve(root, output))
|
46
|
+
const mode = FileManager.getMode(path.resolve(root, output.path))
|
46
47
|
|
47
48
|
if (mode === 'file') {
|
48
49
|
/**
|
49
50
|
* when output is a file then we will always append to the same file(output file), see fileManager.addOrAppend
|
50
51
|
* Other plugins then need to call addOrAppend instead of just add from the fileManager class
|
51
52
|
*/
|
52
|
-
return path.resolve(root, output)
|
53
|
+
return path.resolve(root, output.path)
|
53
54
|
}
|
54
55
|
|
55
56
|
if (options?.tag && group?.type === 'tag') {
|
@@ -58,7 +59,7 @@ export const definePlugin = createPlugin<PluginOptions>((options) => {
|
|
58
59
|
return path.resolve(root, renderTemplate(template, { tag }), baseName)
|
59
60
|
}
|
60
61
|
|
61
|
-
return path.resolve(root, output, baseName)
|
62
|
+
return path.resolve(root, output.path, baseName)
|
62
63
|
},
|
63
64
|
resolveName(name, type) {
|
64
65
|
const resolvedName = pascalCase(name)
|
@@ -83,7 +84,7 @@ export const definePlugin = createPlugin<PluginOptions>((options) => {
|
|
83
84
|
|
84
85
|
const schemas = await swaggerPlugin.api.getSchemas()
|
85
86
|
const root = path.resolve(this.config.root, this.config.output.path)
|
86
|
-
const mode = FileManager.getMode(path.resolve(root, output))
|
87
|
+
const mode = FileManager.getMode(path.resolve(root, output.path))
|
87
88
|
const builder = new TypeBuilder(this.plugin.options, { oas, pluginManager: this.pluginManager })
|
88
89
|
|
89
90
|
builder.add(
|
@@ -126,7 +127,7 @@ export const definePlugin = createPlugin<PluginOptions>((options) => {
|
|
126
127
|
|
127
128
|
await this.addFile({
|
128
129
|
path: resolvedPath,
|
129
|
-
baseName: output as KubbFile.BaseName,
|
130
|
+
baseName: output.path as KubbFile.BaseName,
|
130
131
|
source,
|
131
132
|
imports: [],
|
132
133
|
meta: {
|
@@ -161,25 +162,9 @@ export const definePlugin = createPlugin<PluginOptions>((options) => {
|
|
161
162
|
|
162
163
|
await this.fileManager.addIndexes({
|
163
164
|
root,
|
164
|
-
|
165
|
+
output,
|
165
166
|
meta: { pluginKey: this.plugin.key },
|
166
167
|
options: {
|
167
|
-
map: (file) => {
|
168
|
-
return {
|
169
|
-
...file,
|
170
|
-
exports: file.exports?.map((item) => {
|
171
|
-
if (exportAs) {
|
172
|
-
return {
|
173
|
-
...item,
|
174
|
-
name: exportAs,
|
175
|
-
asAlias: !!exportAs,
|
176
|
-
}
|
177
|
-
}
|
178
|
-
return item
|
179
|
-
}),
|
180
|
-
}
|
181
|
-
},
|
182
|
-
output,
|
183
168
|
isTypeOnly: true,
|
184
169
|
},
|
185
170
|
})
|
package/src/types.ts
CHANGED
@@ -1,13 +1,23 @@
|
|
1
|
-
import type { KubbPlugin, PluginFactoryOptions, ResolveNameParams } from '@kubb/core'
|
1
|
+
import type { KubbFile, KubbPlugin, PluginFactoryOptions, ResolveNameParams } from '@kubb/core'
|
2
2
|
import type { AppMeta as SwaggerAppMeta, Exclude, Include, Override, ResolvePathOptions } from '@kubb/swagger'
|
3
3
|
|
4
4
|
export type Options = {
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
5
|
+
output?: {
|
6
|
+
/**
|
7
|
+
* Relative path to save the TypeScript types.
|
8
|
+
* When output is a file it will save all models inside that file else it will create a file per schema item.
|
9
|
+
* @default 'types'
|
10
|
+
*/
|
11
|
+
path: string
|
12
|
+
/**
|
13
|
+
* Name to be used for the `export * as {{exportAs}} from './'`
|
14
|
+
*/
|
15
|
+
exportAs?: string
|
16
|
+
/**
|
17
|
+
* Add an extension to the generated imports and exports, default it will not use an extension
|
18
|
+
*/
|
19
|
+
extName?: KubbFile.Extname
|
20
|
+
}
|
11
21
|
/**
|
12
22
|
* Group the TypeScript types based on the provided name.
|
13
23
|
*/
|
@@ -25,10 +35,6 @@ export type Options = {
|
|
25
35
|
*/
|
26
36
|
output?: string
|
27
37
|
}
|
28
|
-
/**
|
29
|
-
* Name to be used for the `export * as {{exportAs}} from './`
|
30
|
-
*/
|
31
|
-
exportAs?: string
|
32
38
|
/**
|
33
39
|
* Array containing exclude paramaters to exclude/skip tags/operations/methods/paths.
|
34
40
|
*/
|
@@ -65,6 +71,12 @@ export type Options = {
|
|
65
71
|
*/
|
66
72
|
name?: (name: ResolveNameParams['name'], type?: ResolveNameParams['type']) => string
|
67
73
|
}
|
74
|
+
/**
|
75
|
+
* Export Oas object as Oas type with import type { Infer } from `@kubb/swagger-ts/infer`
|
76
|
+
* TODO add docs
|
77
|
+
* @beta
|
78
|
+
*/
|
79
|
+
oasType?: boolean
|
68
80
|
}
|
69
81
|
|
70
82
|
type ResolvedOptions = {
|
@@ -72,6 +84,7 @@ type ResolvedOptions = {
|
|
72
84
|
dateType: NonNullable<Options['dateType']>
|
73
85
|
optionalType: NonNullable<Options['optionalType']>
|
74
86
|
transformers: NonNullable<Options['transformers']>
|
87
|
+
oasType: NonNullable<Options['oasType']>
|
75
88
|
usedEnumNames: Record<string, number>
|
76
89
|
}
|
77
90
|
|
@@ -90,3 +103,5 @@ declare module '@kubb/core' {
|
|
90
103
|
['@kubb/swagger-ts']: PluginOptions
|
91
104
|
}
|
92
105
|
}
|
106
|
+
// external packages
|
107
|
+
export * as Infer from './infer/index.ts'
|