企业🤖AI Agent构建引擎,智能编排和调试,一键部署,支持私有化部署方案 广告
MKOA内置两个对Request.js进行代理函数,方便处理一般API请求。(学习:koa-grace项目) ### proxy——数据代理 修改config.js文件,开启代理助手。 ~~~ ,apiProxy_open:true ,apiProxy_prefix:{} //API调用配置{servicName:prefix} ~~~ 支持两种数据代理场景: 1. 单纯的数据代理,任意请求到后端接口,然后返回json数据(也包括文件流请求到后端,后端返回json数据); 2. 文件代理,请求后端接口,返回一个文件(例如验证码图片); 下面逐一介绍两种代理模式的使用方法。 #### 1、 数据代理 数据代理可以在控制器中使用`this.proxy`方法: ``` this.proxy(object|string,[opt]) ``` ##### 使用方法 `this.proxy` 方法返回的是一个Promise,所以这里你可以根据当前Controller的类型使用`async/await`或者`Generator`实现异步并发。例如: **async/await:** ``` exports.demo = async function () { await this.proxy({ /* ... */ }) } ``` **Generator:** ``` exports.demo = function * () { yield this.proxy({ /* ... */ }) } ``` 为了使语法更简便,可以在执行`this.proxy`之后,直接在上下文中的`backData`字段中获取到数据。例如: ``` exports.demo = async function () { await this.proxy({ userInfo:'github:post:user/login/oauth/access_token?client_id=****', otherInfo:'github:other/info?test=test', }) console.log(this.backData); /** * { * userInfo : {...}, * otherInfo : {...} * } */ } ``` `Generator`方法亦然。 此外,如果要获取proxy的请求头信息,你可以在proxy方法返回的内容中获取到,例如: ```javascript exports.demo = async function (){ let res = await this.proxy({ userInfo:'github:post:user/login/oauth/access_token?client_id=****', otherInfo:'github:other/info?test=test', }); console.log(res); /** * { * userInfo : { * statusCode: {...} // 返回http status code * request: {...} // 请求体 * headers: {...} // 响应头信息 * body: {...} // 未处理的response body * }, * otherInfo : {...} * } */ } ``` ##### 使用场景一:多个数据请求的代理 可以发现,上文的案例就是多个数据同时请求的代理方案,这里也就是**异步并发**获取数据的实现。使用`this.proxy`方法实现多个数据异步并发请求非常简单: ```javascript exports.demo = async function (){ await this.proxy({ userInfo:'github:post:user/login/oauth/access_token?client_id=****', otherInfo:'github:other/info?test=test', }); console.log(this.backData); /** * { * userInfo : {...}, * otherInfo : {...} * } */ } ``` 然后,proxy的结果会默认注入到上下文的`this.backData`对象中。 ##### 使用场景二:单个数据请求的代理 如果只是为了实现一个接口请求代理,可以这么写: ```javascript exports.demo = async function (){ await this.proxy('github:post:user/login/oauth/access_token?client_id=****'); } //post不指定前置配置及自定义参数 exports.demo = async function (){ await this.proxy(':post:user/login/oauth/access_token?client_id=****',{form: {code: 123}}); } ``` 这样proxy请求返回的数据体会直接赋值给`this.body`,也就是将这个请求直接返回给客户端。 ##### 说明 `github:post:user/login/oauth/access_token?client_id=****`说明如下: * `github`: 为在`config.js`的 `apiProxy_prefix` 对象中进行配置; * `post` : 为数据代理请求的请求方法,该参数可以不传,默认为`get` * `path`: 后面请求路径中的query参数会覆盖当前页面的请求参数(this.query),将query一同传到请求的接口 * 你也可以写完整的路径:`{userInfo:'https://api.github.com/user/login?test=test'}` 另外,`this.proxy`的形参说明如下: | 参数名 | 类型 | 默认 | 说明| | --- | --- | --- | | `dest` | `Object` | `this.backData` | 指定接收数据的对象,默认为`this.backData` | | `conf` | `Obejct` | `{}` | this.proxy使用[Request.js](https://github.com/request/request)实现,此为传给request的重置配置(你可以在这里设置接口超时时间:`conf: { timeout: 25000 }`)| |`form` | `Object` | `{}` | 指定post方法的post数据,默认为当前页面的post数据,这里的数据content-type会根据当前请求的类型指定| | `headers` | `Object` | `{}` | 指定当前请求的headers| 关于this.proxy方法还有很多有趣的细节,推荐有兴趣的同学看源码:https://github.com/xiongwilee/koa-grace/middleware/proxy #### 2、 文件代理 文件代理可以在控制器中使用`this.fetch`方法: ``` this.fetch(string) ``` 文件请求代理也很简单,比如如果需要从github代理一个图片请求返回到浏览器中,参考:http://feclub.cn/user/avatar?img=https://avatars.githubusercontent.com/u/1962352?v=3 , 或者要使用导出文件的功能: ```javascript exports.avatar = async function (){ await this.fetch(imgUrl); } ``` 这里需要注意的是:**在this.fetch方法之后会直接结束response, 不会再往其他中间件执行**。