diff --git a/packages/axios/src/index.ts b/packages/axios/src/index.ts index c29d9d2b..cfbde18e 100644 --- a/packages/axios/src/index.ts +++ b/packages/axios/src/index.ts @@ -3,6 +3,7 @@ import type { AxiosResponse, CreateAxiosDefaults, InternalAxiosRequestConfig } f import axiosRetry from 'axios-retry'; import { nanoid } from '@sa/utils'; import { createAxiosConfig, createDefaultOptions, createRetryOptions } from './options'; +import { transformResponse } from './shared'; import { BACKEND_ERROR_CODE, REQUEST_ID_KEY } from './constant'; import type { CustomAxiosRequestConfig, @@ -52,6 +53,8 @@ function createCommonRequest( async response => { const responseType: ResponseType = (response.config?.responseType as ResponseType) || 'json'; + await transformResponse(response); + if (responseType !== 'json' || opts.isBackendSuccess(response)) { return Promise.resolve(response); } diff --git a/packages/axios/src/shared.ts b/packages/axios/src/shared.ts index 7afd32b1..1bb68f0b 100644 --- a/packages/axios/src/shared.ts +++ b/packages/axios/src/shared.ts @@ -1,4 +1,5 @@ import type { AxiosHeaderValue, AxiosResponse, InternalAxiosRequestConfig } from 'axios'; +import type { ResponseType } from './type'; export function getContentType(config: InternalAxiosRequestConfig) { const contentType: AxiosHeaderValue = config.headers?.['Content-Type'] || 'application/json'; @@ -26,3 +27,53 @@ export function isResponseJson(response: AxiosResponse) { return responseType === 'json' || responseType === undefined; } + +export async function transformResponse(response: AxiosResponse) { + const responseType: ResponseType = (response.config?.responseType as ResponseType) || 'json'; + if (responseType === 'json') return; + + const isJson = response.headers['content-type']?.includes('application/json'); + if (!isJson) return; + + if (responseType === 'blob') { + await transformBlobToJson(response); + } + + if (responseType === 'arrayBuffer') { + await transformArrayBufferToJson(response); + } +} + +export async function transformBlobToJson(response: AxiosResponse) { + try { + let data = response.data; + + if (typeof data === 'string') { + data = JSON.parse(data); + } + + if (Object.prototype.toString.call(data) === '[object Blob]') { + const json = await data.text(); + data = JSON.parse(json); + } + + response.data = data; + } catch {} +} + +export async function transformArrayBufferToJson(response: AxiosResponse) { + try { + let data = response.data; + + if (typeof data === 'string') { + data = JSON.parse(data); + } + + if (Object.prototype.toString.call(data) === '[object ArrayBuffer]') { + const json = new TextDecoder().decode(data); + data = JSON.parse(json); + } + + response.data = data; + } catch {} +}