solar-core
Advanced tools
| export default Promise; |
+1
-1
| { | ||
| "name": "solar-core", | ||
| "version": "4.3.0", | ||
| "version": "4.3.1", | ||
| "description": "solar core", | ||
@@ -5,0 +5,0 @@ "main": "src/index", |
+92
-38
@@ -16,2 +16,3 @@ /** | ||
| import UseQuery, { GenerateHooks } from './useQuery'; | ||
| import NativePromise from './promise'; | ||
@@ -46,17 +47,15 @@ let Options = {} as NetworkOptions; | ||
| if (Options.mock) { | ||
| // 开启mock服务 | ||
| Network.on('options', (context) => { | ||
| context.base = typeof Options.mock == 'string' ? Options.mock : ''; | ||
| }); | ||
| Network.on('start', (data, context: any) => { | ||
| const segments = Options.base?.replace('//', '@').split('/'); | ||
| const origin = segments?.shift()?.replace('@', '//'); | ||
| const pathname = segments?.join('/'); | ||
| context.url = context.url.indexOf(Options.base) > -1 ? context.url.replace(Options.base, pathname) : pathname + context.url; | ||
| Network.on('start', (data, context: RequestContext) => { | ||
| const meta = new URL(context.url); | ||
| let mockServerBaseApi = ''; | ||
| if (typeof options.mock === 'function') { | ||
| mockServerBaseApi = String(options.mock(context) || ''); | ||
| } else if (typeof options.mock == 'string') { | ||
| mockServerBaseApi = options.mock || ''; | ||
| } | ||
| // 替换成mock代理服务器地址 | ||
| (context as any).url = context.url.replace(meta.origin, mockServerBaseApi || ''); | ||
| // 通知代理服务器,本次请求目标服务器 | ||
| context.headers['x-proxy-api'] = origin; | ||
| context.headers['x-mobile-proxy'] = meta.origin; | ||
| }); | ||
| if (Options.mock2) { | ||
| document.cookie = `cookie-env-api=${Options.mock2};path=/`; | ||
| } | ||
| } | ||
@@ -70,11 +69,43 @@ } | ||
| // TSVQVQKTH | ||
| // 事件顺序: auth --> start --> options ---> sign --> end --> response ---> ... error | ||
| /** | ||
| * 签名事件,可用于进行接口签名 | ||
| * 此阶段可以修改请求数据,请求头等信息 | ||
| */ | ||
| static on(name: 'sign', handler: (url: string, body: string | FormData, headers: Record<string, string>, context: RequestContext) => any): typeof Network | ||
| /** | ||
| * 附加权限数据事件 | ||
| * 此阶段可以修改请求头信息 | ||
| */ | ||
| static on(name: 'auth', handler: (data: any, context: RequestContext) => any): typeof Network | ||
| static on(name: 'options', handler: (options: NetworkBaseOptions) => NetworkBaseOptions | void): typeof Network | ||
| /** | ||
| * 请求配置参数修改事件 | ||
| * 此阶段可以修改请求的配置参数 | ||
| */ | ||
| static on(name: 'options', handler: (context: RequestContext) => NetworkBaseOptions | void): typeof Network | ||
| /** | ||
| * 请求开始事件 | ||
| */ | ||
| static on(name: 'start', handler: (data: any, context: RequestContext) => any): typeof Network | ||
| /** | ||
| * 请求结束事件 | ||
| * 注意: end事件执行时 获取的是clone的原始返回对象 | ||
| */ | ||
| static on(name: 'end', handler: (response: Response | Error, context: RequestContext) => any): typeof Network | ||
| /** | ||
| * 请求返回事件 | ||
| * 当服务端返了回数据且在执行了数据类型格式化后(例如.json() .text() .blob())触发 | ||
| */ | ||
| static on(name: 'response', handler: (response: any, context: RequestContext) => any): typeof Network | ||
| static on(name: 'end', handler: (response: Response | Error, context: RequestContext) => any): typeof Network | ||
| static on(name: 'error', handler: (response: Error) => any): typeof Network | ||
| /** | ||
| * 当请求发生异常时触发 | ||
| * 异常包含以下两种 | ||
| * - 原始http请求异常 例如http.status | ||
| * - 后续处理过程中的任意异常 | ||
| */ | ||
| static on(name: 'error', handler: (response: Error, context: RequestContext) => any): typeof Network | ||
| /** | ||
| * 当请求发生重试时触发 | ||
| * 此事件通常一个请求设置了重试机制才可能会触发 | ||
| */ | ||
| static on(name: 'try', handler: (context: RequestContext) => any): typeof Network | ||
@@ -141,3 +172,3 @@ | ||
| * @param {String} uri 服务端接口url 可以为完整路径或者相对路径 | ||
| * 完整路径例如: https://api.solar-pc/rest/order/submit | ||
| * 完整路径例如: https://api.fluxy-pc/rest/order/submit | ||
| * 相对路径: 相对路径是相对于 Network.config() 配置的 base | ||
@@ -154,3 +185,3 @@ * @param {Object/FormData} 发送的正文数据 ,可以为json对象或者字符串或者FormData | ||
| * @param {String} uri 服务端接口url 可以为完整路径或者相对路径 | ||
| * 完整路径例如: https://api.solar-pc/rest/order/submit | ||
| * 完整路径例如: https://api.fluxy-pc/rest/order/submit | ||
| * 相对路径: 相对路径是相对于 Network.config() 配置的 base | ||
@@ -167,3 +198,3 @@ * @param {Object/FormData} 发送的正文数据 ,可以为json对象或者字符串或者FormData | ||
| * @param uri 服务端接口url 可以为完整路径或者相对路径 | ||
| * 完整路径例如: https://api.solar-pc/rest/order/submit | ||
| * 完整路径例如: https://api.fluxy-pc/rest/order/submit | ||
| * 相对路径: 相对路径是相对于 Network.config() 配置的 base | ||
@@ -175,3 +206,5 @@ * @param data 发送的正文数据 ,可以为json对象或者字符串或者FormData | ||
| any<T = any>(uri: string, data?: any, method?: HttpMethods, headers?: any) { | ||
| const context = new RequestContext(uri, method || 'GET', data, headers); | ||
| const selfOptions = this.selfOptions; | ||
| const mergeOptions = { ...Options, ...selfOptions }; | ||
| const context = new RequestContext(uri, method || 'GET', data, headers, mergeOptions); | ||
| const sharedRes = this.findSharedResponse(context); | ||
@@ -201,3 +234,4 @@ if (sharedRes) { | ||
| private listenTimeout(options: NetworkBaseOptions, context: RequestContext, reject: Function) { | ||
| private listenTimeout(context: RequestContext, reject: Function) { | ||
| const options = context.options; | ||
| if (options.timeout > 0) { | ||
@@ -237,6 +271,5 @@ context.timeoutId = setTimeout(() => { | ||
| const tryRequest2 = this.tryRequest.bind(this, context, reject, resolve); | ||
| const selfOptions = this.selfOptions; | ||
| const mergeOptions = { ...Options, ...selfOptions }; | ||
| const results = tunnel.push('options', mergeOptions).filter((n) => !!n); | ||
| const requestOptions = results.length > 0 ? results[0] : mergeOptions; | ||
| // 配置事件 | ||
| tunnel.push('options', context).filter((n) => !!n); | ||
| const requestOptions = context.options; | ||
| // 请求内容类型 | ||
@@ -253,3 +286,3 @@ const contentType = requestContentType || requestOptions.contentType || 'application/x-www-form-urlencoded'; | ||
| // 超时监听 | ||
| this.listenTimeout(requestOptions, context, reject); | ||
| this.listenTimeout(context, reject); | ||
| const useUrl = combine(url || '', method, data, requestOptions); | ||
@@ -272,2 +305,3 @@ const useBody = adapter(data, headers, method); | ||
| .then((response: Response) => { | ||
| context.response = response.clone(); | ||
| clearTimeout(context.timeoutId); | ||
@@ -281,3 +315,2 @@ // 如果请求被取消掉,则直接返回,不做任何处理 | ||
| const cloneData = response.clone(); | ||
| context.response = response.clone(); | ||
| tunnel.push('end', cloneData, context); | ||
@@ -296,3 +329,3 @@ return isOK ? response : Promise.reject(new BizError(500, 'http:' + response.status, response)); | ||
| if (!tryRequest2()) { | ||
| reject(new BizError(500, 'http:' + response.status, response)); | ||
| reject(new BizError(500, 'TRY_TIMEOUT', response)); | ||
| } | ||
@@ -303,3 +336,5 @@ return; | ||
| return Promise | ||
| // 执行response事件 | ||
| .resolve(this.callResponseEvent(response, context)) | ||
| // 执行attachResponse | ||
| .then((selfResponse) => resolve(selfResponse === undefined ? response : selfResponse)) | ||
@@ -367,3 +402,3 @@ .catch((ex) => { | ||
| */ | ||
| export class AttachResponse<T, R> extends Promise<T> { | ||
| export class AttachResponse<T, R> extends NativePromise<T> { | ||
| /** | ||
@@ -416,3 +451,3 @@ * 是否当前返回,为瞬时共享返回数据 | ||
| if (e && !this.silently) { | ||
| tunnel.push('error', e); | ||
| tunnel.push('error', e, context); | ||
| } | ||
@@ -446,2 +481,16 @@ return data; | ||
| const errorWrapper = (result: any) => { | ||
| /** | ||
| * async function demo1() { | ||
| * // 由于使用了await这里会隐式调用 network.post('ss').then((a)=>a,()=>{ 异常捕获 }) | ||
| * await network.post('ssss'); | ||
| * } | ||
| * async function demo2() { | ||
| * await network.post('ssss').then( | ||
| * ()=> ...成功逻辑, | ||
| * ()=> ...捕获异常, 这里虽然捕获了异常,但是由于上面demo1中 无论await外层是否有try catch,(await)始终会隐式调用then(success,error)导致无法判定最终是否要自定义捕获异常 | ||
| * ) | ||
| * } | ||
| * 由于在await场景下会隐式调用then(success,error),这里为了保证在接口有异常时能正确触发全局error事件, | ||
| * 只要接口处理过程有异常就会触发全局error事件(除非调用了silent来屏蔽本次请求的全局error事件) | ||
| */ | ||
| // 将产生的异常推入数组 | ||
@@ -700,3 +749,3 @@ this.errors.push(this.createError(result)); | ||
| case 'application/json': | ||
| return JSON.stringify(data); | ||
| return toBodyJSONString(data); | ||
| case 'application/x-www-form-urlencoded': | ||
@@ -711,2 +760,9 @@ return formdata(data); | ||
| function toBodyJSONString(data: any) { | ||
| if (typeof data === 'string') { | ||
| return data; | ||
| } | ||
| return JSON.stringify(data); | ||
| } | ||
| /** | ||
@@ -726,5 +782,6 @@ * 合并全局参数 | ||
| } | ||
| const fd = data as FormData; | ||
| Object.keys(merge).forEach((k) => { | ||
| if (!data.get(k)) { | ||
| data.append(k, merge[k]); | ||
| if (!fd.get(k)) { | ||
| fd.append(k, merge[k]); | ||
| } | ||
@@ -742,5 +799,2 @@ }); | ||
| function combine(uri: string, method: string, data: any, requestOptions: any) { | ||
| if (!/(https:|http:|\/\/)/.test(uri) && requestOptions.base) { | ||
| uri = requestOptions.base.replace(/\/$/, '') + '/' + uri?.replace(/^\//, ''); | ||
| } | ||
| data = merge(data, requestOptions.data); | ||
@@ -747,0 +801,0 @@ const m = method.toLowerCase(); |
131344
1.42%52
1.96%3521
1.56%