@kubb/plugin-axios 5.0.0-beta.75 → 5.0.0-beta.76
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/index.cjs +178 -119
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +4 -2
- package/dist/index.js +178 -119
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
- package/src/generators/clientGenerator.tsx +2 -1
- package/templates/axios.ts +34 -10
package/templates/axios.ts
CHANGED
|
@@ -86,7 +86,8 @@ export type BodySerializer = (body: unknown, contentType?: string) => unknown
|
|
|
86
86
|
|
|
87
87
|
/**
|
|
88
88
|
* Parses a value before it is sent or after it is received, returning the parsed (and optionally
|
|
89
|
-
* transformed) value. Wires zod parsing through the per-call `parser.request` / `parser.response`
|
|
89
|
+
* transformed) value. Wires zod parsing through the per-call `parser.request` / `parser.response` /
|
|
90
|
+
* `parser.error` hooks (`error` runs on the error body when a non-2xx call does not throw).
|
|
90
91
|
*/
|
|
91
92
|
export type Parser<T = unknown> = (value: T) => T | Promise<T>
|
|
92
93
|
|
|
@@ -136,7 +137,7 @@ export type RequestConfig<TBody = unknown, TRequest = AxiosRequestConfig, TRespo
|
|
|
136
137
|
transport?: AxiosInstance
|
|
137
138
|
querySerializer?: QuerySerializer
|
|
138
139
|
bodySerializer?: BodySerializer
|
|
139
|
-
parser?: { request?: Parser; response?: Parser }
|
|
140
|
+
parser?: { request?: Parser; response?: Parser; error?: Parser }
|
|
140
141
|
security?: Array<Auth>
|
|
141
142
|
auth?: AuthResolver
|
|
142
143
|
}
|
|
@@ -254,13 +255,30 @@ function isFormBody(body: unknown): boolean {
|
|
|
254
255
|
)
|
|
255
256
|
}
|
|
256
257
|
|
|
258
|
+
function appendFormDataValue(formData: FormData, key: string, value: unknown): void {
|
|
259
|
+
if (value === undefined || value === null) return
|
|
260
|
+
if (value instanceof Blob) formData.append(key, value)
|
|
261
|
+
else if (value instanceof Date) formData.append(key, value.toISOString())
|
|
262
|
+
else if (typeof value === 'object') formData.append(key, JSON.stringify(value))
|
|
263
|
+
else formData.append(key, String(value))
|
|
264
|
+
}
|
|
265
|
+
|
|
257
266
|
/**
|
|
258
267
|
* Default body serializer: passes binary/form bodies through and JSON-serializes everything else.
|
|
259
|
-
* For `
|
|
268
|
+
* For `multipart/form-data` plain objects become `FormData` and for
|
|
269
|
+
* `application/x-www-form-urlencoded` they become `URLSearchParams`.
|
|
260
270
|
*/
|
|
261
271
|
export const defaultBodySerializer: BodySerializer = (body, contentType) => {
|
|
262
272
|
if (body === undefined || body === null) return undefined
|
|
263
273
|
if (isFormBody(body)) return body
|
|
274
|
+
if (contentType?.includes('multipart/form-data')) {
|
|
275
|
+
const formData = new FormData()
|
|
276
|
+
for (const [key, value] of Object.entries(body as Record<string, unknown>)) {
|
|
277
|
+
if (Array.isArray(value)) for (const item of value) appendFormDataValue(formData, key, item)
|
|
278
|
+
else appendFormDataValue(formData, key, value)
|
|
279
|
+
}
|
|
280
|
+
return formData
|
|
281
|
+
}
|
|
264
282
|
if (contentType?.includes('application/x-www-form-urlencoded')) {
|
|
265
283
|
return new URLSearchParams(body as Record<string, string>)
|
|
266
284
|
}
|
|
@@ -426,10 +444,7 @@ export function createClientCore<TRequest = AxiosRequestConfig, TResponse = Axio
|
|
|
426
444
|
const bodySerializer = requestConfig.bodySerializer ?? config.bodySerializer ?? defaultBodySerializer
|
|
427
445
|
|
|
428
446
|
const headers = mergeHeaders(config.headers, requestConfig.headers)
|
|
429
|
-
|
|
430
|
-
headers['Content-Type'] = requestConfig.contentType
|
|
431
|
-
}
|
|
432
|
-
const contentType = headers['Content-Type'] ?? headers['content-type']
|
|
447
|
+
const requestContentType = requestConfig.contentType ?? headers['Content-Type'] ?? headers['content-type']
|
|
433
448
|
|
|
434
449
|
const query: Record<string, unknown> = { ...((requestConfig.query ?? requestConfig.params) as Record<string, unknown> | undefined) }
|
|
435
450
|
|
|
@@ -441,6 +456,14 @@ export function createClientCore<TRequest = AxiosRequestConfig, TResponse = Axio
|
|
|
441
456
|
})
|
|
442
457
|
|
|
443
458
|
const validatedBody = await runParser(requestConfig.parser?.request, requestConfig.body)
|
|
459
|
+
const body = bodySerializer(validatedBody, requestContentType)
|
|
460
|
+
// A FormData body must keep its Content-Type unset so axios appends the multipart boundary.
|
|
461
|
+
if (body instanceof FormData) {
|
|
462
|
+
delete headers['Content-Type']
|
|
463
|
+
delete headers['content-type']
|
|
464
|
+
} else if (requestConfig.contentType) {
|
|
465
|
+
headers['Content-Type'] = requestConfig.contentType
|
|
466
|
+
}
|
|
444
467
|
const pathParams = requestConfig.path ?? {}
|
|
445
468
|
const url = (requestConfig.url ?? '').replace(/\{([^{}]+)\}/g, (_, key: string) => encodeURIComponent(String(pathParams[key] ?? '')))
|
|
446
469
|
const baseURL = [config.baseURL, requestConfig.baseURL].filter(Boolean).join('') || undefined
|
|
@@ -455,8 +478,8 @@ export function createClientCore<TRequest = AxiosRequestConfig, TResponse = Axio
|
|
|
455
478
|
headers,
|
|
456
479
|
params: query,
|
|
457
480
|
paramsSerializer: (params) => querySerializer(params as Record<string, unknown>),
|
|
458
|
-
data:
|
|
459
|
-
transformRequest: (data) =>
|
|
481
|
+
data: body,
|
|
482
|
+
transformRequest: (data) => data,
|
|
460
483
|
signal: requestConfig.signal,
|
|
461
484
|
responseType: requestConfig.responseType,
|
|
462
485
|
validateStatus,
|
|
@@ -466,10 +489,11 @@ export function createClientCore<TRequest = AxiosRequestConfig, TResponse = Axio
|
|
|
466
489
|
const response = await activeInstance.request<unknown, AxiosResponse>(axiosConfig)
|
|
467
490
|
const isSuccess = response.status >= 200 && response.status < 300
|
|
468
491
|
const data = isSuccess ? await runParser(requestConfig.parser?.response, response.data) : undefined
|
|
492
|
+
const error = isSuccess ? undefined : await runParser(requestConfig.parser?.error, response.data)
|
|
469
493
|
return {
|
|
470
494
|
status: response.status,
|
|
471
495
|
data,
|
|
472
|
-
error
|
|
496
|
+
error,
|
|
473
497
|
request: response.config as TRequest,
|
|
474
498
|
response: response as TResponse,
|
|
475
499
|
}
|