gloam-http
v1.1.4
Published
基于java-gloam开发框架封装的http基础能力包
Readme
gloam-http 源于日常项目开发中进行的重复性劳动,使用 ts 封装 axios,更加快捷方便的使用方法,支持 filter 过滤器、过滤器排序、token 认证、body 体加密,内置事件系统,支持业务系统的感知处理
版本更新
2024.11.27 -【1.1.4】
- 优化 ras 公钥的获取为 promise,支持异步获取
2024.8.14 -【1.1.3】
- 修复解密结果不正确的异常
2024.8.14 -【1.0.9】
- 修复加密请求中,对于请求体为空的请求无法传输密钥加密响应的问题
2024.3.15 -【1.0.6】发布 🚀
- 基于 ts 封装 axios,实现请求的快捷使用
- 封装 axios 的拦截器,增加 filter 过滤器,支持过滤器排序执行
- 新增事件系统,支持系统内部多种事件的感知
- 增强 axios 创建的配置参数,使用 httpClient 进行创建
- 配置支持同一添加前缀,时间戳等
- 支持 token 认证,采用 aes 加密方式进行传输,需要后端同样适配
- 支持 body 体加密,采用 rsa+aes 的信封加密方式
快速开始
安装
NPM 镜像安装
npm install gloam-http实例
// 基础配置 const options: HttpClientOptions = {}; // 实例化客户端 const httpClient = new HttpClient(options); // 导出使用 export { httpClient };使用
const res = await httpClient.get({url: "http://www.baidu.com"}})
基础配置
1、HttpClientOptions
在实例化 HttpClient 时的配置,属于全局配置,适用于每一个请求
| 配置字段 | 配置说明 | | :------------: | :--------------------------------------------------------: | | requestOptions | 请求基础配置,详见[RequestOptions](# 2、RequestOptions) | | requestToken | 请求 token 基础配置,详见[RequestToken](# 3、RequestToken) | | webEnvelope | 请求体加密基础配置,详见[WebEnvelope](# 4、WebEnvelope) | | filters | 过滤器基础配置,详见[Filter](# 5、Filter) | | event | 事件基础配置,详见[HttpEvent](# 6、HttpEvent) |
案例
const options: HttpClientOptions = {
requestOptions: {},
requestToken: {},
webEnvelope: {},
filters: [],
event: {},
};
// 实例化客户端
const httpClient = new HttpClient(options);
// 导出使用
export { httpClient };2、RequestOptions
配置请求的基本参数
| 配置字段 | 配置说明 | 类型 | 默认 | | :-------------: | :----------------------------------------------------------: | ------- | ----- | | joinParamsToUrl | post 请求的时候添加参数到 url | boolean | false | | formatDate | 格式化提交参数时间,会将时间数据格式化为 YYYY-MM-DD HH:mm:ss | boolean | false | | joinPrefix | 默认将 prefix 添加到 url,prefix 配置为 urlPrefix | boolean | false | | urlPrefix | 接口拼接地址 | string | ‘’ | | apiUrl | 接口地址 | string | ‘’ | | joinTime | 是否加入时间戳,会在 GET 请求后面加上时间戳参数 | boolean | true |
案例
const options: HttpClientOptions = {
requestOptions: {
joinParamsToUrl: true,
formatDate: true,
joinPrefix: true,
urlPrefix: "service-gateway",
apiUrl: "http://127.0.0.1",
joinTime: true,
},
};
// 实例化客户端
const httpClient = new HttpClient(options);
// 导出使用
export { httpClient };3、RequestToken
请求携带 token 的相关配置
| 配置字段 | 配置说明 | 类型 | 默认 | | :------------------: | :-------------------: | :-----: | :---: | | enable | 是否开启 token 认证 | boolean | false | | authenticationScheme | 认证信息前缀 | string | "" | | aesKey | 认证信息 aes 加密密钥 | string | "" | | split | 认证信息 token 分割 | string | "" |
案例
const options: HttpClientOptions = {
requestToken: {
enable: true,
authenticationScheme: "bearer",
aesKey: "485s8s8d4df8df1f8aqw5f8f49d5ew78",
split: "-SPLIT-",
},
};
// 实例化客户端
const httpClient = new HttpClient(options);
// 导出使用
export { httpClient };4、WebEnvelope
请求体加密参数
| 配置字段 | 配置说明 | 类型 | 默认 | | :------: | :--------------------: | :-----: | :---: | | enable | 是否开启开启请求体加密 | boolean | false |
案例
const options: HttpClientOptions = {
webEnvelope: {
enable: true,
},
};
// 实例化客户端
const httpClient = new HttpClient(options);
// 导出使用
export { httpClient };5、Filter
请求过滤器
| 配置字段 | 配置说明 | 类型 | 默认 | | :------: | :------------------------: | :------------: | :--: | | filters | 配置实现 Filter 接口的对象 | Array<Filter> | [ ] |
案例
const options: HttpClientOptions = {
filters: [
// 外部实现的filter
MyFilter,
// 内部实现的filter
{
order(): number {
return 0;
},
},
],
};
// 实例化客户端
const httpClient = new HttpClient(options);
// 导出使用
export { httpClient };6、HttpEvent
请求事件系统
| 配置字段 | 配置说明 | 类型 | 默认 | | :------: | :-------------------------: | :---: | :--: | | event | 配置实现 Event 抽象类的对象 | Event | { } |
案例
const options: HttpClientOptions = {
event: {
onNetworkError(error: Error, defaultMessage: string): void {
console.log("网络错误了", error, defaultMessage);
},
},
};
// 实例化客户端
const httpClient = new HttpClient(options);
// 导出使用
export { httpClient };Filter
过滤器的实现是基于 Axios 的请求响应拦截原理,在其基础上增强了顺序编排,在 Gloam-Http 中存在三个默认的执行器
1、接口
export interface Filter {
/**
* @description: 请求拦截器
*/
request?: (
config: InternalRequestConfig<any>,
options: HttpClientOptions
) => InternalRequestConfig<any>;
/**
* @description: 响应拦截器
*/
response?: (
res: AxiosResponse<Result> | Result,
options: HttpClientOptions
) => AxiosResponse<Result> | Result;
/**
* @description: 请求之前的拦截器错误处理
*/
requestCatch?: (error: Error, options: HttpClientOptions) => void;
/**
* @description: 请求之后的拦截器错误处理
*/
responseCatch?: (
axiosInstance: AxiosInstance,
error: Error,
options: HttpClientOptions
) => Promise<Error>;
/**
* @description: 执行顺序
*/
order: () => number;
}2、默认拦截器
DefaultFilter
执行顺序为 0
【请求过滤器】:主要负责对请求的基础配置,配置 RequestOptions 参数以及 Token 相关参数
【响应过滤器】:主要负责监听响应头中携带的 Token 信息,通过事件模块进行业务的感知
EncryptFilter
执行顺序为 1
【请求过滤器】:主要负责对需要加密的请求进行数据加密操作
【响应过滤器】:主要负责对响应的数据进行解密
TimeFilter
执行顺序为 1
【请求过滤器】:主要负责对请求中数据为‘createTimeStart’和‘createTimeEnd’的字段进行时间处理,格式为时间戳
3、实现案例
export const timeFilter: Filter = {
order(): number {
return 2;
},
request(
config: InternalRequestConfig<any>,
_options: HttpClientOptions
): InternalRequestConfig<any> {
// 处理get请求的时间格式,统一变成时间戳
const params = config.params;
if (!params) {
return config;
}
if (params.createTimeStart) {
params.createTimeStart = format2Timestamp(params.createTimeStart);
}
if (params.createTimeEnd) {
params.createTimeEnd = format2Timestamp(params.createTimeEnd);
}
return config;
},
};Event
通过事件系统,可以让业务系统感知到请求的节点,配合完成整个请求链路
1、抽象类
export abstract class HttpEvent {
/**
* 在状态错误的请况下,状态不为200
*/
onStatusError?: (error: Error, statusCode: number, massage: string) => void;
/**
* 请求超时错误
*/
onTimeoutError?: (error: Error, defaultMessage: string) => void;
/**
* 网络错误
*/
onNetworkError?: (error: Error, defaultMessage: string) => void;
/**
* 请求结果感知,可以全局拦截到请求结果,进行预处理
*/
webResultAware?: (result: Result, url?: string) => void;
/**
* 响应token感知,如果响应存在token,则会进行感知
*/
authorizationTokenAware?: (token: string) => void;
/**
* 注入token,在每个请求发送时会调用此事件获取token
*/
authorizationTokenInfuse?: () => string;
/**
* 注入rsa加密公钥,请求加解密时必须传入
* requestConfig: HttpClientInternalRequestConfig
*/
rsaPublicKeyInfuse?: () => string;
}Token
1、实现原理
在进行携带 token 时,会先调用事件系统的‘authorizationTokenInfuse( )’方法获取到由业务系统保管的 token
请求中会生成 nonce 字段(由配置的 aesKey 加密)放入请求头 nonce
请求会将 token 按照一定顺序拼接,然后使用配置的 aesKey 加密,放入请求头 Authorization
加密排列:nonce + splip(配置的分隔符) + Date.now().toString() + splip(配置的分隔符) + token;
2、结合事件系统进行 token 的获取与注入
在后端生成 token 后,应该放置 Authorization 请求头,gloam-http 会解析每次响应的 token,如果存在则会调用事件系统的 authorizationTokenAware( )方法,此时业务系统应该将 token 存入本地缓冲,并在事件系统的 authorizationTokenInfuse( )方法中将 token 重新交与 gloam-http
WebEnvelope
1、原理
请求加密的使用需要后端配合提供 RSA 公钥或获取公钥的接口,在事件系统中由 rsaPublicKeyInfuse( )方法告知 gloam-http
gloam-http 在发送请求时,将会随机生成 aesKey,由 aesKey 对数据进行加密,然后由后端提供的公钥将 aesKey 进行加密
请求后端的格式
{ "data": "由aes加密的数据", "key": "由rsa加密的aesKey" }
2、使用
在之前的创建实例的配置中,存在是否开启加密的参数,需要注意的是该参数为 true 时表示加密功能可用,不是全部请求加密,如果为 false 则表示全局不使用加密,在局部配置也是无效的
GET 请求或者 body 中为空时不会进行加密
在创建实例时开启加密功能的情况下,如下使用:
const res = await httpClient.get({ url: "http://www.baidu.com", encrypt: true, data: { a: "传输中会被加密", }, });
参与贡献
- Fork 本仓库
- 新建 Feat_xxx 分支
- 提交代码
- 新建 Pull Request
【注】:commit 时请将修改信息填写清楚
