引言
集成服务端接口应该是每个前端最熟悉的领域之一了,但是你会发现每次集成接口都需要按以下操作:
-> 收到后端交付通知
-> 查看API文档
-> 定义API调用函数
-> 编写typescript响应(ts项目)
-> 在指定位置使用接口
-> 引入接口
-> 编写复杂的请求逻辑
即使你使用了openapi自动生成方案,也只是省去了两个流程。
-> 收到后端交付通知
-> 查看API文档
-> 定义API调用函数❌
-> 编写typescript响应(ts项目)❌
-> 在指定位置使用接口
-> 引入接口
-> 编写复杂的请求逻辑
那么,如何一步到位呢?接下来我们就一起来探讨一下如何简化成只需一个步骤。
此时我们会用到一个叫alova的下一代请求工具,目前github的stars已经到达3k(Github仓库地址),并且在 soybean-admin(10k+ stars)、naive-ui-admin(5k+ stars)等高人气的管理系统模板中使用了alova作为请求方案。
让我们一起来看看它的神奇之处吧。
alova到底是个什么东西
alova是一个流程简化的下一代请求工具,它主要通过预先封装好的针对各种请求场景的请求模块(俗称请求策略),以及更现代化的openapi解决方案极致地将api集成简化到只需 1 个步骤,帮你在接口处理方面节约大部分的时间和精力,像下面这样,带❌部分的流程全部自动化了。
基本可以达到以下的效果
-> 收到后端交付通知❌
-> 查看API文档❌
-> 定义API调用函数❌
-> 编写typescript响应(ts项目)❌
-> 在指定位置使用接口
-> 引入接口❌
-> 编写复杂的请求逻辑❌
它的主要特性如下:
- 简单易用,并且学习成本更低。
- 更先进的 openAPI 解决方案,直接扔掉中间的API文档吧,对,你没看错。
- 搭配客户端技术和请求库,
react/vue/svelte/solid/next/nuxt/sveltkit/solid-start/uniapp/taro/...+fetch/XMLHttpRequest/axios/... - 搭配服务端技术和请求库,
nodejs/deno/bun/...+fetch/XMLHttpRequest/axios/... - 15+ 高性能的请求策略应对复杂的请求场景,帮助你快速开发性能更好的应用。
你也可以前往alova文档查看详细
下面来看下,我们如何通过alova来达到上面的效果。
为了让大家更直观地了解,下面会通过实际的业务开发需求为例,并且分别会在客户端和服务端两个场景下的请求中,将常用的请求方案和alova进行对比。
客户端的使用场景下
在客户端场景下,我们与相关的老牌js库tanstack-query、axios在不同的请求场景下进行对比,以vue3为例。
完整的分页请求
完整的分页请求场景下不仅需要考虑翻页的实现,还需要考虑数据查询、数据的新增删除和编辑等操作,我们来分别看一看各种方案的实现对比,对比代码只保留了js部分。
你也可以放大图片查看具体的实现。
可见alova的代码量是最少的,alova的usePagination不仅自带了对数据查询的功能集成、列表项的操作函数,还可以通过它的缓存特性来实现对下一页数据的预加载,提升用户翻页的流畅体验。
带草稿的表单提交
带草稿的表单项,即在未提交时即使刷新也会保持上一次的填写状态,提升了用户体验。我们也来看下各种方案的实现对比。
无感刷新Token
无感刷新Token在权限系统中需要频繁实现的功能,在tanstack-query和axios中都需要自行实现,而alova的Token认证模块提供了开箱即用的无感刷新特性,Token认证模块的具体特性如下:
- 统一维护 Token 身份认证的所有代码,包括登录、登出、token 附带、token 刷新等;
- 支持在客户端和服务端验证 token 过期,并无感刷新 token;
- 依赖 token 的请求自动等待 token 刷新完成再请求;
- 使用元数据设置请求身份;
- 自动放行不依赖 token 的访客请求;
我们来使用它实现token无感刷新和登录相关的代码维护,当接口返回401时刷新token。
const { onAuthRequired, onResponseRefreshToken } = createServerTokenAuthentication({
// 拦截登录请求,保存登录信息
async login(response) {
const data = await response.clone().json();
accessToken.value = data.accessToken;
refreshToken.value = data.refreshToken;
},
// 拦截登出请求,删除登录信息
logout() {
accessToken.value = '';
refreshToken.value = '';
},
// 对需要权限的接口赋值token
assignToken(method) {
method.config.headers.Authorization = accessToken.value;
},
refreshTokenOnSuccess: {
// 判断token是否过期
async isExpired(response) {
const data = await response.clone().json();
return data.code === 401;
},
// 当token过期时刷新token
async handler() {
const refreshInfo = await handleTokenRefresh(refreshToken.value);
accessToken.value = refreshInfo.accessToken;
refreshToken.value = refreshInfo.refreshToken;
}
}
});
const alovaInstance = createAlova({
statesHook: vueHook,
requestAdapter: adapterFetch(),
beforeRequest: onAuthRequired(method => {
// ...原请求前拦截器
}),
responded: onResponseRefreshToken((response, method) => {
//...原响应成功拦截器
return response.json();
})
});
验证码发送
接下来再对比一下验证码发送的实现,用户先输入邮箱并发送获取验证码,然后将邮箱和验证码一起提交到服务端。
由于篇幅问题,这里只举这几个例子了,完整的客户端请求策略可以点此查看,同时,alova也提供了丰富的示例,可以看到所有的实现效果。
简单请求
除了上面使用各种请求策略的便利外,alova也可以像axios一样以promise的方式进行请求,用法也与axios基本相同。
const res = await alova.Get('/user', {
params: {
id: 1
}
});
服务端的使用场景下
接下来我们再看看alova在服务端中的使用,各种客户端的请求策略是没办法用了,只能以简单请求的方式直接发送请求了。
但是!!!
alova还提供了基于服务端的请求策略,称之为 server hooks,它们是 method 实例的装饰函数,并且可以多个Server hooks组合使用。这些是例如tanstack-query、swrjs和ahooks等无法实现的。
我们来看两个实际业务中的例子:
请求重试
请求重试5次。
const response = await retry(alova.Get('/api/user'), {
retry: 5
});
验证码发送和校验
你还可以在服务端通过server hooks快速实现验证码发送和验证功能,并且验证码的查询验证可以使用集群模式,单服务器集群,或redis。
以下特性将在3.3.0中实现。
// ----- captchaProvider.js -----
// 创建一个验证码provider
const { validateCaptcha, sendCaptcha } = createCaptchaProvider({
/**
* 可再次发送验证码的间隔时间
*/
resetTime: 60 * 1000,
/**
* 配置集群模式
*/
store: createPSCAdapter(NodeSyncAdapter()),
});
export validateCaptcha;
export sendCaptcha;
// ----- captcha.js -----
import { sendCaptcha } from './captchaProvider';
// 发送验证码,自动生成特定规则的code
// 发送成功后将验证码存储在store中,可通过validateCaptcha直接验证
await sendCaptcha(
(code, email) => alova.Post('/api/captcha', {
code,
email
}),
{
key: email // 唯一key,在验证时查找code,这里使用email
}
);
// ----- validate.js -----
import { verifyCaptcha } from './captchaProvider';
// 验证码校验
const isCodeValidated = await validateCaptcha(codeFromUser, key);
你还可以通过组合retry和sendCaptcha来实现带重试效果的验证码发送动作。
await sendCaptcha(
// --> 在这里直接使用retry包裹method实例。
(code, email) => retry(alova.Post('/api/captcha', {
code,
email
})),
{
key: email // 唯一key,在验证时查找code,这里使用email
}
);
你也可以在 alova示例 中选择Server体验实现效果。
更先进的 openAPI 解决方案
alova 的开发工具能够帮你自动化大部分的集成流程:
- 通过openapi文件同时生成三项信息:
- API 调用代码。
- 每个 API 的 TypeScript 类型。
- 每个 API 的详尽文档。
- 配合alova的vscode扩展,定时检查API的更新情况,不再依赖服务端开发来通知你。
- 配合alova的vscode扩展,你现在只需要在编辑器中就能实现查找想要的API,然后在编辑器中一边参照 API 参数表快速完成参数传递,不再需要来回切换传统的API文档看信息再复制的繁琐操作了,感受不一样的 API 集成体验。
你可以前往更现代的openAPI解决方案中查看演示视频。
最后
如果觉得alova还不错,真诚希望你可以尝试体验一下,也可以给我们来一个免费的github stars。
访问alovajs的官网查看更多详细信息:alovajs官网。
有兴趣可以加入我们的交流社区,在第一时间获取到最新进展,也能直接和开发团队交流,提出你的想法和建议。
有任何问题,你可以加入以下群聊咨询,也可以在github 仓库中发布 Discussions,如果遇到问题,也请在github 的 issues中提交,我们会在最快的时间解决。
同时也欢迎贡献你的一份力量,请移步贡献指南。