From f7c380c9fa5b1f0b22da0dd32789240a34c8da82 Mon Sep 17 00:00:00 2001 From: life <36911513+Ares-Chang@users.noreply.github.com> Date: Sun, 31 Dec 2023 18:29:09 +0800 Subject: [PATCH] docs: Documentation based on Vitepress (#45) * chore: init docs * docs: add logo & Adjust docs config * docs: document migration and some modifications * docs: move some files * docs: update docs index page details * docs: adjust indev page hero theme style --- .gitignore | 3 + docs/.vitepress/config.ts | 72 +++ docs/advanced/cancellation.md | 89 ++++ docs/advanced/composition-api.md | 13 + docs/advanced/enhancements.md | 56 +++ docs/advanced/handling-errors.md | 67 +++ docs/advanced/interceptors.md | 114 +++++ docs/advanced/ts-support.md | 94 ++++ docs/guide/api-intro.md | 41 ++ docs/guide/config-defaults.md | 40 ++ docs/guide/example.md | 85 ++++ docs/guide/instance.md | 26 ++ docs/guide/introduction.md | 20 + docs/guide/quick-start.md | 29 ++ docs/guide/req-config.md | 197 +++++++++ docs/guide/res-schema.md | 70 +++ docs/index.md | 63 +++ docs/other/build.md | 61 +++ docs/other/thank.md | 13 + docs/other/why-not.md | 40 ++ docs/public/logo.png | Bin 0 -> 7519 bytes package.json | 6 +- pnpm-lock.yaml | 725 ++++++++++++++++++++++++++++++- 23 files changed, 1909 insertions(+), 15 deletions(-) create mode 100644 docs/.vitepress/config.ts create mode 100644 docs/advanced/cancellation.md create mode 100644 docs/advanced/composition-api.md create mode 100644 docs/advanced/enhancements.md create mode 100644 docs/advanced/handling-errors.md create mode 100644 docs/advanced/interceptors.md create mode 100644 docs/advanced/ts-support.md create mode 100644 docs/guide/api-intro.md create mode 100644 docs/guide/config-defaults.md create mode 100644 docs/guide/example.md create mode 100644 docs/guide/instance.md create mode 100644 docs/guide/introduction.md create mode 100644 docs/guide/quick-start.md create mode 100644 docs/guide/req-config.md create mode 100644 docs/guide/res-schema.md create mode 100644 docs/index.md create mode 100644 docs/other/build.md create mode 100644 docs/other/thank.md create mode 100644 docs/other/why-not.md create mode 100644 docs/public/logo.png diff --git a/.gitignore b/.gitignore index 6ee834c..cbe8a96 100644 --- a/.gitignore +++ b/.gitignore @@ -175,3 +175,6 @@ dist_ssg # Android *.keystore + +# Vitepress +cache diff --git a/docs/.vitepress/config.ts b/docs/.vitepress/config.ts new file mode 100644 index 0000000..aaecb8a --- /dev/null +++ b/docs/.vitepress/config.ts @@ -0,0 +1,72 @@ +import { defineConfig } from 'vitepress'; + +export default defineConfig({ + title: 'Uni Network', + description: '为 uni-app 打造的基于 Promise 的 HTTP 客户端。', + head: [ + ['link', { rel: 'icon', type: 'image/png', href: '/logo.png' }], + ['meta', { name: 'og:type', content: 'website' }], + ['meta', { name: 'og:locale', content: 'zh-cn' }], + ['meta', { name: 'og:site_name', content: 'Uni Network' }], + [ + 'meta', + { + name: 'og:image', + content: + 'https://github.com/uni-helper/website/raw/main/.github/assets/uni-helper-banner.png', + }, + ], + ], + themeConfig: { + logo: { src: '/logo.png', width: 24, height: 24 }, + nav: [ + { text: '指南', link: '/guide/introduction' }, + { + text: '更新日志', + link: 'https://github.com/uni-helper/uni-network/tree/main/CHANGELOG.md', + }, + ], + + sidebar: [ + { + text: '指南', + items: [ + { text: '介绍', link: '/guide/introduction' }, + { text: '安装', link: '/guide/quick-start' }, + { text: '示例', link: '/guide/example' }, + ], + }, + { + text: 'Un Api', + items: [ + { text: 'API', link: '/guide/api-intro' }, + { text: 'Un 实例', link: '/guide/instance' }, + { text: '请求配置', link: '/guide/req-config' }, + { text: '响应结构', link: '/guide/res-schema' }, + { text: '默认配置', link: '/guide/config-defaults' }, + ], + }, + { + text: '进阶', + items: [ + { text: '拦截器', link: '/advanced/interceptors' }, + { text: '错误处理', link: '/advanced/handling-errors' }, + { text: '取消请求', link: '/advanced/cancellation' }, + { text: 'TS 支持', link: '/advanced/ts-support' }, + { text: '高级功能', link: '/advanced/enhancements' }, + { text: '组合式函数', link: '/advanced/composition-api' }, + ], + }, + { + text: '其它', + items: [ + { text: '构建', link: '/other/build' }, + { text: '为什么不是...?', link: '/other/why-not' }, + { text: '致谢', link: '/other/thank' }, + ], + }, + ], + + socialLinks: [{ icon: 'github', link: 'https://github.com/uni-helper/uni-network' }], + }, +}); diff --git a/docs/advanced/cancellation.md b/docs/advanced/cancellation.md new file mode 100644 index 0000000..a9e4d62 --- /dev/null +++ b/docs/advanced/cancellation.md @@ -0,0 +1,89 @@ +# 取消请求 + +## AbortController + +支持使用 [AbortController](https://developer.mozilla.org/en-US/docs/Web/API/AbortController) 取消请求。要使用 AbortController,请使用 [这个 polyfill](https://github.com/mysticatea/abort-controller)。 + +::: code-group + +```sh [npm] +npm add -D abort-controller@^3.0.0 +``` + +```sh [pnpm] +pnpm add -D abort-controller@^3.0.0 +``` + +```sh [yarn] +yarn add -D abort-controller@^3.0.0 +``` + +::: + +```ts +import AbortController from 'abort-controller/dist/abort-controller'; +// ❌ 错误做法 1 +// import AbortController from 'abort-controller'; +// ❌ 错误做法 2 +// import 'abort-controller/polyfill'; + +const controller = new AbortController(); + +un.get('/foo/bar', { + signal: controller.signal, +}).then(function (response) { + //... +}); +// 取消请求 +controller.abort(); +``` + +## CancelToken + +你也可以使用 `CancelToken`。 + +```ts +const CancelToken = un.CancelToken; +const source = CancelToken.source(); + +un.get('/user/12345', { + cancelToken: source.token, +}).catch(function (error) { + if (un.isUnCancel(error)) { + console.log('Request canceled', error.message); + } else { + // 处理错误 + } +}); + +un.post( + '/user/12345', + { + name: 'new name', + }, + { + cancelToken: source.token, + }, +); +// 取消请求(信息是可选的) +source.cancel('Operation canceled by the user.'); +``` + +你也可以通过向 `CancelToken` 构造函数传递一个执行函数来创建一个 `CancelToken` 实例。 + +```ts +const CancelToken = un.CancelToken; +let cancel; + +un.get('/user/12345', { + cancelToken: new CancelToken(function executor(c) { + cancel = c; + }), +}); + +// 取消请求 +cancel(); +``` + +> 注意:你可以用同一个 `CancelToken` / `AbortController` 取消几个请求。 +> 如果在发起请求的时候已经取消请求,那么该请求就会被立即取消,不会真正发起请求。 diff --git a/docs/advanced/composition-api.md b/docs/advanced/composition-api.md new file mode 100644 index 0000000..44b38ae --- /dev/null +++ b/docs/advanced/composition-api.md @@ -0,0 +1,13 @@ +# 组合式函数 + +如果你还不了解组合式函数,请先阅读 [组合式 API 常见问答](https://cn.vuejs.org/guide/extras/composition-api-faq.html) 和 [组合式函数](https://cn.vuejs.org/guide/reusability/composables.html)。 + +我们使用 [vue-demi](https://github.com/vueuse/vue-demi) 来同时支持 `vue2` 和 `vue3`。请先阅读它的使用说明。 + +你需要从 `@uni-helper/uni-network/composables` 中导入组合式函数。 + +```typescript +import { useUn } from '@uni-helper/uni-network/composables'; +``` + +`useUn` 的用法和 [useAxios](https://vueuse.org/integrations/useaxios/) 几乎完全一致。这里不再赘述。 diff --git a/docs/advanced/enhancements.md b/docs/advanced/enhancements.md new file mode 100644 index 0000000..c98b19b --- /dev/null +++ b/docs/advanced/enhancements.md @@ -0,0 +1,56 @@ +# 高级功能 + +对于缓存、去重、重试的高级功能,建议结合 [@tanstack/query](https://tanstack.com/query/)、[swrv](https://docs-swrv.netlify.app/)、[vue-request](https://www.attojs.com/)、[alova](https://alova.js.org/zh-CN/) 等库使用。 + +如果你不希望引入过多的库导致占用体积过多,你也可以参考以下内容以实现部分高级功能。 + +## 缓存 + +请参考 [Axios 如何缓存请求数据](https://juejin.cn/post/6974902702400602148)。 + +## 去重 + +请参考 [Axios 如何取消重复请求](https://juejin.cn/post/6955610207036801031) 和 [Axios 如何取消重复请求?取消重复请求方法有哪几种?](https://apifox.com/apiskills/axios-repeated-request/)。 + +## 重试 + +请参考 [Axios 如何实现请求重试?](https://juejin.cn/post/6973812686584807432)。 + +## 响应失败不抛出错误 + +::: warning ⚠️ 注意: +这可能不是一个好主意。请慎重考虑。 +::: + +在某些情况下,你可能不希望响应失败抛出错误,这时候可以使用响应拦截器来处理。 + +```typescript +// 添加响应拦截器 +un.interceptors.response.use( + (response) => response, + // 直接返回错误,不再需要使用 catch 来捕获 + // 需要注意返回值可能是 UnError 类型 + (error) => error, +); +``` + +## 无感刷新登录态 + +在某些情况下,你可能希望无感刷新登录态,避免当前登录态过期后用户手动登录。 + +如果你有一个可以使用过期登录态换取新鲜登录态的接口,请参考 [uni-ajax - FAQ - 无感刷新 Token](https://uniajax.ponjs.com/guide/question#%E6%97%A0%E6%84%9F%E5%88%B7%E6%96%B0-token)。 +该部分代码实现略经修改也适用于使用双登录态的认证系统。 + +::: warning ⚠️ 注意: +这类接口并非十分安全。请慎重考虑。 +::: + +如果你正在使用一个使用双登录态的认证系统,请参考 [项目中前端如何实现无感刷新 token!](https://juejin.cn/post/7254572706536734781) 和 [基于 Axios 封装一个完美的双 token 无感刷新](https://juejin.cn/post/7271139265442021391)。 + +## 全局请求加载 + +请参考 [uni-ajax - FAQ - 配置全局请求加载](https://uniajax.ponjs.com/guide/question#%E9%85%8D%E7%BD%AE%E5%85%A8%E5%B1%80%E8%AF%B7%E6%B1%82%E5%8A%A0%E8%BD%BD)。 + +::: warning ⚠️ 注意: +这类做法不适用于局部加载展示。 +::: diff --git a/docs/advanced/handling-errors.md b/docs/advanced/handling-errors.md new file mode 100644 index 0000000..7f66753 --- /dev/null +++ b/docs/advanced/handling-errors.md @@ -0,0 +1,67 @@ +# 错误处理 + +`uni-network` 默认把每一个返回的状态代码不在 `2xx` 范围内的响应视为错误。 + +```ts +un.get('/user/12345').catch((error) => { + if (error.response) { + // 请求成功发出且服务器也响应了状态码,但状态代码超出了 2xx 的范围 + console.log(error.response.data); + console.log(error.response.status); + console.log(error.response.headers); + } else if (error.task) { + // 请求已经成功发起,但没有收到响应 + // `error.task` 是 task 实例 + console.log(error.task); + } else { + // 发送请求时出了点问题 + console.log('Error', error.message); + } + console.log(error.config); +}); +``` + +使用 `validateStatus` 配置选项,可以自定义抛出错误的 HTTP code。 + +```ts +un.get('/user/12345', { + validateStatus: (status) => { + return status < 500; // 处理状态码小于 500 的情况 + }, +}); +``` + +如果你追求语义化,可以使用导出的和挂载的状态码、[statuses](https://github.com/jshttp/statuses)、[http-status-codes](https://github.com/prettymuchbryce/http-status-codes) 或 [node-http-status](https://github.com/adaltas/node-http-status)。 + +```ts +import { HttpStatusCode } from '@uni-helper/uni-network'; + +un.get('/user/12345', { + validateStatus: (status) => { + return status < HttpStatusCode.InternalServerError; // 处理状态码小于 500 的情况 + // return status < un.HttpStatusCode.InternalServerError; // 也可以使用挂载在 un 上的状态码 + }, +}); +``` + +使用 `toJSON` 可以获取更多关于 HTTP 错误的信息。 + +```ts +un.get('/user/12345').catch((error) => { + console.log(error.toJSON()); +}); +``` + +如果需要针对 `UnError` 和非 `UnError` 做处理,可以使用导出的 `isUnError` 方法判断。 + +```ts +import { isUnError } from '@uni-helper/uni-network'; + +un.get('/user/12345').catch((error) => { + if (isUnError(error)) { + /* ... */ + } else { + /* ... */ + } +}); +``` diff --git a/docs/advanced/interceptors.md b/docs/advanced/interceptors.md new file mode 100644 index 0000000..ea3c8a0 --- /dev/null +++ b/docs/advanced/interceptors.md @@ -0,0 +1,114 @@ +# 拦截器 + +在请求或响应被 `then` 或 `catch` 处理前拦截它们。 + +## 添加拦截器 + +```ts +// 添加请求拦截器 +un.interceptors.request.use( + function (config) { + // 在发送请求之前做些什么 + return config; + }, + function (error) { + // 对请求错误做些什么 + return Promise.reject(error); + }, +); + +// 添加响应拦截器 +un.interceptors.response.use( + function (response) { + // 2xx 范围内的状态码都会触发该函数 + // 对响应数据做点什么 + return response; + }, + function (error) { + // 超出 2xx 范围的状态码都会触发该函数 + // 对响应错误做点什么 + return Promise.reject(error); + }, +); +``` + +可以给自定义实例添加拦截器。 + +```ts +const instance = un.create(); +instance.interceptors.request.use(() => { + /*...*/ +}); +``` + +## 移除拦截器 + +```ts +const myInterceptor = un.interceptors.request.use(() => { + /*...*/ +}); +un.interceptors.request.eject(myInterceptor); +``` + +也可以移除所有请求或响应的拦截器。 + +```ts +const instance = un.create(); +instance.interceptors.request.use(() => { + /*...*/ +}); +instance.interceptors.request.clear(); // 移除所有请求拦截器 +instance.interceptors.response.use(() => { + /*...*/ +}); +instance.interceptors.response.clear(); // 移除所有响应拦截器 +``` + +## 拦截器选项 + +当你添加请求拦截器时,`@uni-helper/uni-network` 默认认为它们是异步的。 + +当主线程被阻塞时,这可能会导致 `@uni-helper/uni-network` 请求的执行延迟(底层为拦截器创建了一个 `Promise`,你的请求被放在了调用栈的底部)。 + +如果你的请求拦截器是同步的,你可以在选项对象中添加一个标志,告诉 `@uni-helper/uni-network` 同步运行代码,避免请求执行中的任何延迟。 + +```ts +un.interceptors.request.use( + (config) => { + config.headers.test = 'I am only a header!'; + return config; + }, + null, + { synchronous: true }, +); +``` + +如果你想根据运行时检查来执行某个拦截器,你可以在 `options` 对象中设置 `runWhen` 函数。 + +**当且仅当** `runWhen` 的返回值为 `false` 时,拦截器不会被执行。该函数将和 `config` 对象一起被调用(别忘了,你也可以绑定你自己的参数)。 + +当你有一个只需要在特定时间运行的异步请求拦截器时,这可能会很方便。 + +```ts +const onGetCall = (config) => config.method.toUpperCase() === 'GET'; +un.interceptors.request.use( + (config) => { + config.headers.test = 'special get headers'; + return config; + }, + null, + { runWhen: onGetCall }, +); +``` + +## 多个拦截器 + +假设你添加了多个响应拦截器,并且响应是 `fulfilled` 状态时: + +- 按照添加的顺序执行每个拦截器 +- 只返回最后一个拦截器的结果 +- 每个拦截器都会收到其前一个拦截器的结果 +- 当 `fulfilled` 拦截器抛出时 + - 后面的 `fulfilled` 拦截器不会被调用 + - 后面的 `rejection` 拦截器会被调用 + - 一旦被捕获,后面的另一个 `fulfilled` 拦截器会被再次调用(就像在一个 `Promise` 链中一样) diff --git a/docs/advanced/ts-support.md b/docs/advanced/ts-support.md new file mode 100644 index 0000000..7468c9e --- /dev/null +++ b/docs/advanced/ts-support.md @@ -0,0 +1,94 @@ +# TypeScript 支持 + +`uni-network` 使用 TypeScript 编写,你可以享受到完整的 TypeScript 支持。 + +最常见的一个类型问题是,调用 API 时得不到响应数据和发送数据的类型。 + +```ts +// response 的类型是 UnResponse +// response.data 的类型是 UnData,你希望是 Record +const response = await un({ + method: 'post', + url: '/user/12345', + // 以下 data 的类型是 UnData,你希望是 Record + data: { + firstName: 'Fred', + lastName: 'Flintstone', + }, +}); +``` + +这可以通过设置两个泛型类型来解决,两个泛型类型分别对应响应数据和发送数据的类型。 + +```ts +// response 的类型是 UnResponse, Record> +// response.data 的类型是 Record +const response = await un, Record>({ + method: 'post', + url: '/user/12345', + // 以下 data 的类型是 Record + data: { + firstName: 'Fred', + lastName: 'Flintstone', + }, +}); +``` + +而另一个常见的类型问题是,使用响应拦截器后响应类型不正确。 + +```ts +// 添加响应拦截器直接返回 response.data +un.interceptors.response.use((response) => response.data); + +// response 的类型是 UnResponse,你希望是 Record +// response.data 的类型是 UnData,你希望是 Record +const response = await un({ + method: 'post', + url: '/user/12345', + // 以下 data 的类型是 UnData,你希望是 Record + data: { + firstName: 'Fred', + lastName: 'Flintstone', + }, +}); +``` + +这需要设置三个泛型类型来解决,三个泛型类型分别对应响应数据、发送数据、响应的类型。 + +```ts +// 添加响应拦截器直接返回 response.data +un.interceptors.response.use((response) => response.data); + +// response 的类型是 Record +// response.data 的类型是 Record +const response = await un, Record, Record>({ + method: 'post', + url: '/user/12345', + // 以下 data 的类型是 Record + data: { + firstName: 'Fred', + lastName: 'Flintstone', + }, +}); +``` + +⚠️ 注意:如果你只想修改响应的类型,而不修改其它类型,你仍然需要书写三个泛型类型。这和 `axios` 的泛型类型设计不同,因为 `uni-app` 对数据类型有更严格的要求。 + +你可以从 `@uni-helper/uni-network` 中导入 `UnData` 以保持前两个泛型类型的默认值。 + +```ts +// 添加响应拦截器直接返回 response.data +un.interceptors.response.use((response) => response.data); + +// response 的类型是 Record +// response.data 的类型是 UnData +const response = await un>({ + method: 'post', + url: '/user/12345', + // 以下 data 的类型是 UnData + data: { + firstName: 'Fred', + lastName: 'Flintstone', + }, +}); +``` diff --git a/docs/guide/api-intro.md b/docs/guide/api-intro.md new file mode 100644 index 0000000..af5f8ba --- /dev/null +++ b/docs/guide/api-intro.md @@ -0,0 +1,41 @@ +# API + +可以直接向 `uni-network` 传递相关配置来发起请求。 + +## un(config) + +```ts +// 发起 POST 请求 +un({ + method: 'POST', + url: '/user/12345', + data: { + firstName: 'Fred', + lastName: 'Flintstone', + }, +}); +``` + +## un(url[, config]) + +```ts +// 发起 GET 请求(默认请求方法) +un('/user/12345'); +``` + +## 请求别名 + +为了方便起见,已经为所有支持的请求方法提供了别名。在使用别名方法时,`url`、`method`、`data` 不需要在配置中指定。 + +- `un.request(config)` +- `un.download(config)` +- `un.upload(config)` +- `un.get(url[, config])` +- `un.delete(url[, config])` +- `un.head(url[, config])` +- `un.options(url[, config])` +- `un.trace(url[, config])` +- `un.connect(url[, config])` +- `un.post(url[, data[, config]])` +- `un.put(url[, data[, config]])` +- `un.patch(url[, data[, config]])` diff --git a/docs/guide/config-defaults.md b/docs/guide/config-defaults.md new file mode 100644 index 0000000..3d3e42c --- /dev/null +++ b/docs/guide/config-defaults.md @@ -0,0 +1,40 @@ +# 默认配置 + +你可以指定默认配置,它将作用于每个请求。 + +## 全局配置默认值 + +```ts +un.defaults.baseUrl = 'https://api.example.com'; +``` + +## 自定义实例默认值 + +```ts +// 创建实例时配置默认值 +const instance = un.create({ + baseUrl: 'https://api.example.com', +}); + +// 创建实例后修改默认值 +instance.defaults.baseUrl = 'https://api.another-example.com'; +``` + +## 配置的优先级 + +配置将会按优先级进行合并。优先级从低到高是内置的默认值、实例的 `defaults` 配置、请求的 `config`。后面的优先级要高于前面的。下面有一个例子。 + +```ts +// 使用库提供的默认配置创建实例 +// 此时超时配置的默认值是实际调用的 API 的默认值 +const instance = un.create(); + +// 重写库的超时默认值 +// 现在,所有使用此实例的请求都将等待 2.5 秒,然后才会超时 +instance.defaults.timeout = 2500; + +// 重写此请求的超时时间,因为该请求需要很长时间 +instance.get('/longRequest', { + timeout: 5000, +}); +``` diff --git a/docs/guide/example.md b/docs/guide/example.md new file mode 100644 index 0000000..0aeae97 --- /dev/null +++ b/docs/guide/example.md @@ -0,0 +1,85 @@ +# 基本用例 + +使用 `uni-network` 基本用例 + +## GET 请求 + +```ts +import un from '@uni-helper/uni-network'; + +// 请求特定 ID 的用户数据 +un.get('/user?ID=12345') + .then((response) => { + // 处理响应 + console.log('response', response); + }) + .catch((error) => { + // 处理错误 + console.log('error', error); + }) + .finally(() => { + // 总是会执行 + }); + +// 上述请求和以下等同 +un.get('/user', { + params: { + ID: '12345', + }, +}) + .then((response) => { + console.log('response', response); + }) + .catch((error) => { + console.log('error', error); + }) + .finally(() => { + // 总是会执行 + }); +``` + +## async/await + +```ts +async function getUser() { + try { + const response = await un.get('/user?ID=12345'); + console.log(response); + } catch (error) { + console.error(error); + } +} +``` + +## POST 请求 + +```ts +un.post('/user', { + firstName: 'Fred', + lastName: 'Flintstone', +}) + .then(function (response) { + console.log(response); + }) + .catch(function (error) { + console.log(error); + }) + .finally(() => {}); +``` + +## 并发请求 + +```ts +function getUserAccount() { + return un.get('/user/12345'); +} + +function getUserPermissions() { + return un.get('/user/12345/permissions'); +} + +Promise.all([getUserAccount(), getUserPermissions()]).then((responses) => { + const acct = responses[0]; + const perm = responses[1]; +}); +``` diff --git a/docs/guide/instance.md b/docs/guide/instance.md new file mode 100644 index 0000000..e1a5f54 --- /dev/null +++ b/docs/guide/instance.md @@ -0,0 +1,26 @@ +# Un 实例 + +## 创建实例 + +可以使用自定义配置创建一个实例。 + +### un.create([config]) + +```ts +const instance = un.create({ + baseUrl: 'https://some-domain.com/api/', + timeout: 1000, + headers: { 'X-Custom-Header': 'foobar' }, +}); +``` + +```ts +instance.request({ + method: 'POST', + url: '/user/12345', + data: { + firstName: 'Fred', + lastName: 'Flintstone', + }, +}); +``` diff --git a/docs/guide/introduction.md b/docs/guide/introduction.md new file mode 100644 index 0000000..f11b147 --- /dev/null +++ b/docs/guide/introduction.md @@ -0,0 +1,20 @@ +# 介绍 + +`@uni-helper/uni-network` 是一个为 [uni-app](https://uniapp.dcloud.io/) 打造的 [基于 Promise](https://javascript.info/promise-basics) 的 HTTP 客户端。 + +底层基于 `uni.request`,封装增加了一些功能,使其支持 Promise 现代化的使用,功能包括: + +- 默认请求使用 [uni.request](https://uniapp.dcloud.io/api/request/request.html) +- 上传文件使用 [uni.uploadFile](https://uniapp.dcloud.io/api/request/network-file.html#uploadfile) +- 下载文件使用 [uni.downloadFile](https://uniapp.dcloud.io/api/request/network-file.html#downloadfile) +- 支持 [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise) API +- [拦截请求和响应的数据](../advanced/interceptors.md) +- [取消请求](../advanced/cancellation.md) +- [TypeScript 支持](../advanced/ts-support.md) +- [组合式函数](../advanced/composition-api.md) + +`@uni-helper/uni-network` 灵感和代码绝大部分源于 `axios@0.27.2`。如果你想了解 `@uni-helper/uni-network` 与 `axios`、其它类似库的差别,请参考 [比较](../other/why-not.md) 部分的说明。 + +## 设备和浏览器支持 + +请查看 [构建](../other/build.md) 部分的说明。 diff --git a/docs/guide/quick-start.md b/docs/guide/quick-start.md new file mode 100644 index 0000000..a772b8c --- /dev/null +++ b/docs/guide/quick-start.md @@ -0,0 +1,29 @@ +# 安装 + +如果你有一个正在使用的包管理器,可以使用以下命令安装。 + +使用 npm: + +```sh +npm add -D @uni-helper/uni-network +``` + +使用 pnpm: + +```sh +pnpm add -D @uni-helper/uni-network +``` + +请参考 [文档](https://pnpm.io/npmrc#shamefully-hoist) 设置 `shamefully-hoist` 为 `true`。 + +使用 yarn: + +```sh +yarn add -D @uni-helper/uni-network +``` + +请参考 [文档](https://yarnpkg.com/configuration/yarnrc/#nodeLinker) 设置 `nodeLinker` 为 `node_modules`。 + +### 关于 `uni_modules` + +目前没有支持 `uni_modules` 的计划,但欢迎 PR 贡献。 diff --git a/docs/guide/req-config.md b/docs/guide/req-config.md new file mode 100644 index 0000000..778d4e6 --- /dev/null +++ b/docs/guide/req-config.md @@ -0,0 +1,197 @@ +# 请求配置 + +这些是创建请求时可以用的配置选项。 + +只有 `url` 是必需的,如果没有指定 `method` 且没有指定 `adapter`,请求将默认使用 `GET` 方法。 + +```ts +const config = { + // `url` 是用于请求的服务器 URL + url: '/user', + + // `baseUrl` 将自动加在 `url` 前面,除非 `url` 是一个绝对 URL + // 设置一个 `baseUrl` 便于为 un 实例的方法传递相对 URL + baseUrl: 'https://some-domain.com/api/', + + // 自定义请求头 + headers: { + 'content-type': 'application/json', + }, + + // `params` 是与请求一起发送的 URL 参数 + // 必须是一个普通对象或一个 URLSearchParams 对象 + // 要使用 URLSearchParams 对象,请使用 core-js 提供的 polyfill + // 可参考构建部分的说明或该仓库提供的 playground + params: { + ID: '12345', + }, + + // `paramsSerializer` 是可选方法,主要用于序列化 `params` + // 默认使用 [query-string](https://github.com/sindresorhus/query-string) 序列化 + paramsSerializer: (params) => { + /* 返回一个字符串 */ + }, + + // `timeout` 指定请求超时的毫秒数 + // 如果请求时间超过 `timeout` 的值,则请求会被中断 + timeout: 1000, // 默认值是实际调用的 API 的默认值 + + // `adapter` 允许自定义处理请求 + // 可以指定为 'request'、'upload' 和 'download' 三者之一 + // 也可以指定为一个方法,返回一个 Promise 并提供一个有效的响应 + // 如果你正在使用 un.request、un.download、un.upload、un.get 等别名方法 + // 无需再指定该键的值 + // adapter: 'request', // 默认值 + adapter: (config) => { + /* ... */ + }, + + // `validateStatus` 定义了对于给定的 HTTP 状态码是 resolve 还是 reject + // 如果 `validateStatus` 返回 `true`、`null` 或 `undefined` + // 则 promise 将会被 resolve,否则会被 reject + validateStatus: function (status) { + return status >= 200 && status < 300; // 默认值 + }, + + // 用于取消请求 + signal: new AbortController().signal, + + // 用于取消请求 + cancelToken: new CancelToken(function (cancel) { + /* ... */ + }), + + // 监听 HTTP Response Header 事件 + // 会比请求完成事件更早 + onHeadersReceived: (result) => { + /* ... */ + }, + + // request 使用 + // 创建请求时使用的方法 + method: 'GET', // 默认值 + + // request 使用 + // `data` 是作为请求体被发送的数据 + // 必须是以下类型之一:string、object、ArrayBuffer、ArrayBufferView、URLSearchParams + data: { + firstName: 'Fred', + }, + data: 'Country=Brasil&City=Belo Horizonte', + + // request 使用 + // 返回的数据类型 + // 如果设置为 json,会尝试对返回的数据做一次 JSON.parse + dataType: 'json', // 默认值 + + // request 使用 + // 响应的数据类型,选项包括 'text' 和 'arraybuffer' + responseType: 'text', // 默认值 + + // request 使用 + // 是否开启 http2 + enableHttp2: false, // 默认值 + + // request 使用 + // 是否开启 quic + enableQuic: false, // 默认值 + + // request 使用 + // 是否开启缓存 + enableCache: false, // 默认值 + + // request 使用 + // 是否开启 HttpDNS 服务 + enableHttpDNS: false, // 默认值 + + // request 使用 + // HttpDNS 服务商 Id + httpDNSServiceId: '', + + // request 使用 + // 是否开启 transfer-encoding chunked + enableChunked: false, // 默认值 + + // request 使用 + // 是否在 wifi 下使用移动网络发送请求 + forceCellularNetwork: false, // 默认值 + + // request 使用 + // 是否验证 ssl 证书 + sslVerify: true, // 默认值 + + // request 使用 + // 跨域请求时是否需要使用凭证 + withCredentials: false, // 默认值 + + // request 使用 + // 是否在 DNS 解析时优先使用 ipv4 + firstIpv4: false, // 默认值 + + // request 使用 + // 监听 Transfer-Encoding Chunk Received 事件 + // 当接收到新的 chunk 时触发 + onChunkReceived: (response) => { + /* ... */ + }, + + // upload 使用 + // 需要上传的文件列表,files 和 filePath 必填一个 + // 使用该参数时,filePath 和 name 无效 + // 不支持小程序 + files: [], + + // upload 使用 + // 文件类型 + fileType: 'image', // image, video, audio + + // upload 使用 + // 文件对象 + file: new File(), + + // upload 使用 + // 文件路径,files 和 filePath 必填一个 + // + // download 使用 + // 文件下载后存储的本地路径 + filePath: '/fake/path', + + // upload 使用 + // 文件名称 + name: 'fake-file.png', + + // upload 使用 + // 一个对象,会作为 HTTP 请求中其它额外的 form data + formData: Record, + + // download 使用 + // 下载进度变化时触发 + // 优先级 onDownloadProgress > onDownloadProgressUpdate > onProgress > onProgressUpdate + onDownloadProgress: UnOnProgress, + + // download 使用 + // 下载进度变化时触发 + // 优先级 onDownloadProgress > onDownloadProgressUpdate > onProgress > onProgressUpdate + onDownloadProgressUpdate: UnOnProgress, + + // upload 使用 + // 上传进度变化时触发 + // 优先级 onUploadProgress > onUploadProgressUpdate > onProgress > onProgressUpdate + onUploadProgress: UnOnProgress, + + // upload 使用 + // 上传进度变化时触发 + // 优先级 onUploadProgress > onUploadProgressUpdate > onProgress > onProgressUpdate + onUploadProgressUpdate: UnOnProgress, + + // upload / download 使用 + // 上传/下载进度变化时触发 + // 优先级 onUploadProgress / onDownloadProgress > onUploadProgressUpdate / onDownloadProgressUpdate > onProgress > onProgressUpdate + onProgress: UnOnProgress, + + // upload / download 使用 + // 上传/下载进度变化时触发 + // 优先级 onUploadProgress / onDownloadProgress > onUploadProgressUpdate / onDownloadProgressUpdate > onProgress > onProgressUpdate + onProgressUpdate: UnOnProgress, +}; +``` diff --git a/docs/guide/res-schema.md b/docs/guide/res-schema.md new file mode 100644 index 0000000..35fd0f3 --- /dev/null +++ b/docs/guide/res-schema.md @@ -0,0 +1,70 @@ +# 响应结构 + +一个请求的响应包应含以下信息。 + +```ts +const res = { + // `errMsg` 是可选的错误信息 + errMsg: '', + + // `errno` 是可选的错误代码 + errno: 0, + + // `profile` 是可选的调试信息 + profile: {}, + + // `config` 是 `un` 请求的配置信息 + config: {}, + + // `task` 是对应的 task 信息 + task: {}, + + // `status` 来自服务器响应的 HTTP 状态码 + status: 200, + + // `statusText` 来自服务器响应的 HTTP 状态信息 + statusText: 'OK', + + // `headers` 是服务器响应头 + // 所有的 header 名称都是小写,而且可以使用方括号语法访问 + // 例如: `response.headers['content-type']` + headers: {}, + + // `data` 是由服务器提供的响应数据 + data: {}, + + // request 特有 + // 服务器提供的 cookies 数据 + cookies: [], + + // download 特有 + // 临时本地文件路径 + // 没传入 filePath 指定文件存储路径时会返回,下载后的文件会存储到一个临时文件 + tempFilePath: '', + + // download 特有 + // 用户本地文件路径 + // 传入 filePath 时会返回,跟传入的 filePath 一致 + filePath: '', +}; +``` + +当使用 then 时,你将接收如下响应: + +```typescript +un.get('/user/12345').then((response) => { + console.log('errMsg', response?.errMsg); + console.log('errno', response?.errno); + console.log('profile', response?.profile); + console.log('config', response?.config); + console.log('status', response?.status); + console.log('statusText', response?.statusText); + console.log('headers', response?.headers); + console.log('data', response?.data); + console.log('cookies', response?.cookies); + console.log('tmpFilePath', response?.tmpFilePath); + console.log('filePath', response?.filePath); +}); +``` + +当使用 `catch`,或者传递一个 `rejection callback` 作为 `then` 的第二个参数时,响应可以作为 `error` 对象被使用,正如在 [错误处理](../advanced/handling-errors.md) 部分解释的那样。 diff --git a/docs/index.md b/docs/index.md new file mode 100644 index 0000000..ccc2837 --- /dev/null +++ b/docs/index.md @@ -0,0 +1,63 @@ +--- +layout: home + +hero: + name: 'Uni Network' + text: 'Uni Helper 官方维护的请求库' + tagline: 为 uni-app 打造的基于 Promise 的 HTTP 客户端。 + actions: + - theme: brand + text: 快速入门 → + link: /guide/introduction + - theme: alt + text: 安装 + link: /guide/quick-start + image: + src: /logo.png + alt: Uni Helper + +features: + - title: 📝 支持 Promise API + details: 默认支持 Promise API, 可直接使用 async/await,更加简洁明了 + - title: 🛠 请求响应拦截器 + details: 可配置请求和响应拦截器,自定义处理数据 + - title: 🔌 取消请求 + details: 可扩展请求取消,完全可控请求状态 + - title: 🦾 TypeScript 支持 + details: 基于 TypeScript 开发,默认支持 TypeScript,安全可控 + - title: 🧱 组合式函数 + details: 提供组合式函数,更加方便的使用 Uni Network + - title: 📤 支持上传下载 + details: 基于 uni.request 内部封装,支持上传和下载方法 +--- + + + + diff --git a/docs/other/build.md b/docs/other/build.md new file mode 100644 index 0000000..ed4c468 --- /dev/null +++ b/docs/other/build.md @@ -0,0 +1,61 @@ +# 构建 + +目前 `@uni-helper/uni-network` 会使用 `unbuild` 将 `uni` API 之外的部分转译到 `ES2017`(即 `ES8`)。`uni` API 需要在项目构建时由 `uni-app` 官方提供的插件处理。 + +对于 `vue-cli + vue2` 项目,请修改项目根目录 `vue.config.js` 如下所示。 + +这会让 `vue-cli` 处理 `@uni-helper/uni-network`,保证生成代码符合 `browserslist` 里的配置。我们建议设置 `browserslist` 为 `chrome>=53,ios>=8`。 + +```javascript +module.exports = { + transpileDependencies: ['@uni-helper/uni-network'], + // 如果是 vue-cli 5 + // transpileDependencies: true, +}; +``` + +对于 `vite + vue3` 项目,请设置 `build.target` 为 `ES6`、`optimizeDeps.exclude` 包含 `vue-demi`。 + +```typescript +import { defineConfig } from 'vite'; +import uni from '@dcloudio/vite-plugin-uni'; + +// https://vitejs.dev/config/ +export default defineConfig({ + build: { + target: 'es6', + cssTarget: 'chrome61', // https://cn.vitejs.dev/config/build-options.html#build-csstarget + }, + optimizeDeps: { + exclude: ['vue-demi'], + }, + plugins: [ + ..., + uni(), + ..., + ], +}); +``` + +然后在 `src/main.ts` 或 `src/main.js` 处自行添加 polyfill。以下是使用 [core-js](https://github.com/zloirock/core-js) 的示例(需要自行安装 `core-js`),你也可以使用 [es-shims](https://github.com/es-shims)。 + +```typescript +import 'core-js/actual/array/iterator'; +import 'core-js/actual/promise'; +import 'core-js/actual/object/assign'; +import 'core-js/actual/promise/finally'; +// 你可以根据需要自行添加额外的 polyfills +// import 'core-js/actual/object/values'; +// import 'core-js/actual/url-search-params'; +import { createSSRApp } from 'vue'; +import App from './App.vue'; + +export function createApp() { + const app = createSSRApp(App); + return { + app, + }; +} +``` + +微信小程序的 JavaScript 支持度见 [wechat-miniprogram/miniprogram-compat](https://github.com/wechat-miniprogram/miniprogram-compat)。微信小程序要支持 `vue3`,需设置基础库最低版本为 2.11.2 或以上,2.11.2 对应 `chrome>=53,ios>=10`。 diff --git a/docs/other/thank.md b/docs/other/thank.md new file mode 100644 index 0000000..31b0a0f --- /dev/null +++ b/docs/other/thank.md @@ -0,0 +1,13 @@ +# 致谢 + +- [alova](https://alova.js.org/zh-CN/) +- [axios](https://axios-http.com/) +- [luch-request](https://github.com/lei-mu/luch-request) +- [uni-ajax](https://uniajax.ponjs.com/) +- [vue-use](https://vueuse.org/) +- [react-query](https://tanstack.com/query/) +- [swr](https://swr.vercel.app/) +- [vue-query](https://github.com/DamianOsipiuk/vue-query) +- [@tanstack/query](https://tanstack.com/query/v4) +- [swrv](https://docs-swrv.netlify.app/) +- [vue-request](https://www.attojs.com/) diff --git a/docs/other/why-not.md b/docs/other/why-not.md new file mode 100644 index 0000000..560e525 --- /dev/null +++ b/docs/other/why-not.md @@ -0,0 +1,40 @@ +# 为什么不是 `axios`? + +`axios` 非常棒,但它面对的是浏览器和 `Node.js`,即使使用了 `adapter`,某些底层功能也可能会在小程序内报错。`axios` 体积较大,会占用宝贵的小程序空间。 + +此外,如果你想要获取良好的 TypeScript,你需要修改 `axios` 大部分类型定义。 + +你可以查看 [@uni-helper/axios-adapter](https://github.com/uni-helper/axios-adapter) 获取 `adapter` 支持。 + +### 比较 + +如果你发现这里信息已经过时,请提交 ISSUE 或 PR。 + +| | `axios` | `luch-request` | `uni-ajax` | `@uni-helper/uni-network` | +| ---------------------------- | ------------------------------------------------------------ | ------------------------------------------------------------ | ------------------------------------------------------------ | ------------------------------------------------------------ | +| 基本信息 | [![npm](https://img.shields.io/npm/v/axios)](https://www.npmjs.com/package/axios) [![npm](https://img.shields.io/npm/dw/axios)](https://www.npmjs.com/package/axios) | [![npm](https://img.shields.io/npm/v/luch-request)](https://www.npmjs.com/package/luch-request) [![npm](https://img.shields.io/npm/dw/luch-request)](https://www.npmjs.com/package/luch-request) | [![npm](https://img.shields.io/npm/v/uni-ajax)](https://www.npmjs.com/package/uni-ajax) [![npm](https://img.shields.io/npm/dw/uni-ajax)](https://www.npmjs.com/package/uni-ajax) | [![npm](https://img.shields.io/npm/v/@uni-helper/uni-network)](https://www.npmjs.com/package/@uni-helper/uni-network) [![npm](https://img.shields.io/npm/dw/@uni-helper/uni-network)](https://www.npmjs.com/package/@uni-helper/uni-network) | +| 开发语言 | JavaScript | JavaScript | JavaScript | TypeScript | +| 类型支持 | `index.d.ts`(没有考虑 `uni-app`) | `index.d.ts`(泛型支持较差) | `index.d.ts` | 包含 | +| 运行环境 | 浏览器和 `Node.js` | `uni-app` | `uni-app` | `uni-app` | +| `Promise` | √ | √ | √ | √ | +| `uni_modules` | × | √ | √ | × | +| `npm` 包 | √ | √ | √ | √ | +| 实例化 | √ | √ | √ | √ | +| 请求说明 | √ | √ | √ | √ | +| 请求头 headers | `AxiosHeaders` | 普通对象 | 普通对象 | 普通对象 | +| 请求参数 params | `AxiosURLSearchParams` | 普通对象 | 普通对象 | 普通对象或 `URLSearchParams` 对象 | +| 请求转换 `transformRequest` | √ | × | × | × | +| 响应说明 | √ | × | √ | √ | +| 响应转换 `transformResponse` | √ | × | × | × | +| 任务说明 | ×(没有考虑 `uni-app` 任务) | × | √(只有 `requestTask` 说明) | √(只有简单说明) | +| 适配器 | √(内置 `xhr` 和 `http`) | × | √ | √ | +| `uni.request` | ×(自行开发,还需要覆写类型) | √ | √ | √ | +| `uni.downloadFile` | ×(自行开发,还需要覆写类型) | √ | ×(自行开发,还需要覆写类型) | √ | +| `uni.uploadFile` | ×(自行开发,还需要覆写类型) | √ | ×(自行开发,还需要覆写类型) | √ | +| 请求拦截器 | √ | √ | √ | √ | +| 响应拦截器 | √ | √ | √ | √ | +| 配置说明 | √ | √ | √ | √ | +| 取消请求说明 | √ | × | √ | √ | +| 错误处理说明 | √ | × | √ | √ | +| 测试 | 完善 | 部分 | 无 | 部分 | +| 使用示例 | √ | √ | √ | √ | diff --git a/docs/public/logo.png b/docs/public/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..c9f78e9cf2c8cbb97a1e2efd45bccd71a898a068 GIT binary patch literal 7519 zcmcIpWmg=}(_I#K4*`M(S%SL+S=?P0Sll(ioy7^RArK(AyE`!~SdieJ;O@Tr-`{6= z&huhs&YY_5t~ygS_x9}%S{jP@I8-K?Os!W>d*ESoHxcwc%g%>Gc4@ZKLFYyefTPsYFx8t~l zQMlNeR%Rq>;S6D>GHNbd3`zurFHHfg(rLK#CcX8)gj`Pp*A#_zP@G$H{%9;_hJ4vQ zPp2OryZ5iHx7!&LwP%76iBWLQK6DFw4LJ6FI`TKb>Z z;GuAdzSKRNe@12rUfl%CKdcbYyFr1MxF`h*`Xd>m2^S=QE-b*6PDGlvp>yk(U;_Zr z(al3~dTQn5C`zQ7TwZFb#h3O7CKBjL1lN~^Pzqk+MqDL%-O-9atz))P)GF@uk*0Wn z!308;FdZ3_ry+6oyKeFEo1M*251pFfS-}T!^}L(3@WG2itly(pu&83$_91Nlne!!! z=Kde;tiJ^*clSC(8LEMd!t9qVqgT5X)t^Q`Va%XMe$6WH8*?tsSYoU@dt4LRW&dV& z`uW6QSET;trw3b z(e`>_*E0^9T%}^-*7Y+;HzZ=8h2Exe;W~)6^omro`ci&qd5$7HxX-fja5HTKCA&+& zVuJgw%CXj;Ux{gV7p$4XDzJrUJ`7$?pI9wcjC5P^`*1JwBd6$;jq|{}$K1`1i>wX9 z%(qYYyuA9jT33rLI9`?ORLynUV< zv_mITzIP&hWisW0W(Gmsb%h&Tz=qglAvD>-(Z=P6^u|2Y&==hqom&$0T>;j%i>|Gw zB=qD#?aVK6^j>6⪻RzS5v1fGOB;P8G93a{mj0`5LvTz@M$ruZ|V8#rhAlPgj*xK zvLUTG=Es9=|Lu9h(C&?cX(?j*(xBGYI6$UU#YroJmvcKK%$#s8cLnGV90ioY)}8Cp z&raqnkwG82Wt!0;R^t78PV^;jfA8-TcjtJW`CwG`g$@Xn$_KNX4^1+@H>~~}aM(7H z=P3ccezt!ya-0(X?h09C6Ciogo|KIVVep}Gc^`sdd5}n6zS@7lt)t+BKR+~~LsAOy zX4ZAj2u$vfREpfH`6A%V?lstiFuh2aF1puj>|Tjtw6$^0#?ZAbk!lb=NQ(SfXD^fs zFD7#X^%gnE?w^LGSaBtPW@nr@gZB+dx+QcnHk&z9)Nw?ebhG+3R@1uY9 zlhBJkpCuFOGTc99M>_Iw@vdwAN!a|9M5Lqh&Text36(TdJ#q^oXvkU&n_X>oVjYjj zT*>6`&lOMqH&D>&V7>kJ^1za9$bnYRIqTpO8aRYt@!|X;TyDluX~t5y(Bo3wBp3Yl zmU&!??5ix`Y>c-avNPDt>$!ZqJce+RdH2qVBRbTCP-C`%Cd zbsaS?pSUqTtP@Xg(%crL8#-_XlG>(6(+ZMb)YXYFW$~d&IiZw;l(HE;^=_XMhtE&P zO6dXZTsxDx2-J>Ff&kvX>x)0kAW(*JsZr*m~ZkO&^8 zf{#k?#p6(op6GDt#I?DhR7b048K3;?CyOjg2h<3dxBC^x9+#K7^88T(^~!znAj;8b z)kE;xW@=<;Z#84cty?S&@6MV=+R0+EnR$h6JMk`QP^MHm_df;9;D67I(DJwtO9W*> z*id!e*)FmKorE=otrQqJJ8@J~bgfdN7IEpx!kuQ4qc|}ODV5{qv!0aB6zm_Ot>ocZ zC`z3T+em0*FxS<0#Eo?E7=$^z@y^15V99U{x2j%KU@vYYplItmauYQXMK1j28l||} z<#Po8hXI|^AxSAw^gpAkjD7P{j+yae%QONRh>D2+^Q4dDur;9M3niyhRYuk6D8%~` zT;RgYU&BFmlu0ylDvi~vRRJVY$=cy4wh%s;0e-LHqr^&iQ-}k0AV8yrNIv5+qTpfv zazayzYWqe%yfNU2l1gQB_m0R`0-M|p8tI6lZOCWGK&1eB9f@_}ne&e&k86c|NP9xd zzzHYH!9Do9&sT+Y;QoF>5DoUtJw{PoEDgvT1%?R-0)W}T z8#BQrXkb*Z0N6niz+3gEb$~D8I}q*HRW)8F_J@+_ujkhUO%GXKO)xpR3RGKS6-W04 zs(_IhyY+2H&z8vAZ=FwSetliux_b89$S1IzjuAHw1-+?a?mLT zR_WGHl=vFX4C@i?bG|d!b&iOznoo-_%aaC0)kqvO-V{xo(at}TCaay$g}yyV(rG*# z(Vqd5(Ba^RF3HE7UQbA8d@re=@s4?p`gV+B0zUHaSZjg3LTIr)1F$+xbJKpC%I9si z5BU(R>^OQ}#X(1dQfnx1#aH`;v#Dq>n0$Xe(VPS-njM64IN@XYi0c0~GLQpt0&(QQ z;M;u(P6;?sa(KFm1)~dolD`R!WTDfR@iZ)QDX;qz)#{7QQR)36z_In)$G*Qofi84( zL-X|ll%)P%y+#VxX5yXs|ZxBcU*gtDoBpf=PGC;tD zs}7u_etRInh7E}|g(bFK2z%~UBL2{J0e_ctk;-CZzkL#KJCs+Pp6H>>_= z1!?u?I%M=p0OQr#q~~u_8{KeCmUZ0gfMzGAp#+r5Zu@N^$Ib%-%TehXEv!2+)_ST1 zk1N+Y0!TxlSLOD_1%fnd>Tn=nn-={bBjz&y&>z0{7s=jYUkc_r4Z=9O+MWi(RaN02 z7f}bFS<&<9uZFItNp?ZXrB$;zI9zP-=$o zPexH=FNvVNg#}M-%%qiV(&6!%0{BoTXW9_q^axO#zQ^Ttrmxe-f9sejtMOi1IJIqM zg`w@oRFX^zkNo*6uZs)8o6${~k$|-ro0xAO$_f>beULl(>Oe;DQyq`FZh-1I`-RN* zY-vW?GD)W*mXSc~eLM98r_-=*%C`kS8xZXaw-U8q&9a*h)6Ma99FO1zr{8K@$W`jq z1PI$Ft^r*b*7A$Bt)YyO|E>bfWnPC#8JQn+3NGxE+E|(Y`rHW4vhQ#R-q)9@wTekA z;E|jX@0geqznJVi;u0Jd{FtaOWjbqgBhFBg^azY%wzXl$-z8h+(B4^mK0bLJ)GqAo z9#te)YiK;{e9wi(EIcLd6;bPNqtUCMLp7-PoIZo791VY6w!k((A4oa8oYY}Km2`1FHjzOt{BYs83Y zTjdS9t1G-0yn|qb2@qCgKZLvgQkgxmNG|6jR(U5j8~q2hP>yHqOaIap4HvZne{qKR z{N?Y>$LUo~OM}YlkPeq*J=T5;2JZ<{ph_mBSGwDj+xM7eeSEtSg3csP^~#<~tyCuu zZ<0|wUhGF;Al>60^?P%U+RfKE&A+r7{r3_7DoaFHRWq?GHQJ&pg){w4#ae4QhNRD4d;3Z3YyfVk6D~P=>;q!+AwUe8iL6(> zAm4ohU`g2efk)PKQD5`Za_b?#sKV0Ur(V|yF3tGoDK#p2bL57>=SFJ&+(7J+%+)lg zeWj!$s=sOnz4C-(=JLRJHP?JzsQd$uH8S4j%cuH{cUk9=c=-q34_e}q{=fTVyT6}hif4K)HKoK#_{KjceaONzv+wQ= zDXp}b5>Aq07+RCNdEuC~&5cd_zMl-gWd8B(Ze_;il*JglJnVCr%!I};1x@J}JgJ#h z&OE4^VWy-SR`!hhk0>=eJyVF^%+~n+N!FC9^*r%VNB01)Hx0*9LcOWoy2QhwS6lmv zv2Qjq_0;~j9pU4&ry)G&arWs&*1scnKPG)n&U`!E;a;5-KS|IJvV+{W(A$=&CwM6F z@S|z&2u2b>zv|4MX1shhY+B>soX4Ra?IL}X1C1}@?kx7;XAUXX(=iXDai>6;cdes% z1GZk!Mb7fZlZS0DC6fWdkI&t0T!?*_(AtlCAevMEr%%kYydzFMnPt(uoPEyzh*^Cg z#W;0FfXKL3w#R4UQ;<=xW1`>4%g zRu}y66dhjPDR~pLb$WelL7l`lAgm`jqAyaG>sT4X=}f25Ij&pV{}!&OzEVwwhp1` zC+8F|YyF7e6dbmPwuEP?GA!4nCcmmTt_KtdNhW<+cBsBQ)}HgM#NU1KjCh)B<{^ez z{pgf$UW-5Tspq*Fw5a!XzWr6f|3uigG%SB&Fl5lS%!fb77X|4JTaSCeh5W_1kGJ91 z3(wTO_Bs4opHzp5bLUe``n+K_l&?Kkt#9mRa`9Tmf|j!_1^N%;etVF8G+x*BN1(f| zpTOR$rMbo=pv0iB$s*SQ-l=tWetMOTbBfl3E4JdO!`dy<*8s7L3#1eXPAp2`COp zm8vF<&sf*epVM2O*XF2Y=Dx%PL1?T2xRamv1B>vm zKd39P1k#EJrFRd6?4GaJ;DQT=0%6B(QHCEksce9Zku`7ndTPWMZ{=wC1)tRB4MJlc zopCKYg1q>Cbx~*nQ>Mh7GK7>(RqB-<@Hd_Bi~cKC?@$K>h89*l6!#0Tm)1bm-RpXA z0MHPNi2J=uF8GnJYYL`ECj&H_ zUtiOYmsxV6-9B|CQ*^(O)WWGTQyCF>xqIw%1eqvs=7DHDTg{;{9bqF;#_#c`^N=jx zx*h9MuPXuJsB5)f9r`#7kax3auMXB|I;IKbx#yhdkN+>uU zX6(|HYL7>rjP&mqnexNTX?igL)5ho$>_j*AL^AIzMTpgrR+j&)sV9$wb@3uUY7Egw zaLBxlg!9&A-I`XAla~Yen8jbjCAx_ERCA~qafhU!PebHG*9cd}tY#!1b8&|=V4Q#$ zq0o2b-2-sgLTf`Ihrz+3n=0t~!UR8uxO7J0?LQl^231Je;eXs@lugTWepoHt&0Csy z*_92Jx9+5clcd|9GJ_IEs=2z}Ac$|CH=e~3nW8hd49vbsj*R4cZl1h{ef^N~G;_(l zd<|~)a=xZ=U#J?E@M)&eeGCi&6OFQrH1r6W&*t~%?VUkQvWr7F+|C> zTDD%DM~rG3*spq&M>cegU9^e4(+?unDhTc~7-|^_xa6YO1?J^%x|p2k=~r5NXJ^9x z7H3iXRN-D^LSfohRot-!)8l5n&7`!cDVu&Urnz}V_bEFaN%ED~AEn$;fsnS9%BCFA zyyLc1Vubm9Ek-agew5-9?jfE>+HQe$38GJyB3i6B`2!@zl=~59*>&i%Vm?N}`w(^+ zR{7k`TX9UNG6in-ElQYXOxe}b#a{$@6NXX$=LqM>6dan-d=B@|o+&zCM>)dK9)lk3 z9@fIKhLuq@U#*fgVdRq?vKYB#G)uD}+lB(!$-4 z@>Y*Z{KJq;dwrGF93Y`F=W5&8x4*DjpXMH54k1~^pZOE` zyRuX63RtedncQP9`R6RnH=I>5Fqlk*&!r(Hm&N0!mEO=GL=k>z1RCs`hny?Vu~G_d z-*?#}LYrue%3t@Rt$?dhBTij`RDzHuK<#W>gE@_xntBwHc!Z4WJ3MKG^NFIhpffLU zu&s2-LK@>A6YI21Ou zjtY<@-85!APyPFKq2}~#2o~hzXENVRT902>=2%nw))1Y7qPcIZ35j3tEd=gJL)eY| zTuu|#DZCZ!d!4?*f|6Y4hb@<#=ez;4gZ6Lv(wnrQqYY-#?~%byhRG0q5#$7s8JnJJ zHc(AOpom5tyGN|f)vjKPbNg2Dn4918EGNp+q+>t29TtnvHK+JtwtKH-R5{;XVj-^o zu^?GqO^C%nAlk5w8C3xoY0L;*&aI(MR9jt`7jI}Hht+J9=A$z@TuZGzZluyRtV-rx z=e)@1;C^w{B4+kG&r(D}leu=g2L&ism4(SF)xb<6pHo6h)r7HTWk9ha_wIR3v=H!G zR?|C(e<$v4@gyS4h%Lyib4K_csiWp}LZL$qaLd~^(ZH<;X>CR3T`sC-Vf+xzg+oztOAC9?Bl5<^=uw73AtWm%yCIzm- z%@f4epJTjkf4~}uZU;!mf+f5B&!u_tm0E*O#KqukC4g1)eawHo|s5S%3#70$e zV|Cpm^-lWG?Z&hbM?to=jAsu!D=a08z%;VUV$>3fP*1Z7a#TLde4*Wbf!4913*fe( zskfIB%>z#wk{6@P=w*rA@unXR>cxkmTC+D(W zdnQpp>O$+8?Sa}WT5P!0#{6;efN3f{ovQ_Sr}N-(!cPlQ)TwzSCZhOFcuK&p64{?M z%|QMz;r+{8aV)QeqtG9BKuW;th3PUwCFO`_4O`n_DBDj}1+Y7r$s z3+Q=#eX10gS`9hCaS}&DE7@>VA?uy@O_s{T4%qS=rGPd7I{$EZN;pWJ* aQUpTvEl%lk;D|5s1)waiAy+435&l0fC1ef& literal 0 HcmV?d00001 diff --git a/package.json b/package.json index f2b0355..73b3fcb 100644 --- a/package.json +++ b/package.json @@ -69,7 +69,10 @@ "prepublishOnly": "pnpm run build", "prepare": "is-ci || simple-git-hooks", "test": "vitest run", - "test:coverage": "vitest run --coverage" + "test:coverage": "vitest run --coverage", + "docs:dev": "vitepress dev docs", + "docs:build": "vitepress build docs", + "docs:preview": "vitepress preview docs" }, "dependencies": { "@dcloudio/types": "^3.4.3", @@ -112,6 +115,7 @@ "type-fest": "^4.6.0", "typescript": "^5.2.2", "unbuild": "^2.0.0", + "vitepress": "1.0.0-rc.33", "vitest": "^0.34.6", "vue": "^3.3.7" }, diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index e53fbcc..f254aa7 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -22,7 +22,7 @@ importers: version: 1.0.0(vue@3.3.7) '@vueuse/core': specifier: ^9.13.0 - version: 9.13.0(@vue/composition-api@1.0.0)(vue@3.3.7) + version: 9.13.0(vue@3.3.7) lodash.merge: specifier: ^4.6.2 version: 4.6.2 @@ -34,7 +34,7 @@ importers: version: 2.0.1 vue-demi: specifier: ^0.14.6 - version: 0.14.6(@vue/composition-api@1.0.0)(vue@3.3.7) + version: 0.14.6(vue@3.3.7) devDependencies: '@babel/core': specifier: ^7.23.2 @@ -126,6 +126,9 @@ importers: unbuild: specifier: ^2.0.0 version: 2.0.0(typescript@5.2.2) + vitepress: + specifier: 1.0.0-rc.33 + version: 1.0.0-rc.33(@algolia/client-search@4.22.0)(@types/node@20.8.10)(postcss@8.4.31)(search-insights@2.13.0)(typescript@5.2.2) vitest: specifier: ^0.34.6 version: 0.34.6(@vitest/ui@0.34.6) @@ -219,6 +222,140 @@ packages: engines: {node: '>=0.10.0'} dev: true + /@algolia/autocomplete-core@1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0)(search-insights@2.13.0): + resolution: {integrity: sha512-009HdfugtGCdC4JdXUbVJClA0q0zh24yyePn+KUGk3rP7j8FEe/m5Yo/z65gn6nP/cM39PxpzqKrL7A6fP6PPw==} + dependencies: + '@algolia/autocomplete-plugin-algolia-insights': 1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0)(search-insights@2.13.0) + '@algolia/autocomplete-shared': 1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0) + transitivePeerDependencies: + - '@algolia/client-search' + - algoliasearch + - search-insights + dev: true + + /@algolia/autocomplete-plugin-algolia-insights@1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0)(search-insights@2.13.0): + resolution: {integrity: sha512-a/yTUkcO/Vyy+JffmAnTWbr4/90cLzw+CC3bRbhnULr/EM0fGNvM13oQQ14f2moLMcVDyAx/leczLlAOovhSZg==} + peerDependencies: + search-insights: '>= 1 < 3' + dependencies: + '@algolia/autocomplete-shared': 1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0) + search-insights: 2.13.0 + transitivePeerDependencies: + - '@algolia/client-search' + - algoliasearch + dev: true + + /@algolia/autocomplete-preset-algolia@1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0): + resolution: {integrity: sha512-d4qlt6YmrLMYy95n5TB52wtNDr6EgAIPH81dvvvW8UmuWRgxEtY0NJiPwl/h95JtG2vmRM804M0DSwMCNZlzRA==} + peerDependencies: + '@algolia/client-search': '>= 4.9.1 < 6' + algoliasearch: '>= 4.9.1 < 6' + dependencies: + '@algolia/autocomplete-shared': 1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0) + '@algolia/client-search': 4.22.0 + algoliasearch: 4.22.0 + dev: true + + /@algolia/autocomplete-shared@1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0): + resolution: {integrity: sha512-Wnm9E4Ye6Rl6sTTqjoymD+l8DjSTHsHboVRYrKgEt8Q7UHm9nYbqhN/i0fhUYA3OAEH7WA8x3jfpnmJm3rKvaQ==} + peerDependencies: + '@algolia/client-search': '>= 4.9.1 < 6' + algoliasearch: '>= 4.9.1 < 6' + dependencies: + '@algolia/client-search': 4.22.0 + algoliasearch: 4.22.0 + dev: true + + /@algolia/cache-browser-local-storage@4.22.0: + resolution: {integrity: sha512-uZ1uZMLDZb4qODLfTSNHxSi4fH9RdrQf7DXEzW01dS8XK7QFtFh29N5NGKa9S+Yudf1vUMIF+/RiL4i/J0pWlQ==} + dependencies: + '@algolia/cache-common': 4.22.0 + dev: true + + /@algolia/cache-common@4.22.0: + resolution: {integrity: sha512-TPwUMlIGPN16eW67qamNQUmxNiGHg/WBqWcrOoCddhqNTqGDPVqmgfaM85LPbt24t3r1z0zEz/tdsmuq3Q6oaA==} + dev: true + + /@algolia/cache-in-memory@4.22.0: + resolution: {integrity: sha512-kf4Cio9NpPjzp1+uXQgL4jsMDeck7MP89BYThSvXSjf2A6qV/0KeqQf90TL2ECS02ovLOBXkk98P7qVarM+zGA==} + dependencies: + '@algolia/cache-common': 4.22.0 + dev: true + + /@algolia/client-account@4.22.0: + resolution: {integrity: sha512-Bjb5UXpWmJT+yGWiqAJL0prkENyEZTBzdC+N1vBuHjwIJcjLMjPB6j1hNBRbT12Lmwi55uzqeMIKS69w+0aPzA==} + dependencies: + '@algolia/client-common': 4.22.0 + '@algolia/client-search': 4.22.0 + '@algolia/transporter': 4.22.0 + dev: true + + /@algolia/client-analytics@4.22.0: + resolution: {integrity: sha512-os2K+kHUcwwRa4ArFl5p/3YbF9lN3TLOPkbXXXxOvDpqFh62n9IRZuzfxpHxMPKAQS3Et1s0BkKavnNP02E9Hg==} + dependencies: + '@algolia/client-common': 4.22.0 + '@algolia/client-search': 4.22.0 + '@algolia/requester-common': 4.22.0 + '@algolia/transporter': 4.22.0 + dev: true + + /@algolia/client-common@4.22.0: + resolution: {integrity: sha512-BlbkF4qXVWuwTmYxVWvqtatCR3lzXwxx628p1wj1Q7QP2+LsTmGt1DiUYRuy9jG7iMsnlExby6kRMOOlbhv2Ag==} + dependencies: + '@algolia/requester-common': 4.22.0 + '@algolia/transporter': 4.22.0 + dev: true + + /@algolia/client-personalization@4.22.0: + resolution: {integrity: sha512-pEOftCxeBdG5pL97WngOBi9w5Vxr5KCV2j2D+xMVZH8MuU/JX7CglDSDDb0ffQWYqcUN+40Ry+xtXEYaGXTGow==} + dependencies: + '@algolia/client-common': 4.22.0 + '@algolia/requester-common': 4.22.0 + '@algolia/transporter': 4.22.0 + dev: true + + /@algolia/client-search@4.22.0: + resolution: {integrity: sha512-bn4qQiIdRPBGCwsNuuqB8rdHhGKKWIij9OqidM1UkQxnSG8yzxHdb7CujM30pvp5EnV7jTqDZRbxacbjYVW20Q==} + dependencies: + '@algolia/client-common': 4.22.0 + '@algolia/requester-common': 4.22.0 + '@algolia/transporter': 4.22.0 + dev: true + + /@algolia/logger-common@4.22.0: + resolution: {integrity: sha512-HMUQTID0ucxNCXs5d1eBJ5q/HuKg8rFVE/vOiLaM4Abfeq1YnTtGV3+rFEhOPWhRQxNDd+YHa4q864IMc0zHpQ==} + dev: true + + /@algolia/logger-console@4.22.0: + resolution: {integrity: sha512-7JKb6hgcY64H7CRm3u6DRAiiEVXMvCJV5gRE672QFOUgDxo4aiDpfU61g6Uzy8NKjlEzHMmgG4e2fklELmPXhQ==} + dependencies: + '@algolia/logger-common': 4.22.0 + dev: true + + /@algolia/requester-browser-xhr@4.22.0: + resolution: {integrity: sha512-BHfv1h7P9/SyvcDJDaRuIwDu2yrDLlXlYmjvaLZTtPw6Ok/ZVhBR55JqW832XN/Fsl6k3LjdkYHHR7xnsa5Wvg==} + dependencies: + '@algolia/requester-common': 4.22.0 + dev: true + + /@algolia/requester-common@4.22.0: + resolution: {integrity: sha512-Y9cEH/cKjIIZgzvI1aI0ARdtR/xRrOR13g5psCxkdhpgRN0Vcorx+zePhmAa4jdQNqexpxtkUdcKYugBzMZJgQ==} + dev: true + + /@algolia/requester-node-http@4.22.0: + resolution: {integrity: sha512-8xHoGpxVhz3u2MYIieHIB6MsnX+vfd5PS4REgglejJ6lPigftRhTdBCToe6zbwq4p0anZXjjPDvNWMlgK2+xYA==} + dependencies: + '@algolia/requester-common': 4.22.0 + dev: true + + /@algolia/transporter@4.22.0: + resolution: {integrity: sha512-ieO1k8x2o77GNvOoC+vAkFKppydQSVfbjM3YrSjLmgywiBejPTvU1R1nEvG59JIIUvtSLrZsLGPkd6vL14zopA==} + dependencies: + '@algolia/cache-common': 4.22.0 + '@algolia/logger-common': 4.22.0 + '@algolia/requester-common': 4.22.0 + dev: true + /@ampproject/remapping@2.2.1: resolution: {integrity: sha512-lFMjJTrFL3j7L9yBxwYfCq2k6qqwHyzuUl/XBnif78PWTJYyL/dfowQHWE3sp6U6ZzqWiiIZnpTMO96zhkjwtg==} engines: {node: '>=6.0.0'} @@ -542,6 +679,14 @@ packages: dependencies: '@babel/types': 7.23.0 + /@babel/parser@7.23.6: + resolution: {integrity: sha512-Z2uID7YJ7oNvAI20O9X0bblw7Qqs8Q2hFy0R9tAfnfLkp5MW0UH9eUvnDSnFwKZ0AvgS1ucqR4KzvVHgnke1VQ==} + engines: {node: '>=6.0.0'} + hasBin: true + dependencies: + '@babel/types': 7.23.0 + dev: true + /@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression@7.22.5(@babel/core@7.23.2): resolution: {integrity: sha512-NP1M5Rf+u2Gw9qfSO4ihjcTGW5zXTi36ITLd4/EoAcEhIZ0yjMqmftDNl3QC19CX7olhrjpyU454g/2W7X0jvQ==} engines: {node: '>=6.9.0'} @@ -2438,6 +2583,49 @@ packages: - vue dev: true + /@docsearch/css@3.5.2: + resolution: {integrity: sha512-SPiDHaWKQZpwR2siD0KQUwlStvIAnEyK6tAE2h2Wuoq8ue9skzhlyVQ1ddzOxX6khULnAALDiR/isSF3bnuciA==} + dev: true + + /@docsearch/js@3.5.2(@algolia/client-search@4.22.0)(search-insights@2.13.0): + resolution: {integrity: sha512-p1YFTCDflk8ieHgFJYfmyHBki1D61+U9idwrLh+GQQMrBSP3DLGKpy0XUJtPjAOPltcVbqsTjiPFfH7JImjUNg==} + dependencies: + '@docsearch/react': 3.5.2(@algolia/client-search@4.22.0)(search-insights@2.13.0) + preact: 10.19.3 + transitivePeerDependencies: + - '@algolia/client-search' + - '@types/react' + - react + - react-dom + - search-insights + dev: true + + /@docsearch/react@3.5.2(@algolia/client-search@4.22.0)(search-insights@2.13.0): + resolution: {integrity: sha512-9Ahcrs5z2jq/DcAvYtvlqEBHImbm4YJI8M9y0x6Tqg598P40HTEkX7hsMcIuThI+hTFxRGZ9hll0Wygm2yEjng==} + peerDependencies: + '@types/react': '>= 16.8.0 < 19.0.0' + react: '>= 16.8.0 < 19.0.0' + react-dom: '>= 16.8.0 < 19.0.0' + search-insights: '>= 1 < 3' + peerDependenciesMeta: + '@types/react': + optional: true + react: + optional: true + react-dom: + optional: true + search-insights: + optional: true + dependencies: + '@algolia/autocomplete-core': 1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0)(search-insights@2.13.0) + '@algolia/autocomplete-preset-algolia': 1.9.3(@algolia/client-search@4.22.0)(algoliasearch@4.22.0) + '@docsearch/css': 3.5.2 + algoliasearch: 4.22.0 + search-insights: 2.13.0 + transitivePeerDependencies: + - '@algolia/client-search' + dev: true + /@esbuild/android-arm64@0.17.16: resolution: {integrity: sha512-QX48qmsEZW+gcHgTmAj+x21mwTz8MlYQBnzF6861cNdQGvj2jzzFjqH0EBabrIa/WVZ2CHolwMoqxVryqKt8+Q==} engines: {node: '>=12'} @@ -3897,7 +4085,6 @@ packages: dependencies: '@jridgewell/resolve-uri': 3.1.0 '@jridgewell/sourcemap-codec': 1.4.15 - dev: false /@jridgewell/trace-mapping@0.3.9: resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==} @@ -4272,6 +4459,110 @@ packages: rollup: 3.29.4 dev: true + /@rollup/rollup-android-arm-eabi@4.9.1: + resolution: {integrity: sha512-6vMdBZqtq1dVQ4CWdhFwhKZL6E4L1dV6jUjuBvsavvNJSppzi6dLBbuV+3+IyUREaj9ZFvQefnQm28v4OCXlig==} + cpu: [arm] + os: [android] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-android-arm64@4.9.1: + resolution: {integrity: sha512-Jto9Fl3YQ9OLsTDWtLFPtaIMSL2kwGyGoVCmPC8Gxvym9TCZm4Sie+cVeblPO66YZsYH8MhBKDMGZ2NDxuk/XQ==} + cpu: [arm64] + os: [android] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-darwin-arm64@4.9.1: + resolution: {integrity: sha512-LtYcLNM+bhsaKAIGwVkh5IOWhaZhjTfNOkGzGqdHvhiCUVuJDalvDxEdSnhFzAn+g23wgsycmZk1vbnaibZwwA==} + cpu: [arm64] + os: [darwin] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-darwin-x64@4.9.1: + resolution: {integrity: sha512-KyP/byeXu9V+etKO6Lw3E4tW4QdcnzDG/ake031mg42lob5tN+5qfr+lkcT/SGZaH2PdW4Z1NX9GHEkZ8xV7og==} + cpu: [x64] + os: [darwin] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm-gnueabihf@4.9.1: + resolution: {integrity: sha512-Yqz/Doumf3QTKplwGNrCHe/B2p9xqDghBZSlAY0/hU6ikuDVQuOUIpDP/YcmoT+447tsZTmirmjgG3znvSCR0Q==} + cpu: [arm] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm64-gnu@4.9.1: + resolution: {integrity: sha512-u3XkZVvxcvlAOlQJ3UsD1rFvLWqu4Ef/Ggl40WAVCuogf4S1nJPHh5RTgqYFpCOvuGJ7H5yGHabjFKEZGExk5Q==} + cpu: [arm64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm64-musl@4.9.1: + resolution: {integrity: sha512-0XSYN/rfWShW+i+qjZ0phc6vZ7UWI8XWNz4E/l+6edFt+FxoEghrJHjX1EY/kcUGCnZzYYRCl31SNdfOi450Aw==} + cpu: [arm64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-riscv64-gnu@4.9.1: + resolution: {integrity: sha512-LmYIO65oZVfFt9t6cpYkbC4d5lKHLYv5B4CSHRpnANq0VZUQXGcCPXHzbCXCz4RQnx7jvlYB1ISVNCE/omz5cw==} + cpu: [riscv64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-x64-gnu@4.9.1: + resolution: {integrity: sha512-kr8rEPQ6ns/Lmr/hiw8sEVj9aa07gh1/tQF2Y5HrNCCEPiCBGnBUt9tVusrcBBiJfIt1yNaXN6r1CCmpbFEDpg==} + cpu: [x64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-x64-musl@4.9.1: + resolution: {integrity: sha512-t4QSR7gN+OEZLG0MiCgPqMWZGwmeHhsM4AkegJ0Kiy6TnJ9vZ8dEIwHw1LcZKhbHxTY32hp9eVCMdR3/I8MGRw==} + cpu: [x64] + os: [linux] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-win32-arm64-msvc@4.9.1: + resolution: {integrity: sha512-7XI4ZCBN34cb+BH557FJPmh0kmNz2c25SCQeT9OiFWEgf8+dL6ZwJ8f9RnUIit+j01u07Yvrsuu1rZGxJCc51g==} + cpu: [arm64] + os: [win32] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-win32-ia32-msvc@4.9.1: + resolution: {integrity: sha512-yE5c2j1lSWOH5jp+Q0qNL3Mdhr8WuqCNVjc6BxbVfS5cAS6zRmdiw7ktb8GNpDCEUJphILY6KACoFoRtKoqNQg==} + cpu: [ia32] + os: [win32] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-win32-x64-msvc@4.9.1: + resolution: {integrity: sha512-PyJsSsafjmIhVgaI1Zdj7m8BB8mMckFah/xbpplObyHfiXzKcI5UOUXRyOdHW7nz4DpMCuzLnF7v5IWHenCwYA==} + cpu: [x64] + os: [win32] + requiresBuild: true + dev: true + optional: true + /@rushstack/eslint-patch@1.5.1: resolution: {integrity: sha512-6i/8UoL0P5y4leBIGzvkZdS85RDMG9y1ihZzmTZQ5LdHUYmZ7pKFoj8X0236s3lusPs1Fa5HTQUpwI+UfTcmeA==} dev: true @@ -4446,6 +4737,10 @@ packages: resolution: {integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==} dev: true + /@types/linkify-it@3.0.5: + resolution: {integrity: sha512-yg6E+u0/+Zjva+buc3EIb+29XEg4wltq7cSmd4Uc2EE/1nUVmxyzpX6gUXD0V8jIrG0r7YeOGVIbYRkxeooCtw==} + dev: true + /@types/lodash.merge@4.6.8: resolution: {integrity: sha512-He1g+VBmRclP+6hT6P6zKlzpFoeOLMgPpMGChgINuxbdPumZCIJsITbqSq2cWXzJu2ltmwVN5TfQ6kj0X06rFQ==} dependencies: @@ -4456,6 +4751,13 @@ packages: resolution: {integrity: sha512-BdZ5BCCvho3EIXw6wUCXHe7rS53AIDPLE+JzwgT+OsJk53oBfbSmZZ7CX4VaRoN78N+TJpFi9QPlfIVNmJYWxQ==} dev: false + /@types/markdown-it@13.0.7: + resolution: {integrity: sha512-U/CBi2YUUcTHBt5tjO2r5QV/x0Po6nsYwQU4Y04fBS6vfoImaiZ6f8bi3CjTCxBPQSO1LMyUqkByzi8AidyxfA==} + dependencies: + '@types/linkify-it': 3.0.5 + '@types/mdurl': 1.0.5 + dev: true + /@types/mdast@3.0.10: resolution: {integrity: sha512-W864tg/Osz1+9f4lrGTZpCSO5/z4608eUp19tbozkq2HJK6i3z1kT0H9tlADXuYIb1YYOBByU4Jsqkk75q48qA==} dependencies: @@ -4468,6 +4770,10 @@ packages: '@types/unist': 3.0.1 dev: true + /@types/mdurl@1.0.5: + resolution: {integrity: sha512-6L6VymKTzYSrEf4Nev4Xa1LCHKrlTlYCBMTlQKFuddo1CvQcE52I0mwfOJayueUC7MJuXOeHTcIU683lzd0cUA==} + dev: true + /@types/minimist@1.2.2: resolution: {integrity: sha512-jhuKLIRrhvCPLqwPcx6INqmKeiA5EWrsCOPhrlFSrbrmU4ZMPjj5Ul/oLCMDO98XRUIwVm78xICz4EPCektzeQ==} dev: true @@ -4529,6 +4835,10 @@ packages: resolution: {integrity: sha512-oh8q2Zc32S6gd/j50GowEjKLoOVOwHP/bWVjKJInBwQqdOYMdPrf1oVlelTlyfFK3CKxL1uahMDAr+vy8T7yMQ==} dev: false + /@types/web-bluetooth@0.0.20: + resolution: {integrity: sha512-g9gZnnXVq7gM7v3tJCWV/qw7w+KeOlSHAhgF9RytFyifW6AF61hdT2ucrYhPq9hLs5JIryeupHV3qGk95dH9ow==} + dev: true + /@types/yargs-parser@21.0.0: resolution: {integrity: sha512-iO9ZQHkZxHn4mSakYV0vFHAVDyEOIJQrV2uZ06HxEPcx+mt8swXoZHIbaaJ2crJYFfErySgktuTZ3BeLz+XmFA==} dev: true @@ -4762,6 +5072,17 @@ packages: vite: 4.5.0(@types/node@20.8.10)(terser@5.16.1) vue: 3.2.47 + /@vitejs/plugin-vue@5.0.1(vite@5.0.10)(vue@3.4.1): + resolution: {integrity: sha512-lwvZX5tDhJpRJEKsjoUSWgaD26Lk9X4aDYGAPpr/Q6cLTT3PC8LPu2dsnYEweAZiNgHsbyKL2Svc/CDrFOsbtw==} + engines: {node: ^18.0.0 || >=20.0.0} + peerDependencies: + vite: ^5.0.0 + vue: ^3.2.25 + dependencies: + vite: 5.0.10(@types/node@20.8.10) + vue: 3.4.1(typescript@5.2.2) + dev: true + /@vitest/coverage-v8@0.34.6(vitest@0.34.6): resolution: {integrity: sha512-fivy/OK2d/EsJFoEoxHFEnNGTg+MmdZBAVK9Ka4qhXR2K3J0DS08vcGVwzDtXSuUMabLv4KtPcpSKkcMXFDViw==} peerDependencies: @@ -4873,6 +5194,16 @@ packages: estree-walker: 2.0.2 source-map-js: 1.0.2 + /@vue/compiler-core@3.4.1: + resolution: {integrity: sha512-FBiJi88C2L+REhqhbSRe0ifLSOMFTbB8hj2xkx8gHozVWLnjVFOanibivUaobkNyKem9vJINFXjazYkX2uIjFQ==} + dependencies: + '@babel/parser': 7.23.6 + '@vue/shared': 3.4.1 + entities: 4.5.0 + estree-walker: 2.0.2 + source-map-js: 1.0.2 + dev: true + /@vue/compiler-dom@3.2.47: resolution: {integrity: sha512-dBBnEHEPoftUiS03a4ggEig74J2YBZ2UIeyfpcRM2tavgMWo4bsEfgCGsu+uJIL/vax9S+JztH8NmQerUo7shQ==} dependencies: @@ -4885,6 +5216,13 @@ packages: '@vue/compiler-core': 3.3.7 '@vue/shared': 3.3.7 + /@vue/compiler-dom@3.4.1: + resolution: {integrity: sha512-cftveaDBvtKTcpHDqN+V8b6enBMEOtqJPt/bVZ0gS0+fsyjEP/jIJa1sRXP1IwuOcVgcIXr/9kGMP1qzC0tQiQ==} + dependencies: + '@vue/compiler-core': 3.4.1 + '@vue/shared': 3.4.1 + dev: true + /@vue/compiler-sfc@3.2.47: resolution: {integrity: sha512-rog05W+2IFfxjMcFw10tM9+f7i/+FFpZJJ5XHX72NP9eC2uRD+42M3pYcQqDXVYoj74kHMSEdQ/WmCjt8JFksQ==} dependencies: @@ -4913,6 +5251,20 @@ packages: postcss: 8.4.31 source-map-js: 1.0.2 + /@vue/compiler-sfc@3.4.1: + resolution: {integrity: sha512-h0aWCVSm0uRtGhdM88Gua6lL+wGhiUdHj6BwwBgIaAsms7HK25DzlpnfnCcx4voHDeN9pHmG9jjLBNys/u2Jug==} + dependencies: + '@babel/parser': 7.23.6 + '@vue/compiler-core': 3.4.1 + '@vue/compiler-dom': 3.4.1 + '@vue/compiler-ssr': 3.4.1 + '@vue/shared': 3.4.1 + estree-walker: 2.0.2 + magic-string: 0.30.5 + postcss: 8.4.32 + source-map-js: 1.0.2 + dev: true + /@vue/compiler-ssr@3.2.47: resolution: {integrity: sha512-wVXC+gszhulcMD8wpxMsqSOpvDZ6xKXSVWkf50Guf/S+28hTAXPDYRTbLQ3EDkOP5Xz/+SY37YiwDquKbJOgZw==} dependencies: @@ -4925,6 +5277,13 @@ packages: '@vue/compiler-dom': 3.3.7 '@vue/shared': 3.3.7 + /@vue/compiler-ssr@3.4.1: + resolution: {integrity: sha512-Zjvjc+u7uXS/mmTPxL5bNup7Om9vni4I++JNMDKCeWKHtHN/6G9LmhXU9vGbrdUH9YFVvewk2pjTtzK9CJCoog==} + dependencies: + '@vue/compiler-dom': 3.4.1 + '@vue/shared': 3.4.1 + dev: true + /@vue/composition-api@1.0.0(vue@3.3.7): resolution: {integrity: sha512-VXK5+hk81ngZTgTC9anDwL5jUqh/SGH4BisKheQh3okwqgSESR27McR9DDPfJ9mqba6jJCnlTbWJRFScSoSU1A==} peerDependencies: @@ -4940,7 +5299,6 @@ packages: /@vue/devtools-api@6.5.1: resolution: {integrity: sha512-+KpckaAQyfbvshdDW5xQylLni1asvNSGme1JFs8I1+/H5pHEhqUKMEQD/qn3Nx5+/nycBq11qAEi8lk+LXI2dA==} - dev: false /@vue/reactivity-transform@3.2.47: resolution: {integrity: sha512-m8lGXw8rdnPVVIdIFhf0LeQ/ixyHkH5plYuS83yop5n7ggVJU+z5v0zecwEnX7fa7HNLBhh2qngJJkxpwEEmYA==} @@ -4970,6 +5328,12 @@ packages: dependencies: '@vue/shared': 3.3.7 + /@vue/reactivity@3.4.1: + resolution: {integrity: sha512-3nr59s8lojuXL/ucX+V0GDI70kpA3LC7hT963lN7A+gf33MtQB1ncf6lLxO3GzM+HxfAJjkw/1PR1J6BPpBb1w==} + dependencies: + '@vue/shared': 3.4.1 + dev: true + /@vue/runtime-core@3.2.47: resolution: {integrity: sha512-RZxbLQIRB/K0ev0K9FXhNbBzT32H9iRtYbaXb0ZIz2usLms/D55dJR2t6cIEUn6vyhS3ALNvNthI+Q95C+NOpA==} dependencies: @@ -4982,6 +5346,13 @@ packages: '@vue/reactivity': 3.3.7 '@vue/shared': 3.3.7 + /@vue/runtime-core@3.4.1: + resolution: {integrity: sha512-YRS5pNU7htWa1B7mPIcEHvSG0VjopVMV3BUWwW3/ZYkpgSWTDOpSXoF7AZ/P/uKd0gweCosxcy7Wuw//0uDtyg==} + dependencies: + '@vue/reactivity': 3.4.1 + '@vue/shared': 3.4.1 + dev: true + /@vue/runtime-dom@3.2.47: resolution: {integrity: sha512-ArXrFTjS6TsDei4qwNvgrdmHtD930KgSKGhS5M+j8QxXrDJYLqYw4RRcDy1bz1m1wMmb6j+zGLifdVHtkXA7gA==} dependencies: @@ -4996,6 +5367,14 @@ packages: '@vue/shared': 3.3.7 csstype: 3.1.2 + /@vue/runtime-dom@3.4.1: + resolution: {integrity: sha512-GNSlwBglxscrviChkCYxTYNY6GzAFLP80CPQL3X6u9wI0c8Vc3QUzMAVlBs14+3wgSFZc/xANPPpZVTKSoUg2A==} + dependencies: + '@vue/runtime-core': 3.4.1 + '@vue/shared': 3.4.1 + csstype: 3.1.3 + dev: true + /@vue/server-renderer@3.2.47(vue@3.2.47): resolution: {integrity: sha512-dN9gc1i8EvmP9RCzvneONXsKfBRgqFeFZLurmHOveL7oH6HiFXJw5OGu294n1nHc/HMgTy6LulU/tv5/A7f/LA==} peerDependencies: @@ -5014,34 +5393,118 @@ packages: '@vue/shared': 3.3.7 vue: 3.3.7(typescript@5.2.2) + /@vue/server-renderer@3.4.1(vue@3.4.1): + resolution: {integrity: sha512-ba67d4rO1nL2TUevvp4nXtqXsVpesxrjA1N0dKWEKYwQS+G3xYZx7NpkHchAanlsUPI3EYk2bhTtPHHulIqKig==} + peerDependencies: + vue: 3.4.1 + dependencies: + '@vue/compiler-ssr': 3.4.1 + '@vue/shared': 3.4.1 + vue: 3.4.1(typescript@5.2.2) + dev: true + /@vue/shared@3.2.47: resolution: {integrity: sha512-BHGyyGN3Q97EZx0taMQ+OLNuZcW3d37ZEVmEAyeoA9ERdGvm9Irc/0Fua8SNyOtV1w6BS4q25wbMzJujO9HIfQ==} /@vue/shared@3.3.7: resolution: {integrity: sha512-N/tbkINRUDExgcPTBvxNkvHGu504k8lzlNQRITVnm6YjOjwa4r0nnbd4Jb01sNpur5hAllyRJzSK5PvB9PPwRg==} - /@vueuse/core@9.13.0(@vue/composition-api@1.0.0)(vue@3.3.7): + /@vue/shared@3.4.1: + resolution: {integrity: sha512-ObCj3oQ6nH3otfEz15xsbQhq0oU2gUvOP9aVbzRewcbI6s+cmV78lZ9dlwvsdcTCn50AiRjijdCAfpJonXSbNw==} + dev: true + + /@vueuse/core@10.7.1(vue@3.4.1): + resolution: {integrity: sha512-74mWHlaesJSWGp1ihg76vAnfVq9NTv1YT0SYhAQ6zwFNdBkkP+CKKJmVOEHcdSnLXCXYiL5e7MaewblfiYLP7g==} + dependencies: + '@types/web-bluetooth': 0.0.20 + '@vueuse/metadata': 10.7.1 + '@vueuse/shared': 10.7.1(vue@3.4.1) + vue-demi: 0.14.6(vue@3.4.1) + transitivePeerDependencies: + - vue + dev: true + + /@vueuse/core@9.13.0(vue@3.3.7): resolution: {integrity: sha512-pujnclbeHWxxPRqXWmdkKV5OX4Wk4YeK7wusHqRwU0Q7EFusHoqNA/aPhB6KCh9hEqJkLAJo7bb0Lh9b+OIVzw==} dependencies: '@types/web-bluetooth': 0.0.16 '@vueuse/metadata': 9.13.0 - '@vueuse/shared': 9.13.0(@vue/composition-api@1.0.0)(vue@3.3.7) - vue-demi: 0.14.6(@vue/composition-api@1.0.0)(vue@3.3.7) + '@vueuse/shared': 9.13.0(vue@3.3.7) + vue-demi: 0.14.6(vue@3.3.7) transitivePeerDependencies: - - '@vue/composition-api' - vue dev: false + /@vueuse/integrations@10.7.1(focus-trap@7.5.4)(vue@3.4.1): + resolution: {integrity: sha512-cKo5LEeKVHdBRBtMTOrDPdR0YNtrmN9IBfdcnY2P3m5LHVrsD0xiHUtAH1WKjHQRIErZG6rJUa6GA4tWZt89Og==} + peerDependencies: + async-validator: '*' + axios: '*' + change-case: '*' + drauu: '*' + focus-trap: '*' + fuse.js: '*' + idb-keyval: '*' + jwt-decode: '*' + nprogress: '*' + qrcode: '*' + sortablejs: '*' + universal-cookie: '*' + peerDependenciesMeta: + async-validator: + optional: true + axios: + optional: true + change-case: + optional: true + drauu: + optional: true + focus-trap: + optional: true + fuse.js: + optional: true + idb-keyval: + optional: true + jwt-decode: + optional: true + nprogress: + optional: true + qrcode: + optional: true + sortablejs: + optional: true + universal-cookie: + optional: true + dependencies: + '@vueuse/core': 10.7.1(vue@3.4.1) + '@vueuse/shared': 10.7.1(vue@3.4.1) + focus-trap: 7.5.4 + vue-demi: 0.14.6(vue@3.4.1) + transitivePeerDependencies: + - vue + dev: true + + /@vueuse/metadata@10.7.1: + resolution: {integrity: sha512-jX8MbX5UX067DYVsbtrmKn6eG6KMcXxLRLlurGkZku5ZYT3vxgBjui2zajvUZ18QLIjrgBkFRsu7CqTAg18QFw==} + dev: true + /@vueuse/metadata@9.13.0: resolution: {integrity: sha512-gdU7TKNAUVlXXLbaF+ZCfte8BjRJQWPCa2J55+7/h+yDtzw3vOoGQDRXzI6pyKyo6bXFT5/QoPE4hAknExjRLQ==} dev: false - /@vueuse/shared@9.13.0(@vue/composition-api@1.0.0)(vue@3.3.7): + /@vueuse/shared@10.7.1(vue@3.4.1): + resolution: {integrity: sha512-v0jbRR31LSgRY/C5i5X279A/WQjD6/JsMzGa+eqt658oJ75IvQXAeONmwvEMrvJQKnRElq/frzBR7fhmWY5uLw==} + dependencies: + vue-demi: 0.14.6(vue@3.4.1) + transitivePeerDependencies: + - vue + dev: true + + /@vueuse/shared@9.13.0(vue@3.3.7): resolution: {integrity: sha512-UrnhU+Cnufu4S6JLCPZnkWh0WwZGUp72ktOF2DFptMlOs3TOdVv8xJN53zhHGARmVOsz5KqOls09+J1NR6sBKw==} dependencies: - vue-demi: 0.14.6(@vue/composition-api@1.0.0)(vue@3.3.7) + vue-demi: 0.14.6(vue@3.3.7) transitivePeerDependencies: - - '@vue/composition-api' - vue dev: false @@ -5055,6 +5518,7 @@ packages: /abab@2.0.6: resolution: {integrity: sha512-j2afSsaIENvHZN2B8GOpF566vZ5WVk5opAiMTvWgaQT8DkbOqsTfvNAvHoRGU2zzP8cPoqys+xHTRDWW8L+/BA==} + deprecated: Use your platform's native atob() and btoa() methods instead dev: true /abbrev@2.0.0: @@ -5167,6 +5631,25 @@ packages: uri-js: 4.4.1 dev: true + /algoliasearch@4.22.0: + resolution: {integrity: sha512-gfceltjkwh7PxXwtkS8KVvdfK+TSNQAWUeNSxf4dA29qW5tf2EGwa8jkJujlT9jLm17cixMVoGNc+GJFO1Mxhg==} + dependencies: + '@algolia/cache-browser-local-storage': 4.22.0 + '@algolia/cache-common': 4.22.0 + '@algolia/cache-in-memory': 4.22.0 + '@algolia/client-account': 4.22.0 + '@algolia/client-analytics': 4.22.0 + '@algolia/client-common': 4.22.0 + '@algolia/client-personalization': 4.22.0 + '@algolia/client-search': 4.22.0 + '@algolia/logger-common': 4.22.0 + '@algolia/logger-console': 4.22.0 + '@algolia/requester-browser-xhr': 4.22.0 + '@algolia/requester-common': 4.22.0 + '@algolia/requester-node-http': 4.22.0 + '@algolia/transporter': 4.22.0 + dev: true + /ansi-escapes@3.2.0: resolution: {integrity: sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ==} engines: {node: '>=4'} @@ -6341,6 +6824,10 @@ packages: /csstype@3.1.2: resolution: {integrity: sha512-I7K1Uu0MBPzaFKg4nI5Q7Vs2t+3gWWW648spaF+Rg7pI9ds18Ugn+lvg4SHczUdKlHI5LWBXyqfS8+DufyBsgQ==} + /csstype@3.1.3: + resolution: {integrity: sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==} + dev: true + /cz-conventional-changelog@3.3.0(typescript@5.2.2): resolution: {integrity: sha512-U466fIzU5U22eES5lTNiNbZ+d8dfcHcssH4o7QsdWaCcRs/feIPCxKYSWkYBNs5mny7MvEfwpTLWjvbm94hecw==} engines: {node: '>= 10'} @@ -6641,6 +7128,7 @@ packages: /domexception@2.0.1: resolution: {integrity: sha512-yxJ2mFy/sibVQlu5qHjOkf9J3K6zgmCxgJ94u2EdvDOV09H+32LtRswEcUsmUWN72pVLOEnTSRaIVVzVQgS0dg==} engines: {node: '>=8'} + deprecated: Use your platform's native DOMException instead dependencies: webidl-conversions: 5.0.0 dev: true @@ -6731,6 +7219,11 @@ packages: engines: {node: '>=0.12'} dev: true + /entities@4.5.0: + resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} + engines: {node: '>=0.12'} + dev: true + /env-paths@2.2.1: resolution: {integrity: sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A==} engines: {node: '>=6'} @@ -7960,6 +8453,12 @@ packages: resolution: {integrity: sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ==} dev: true + /focus-trap@7.5.4: + resolution: {integrity: sha512-N7kHdlgsO/v+iD/dMoJKtsSqs5Dz/dXZVebRgJw23LDk+jMi/974zyiOYDziY2JPp8xivq9BmUGwIJMiuSBi7w==} + dependencies: + tabbable: 6.2.0 + dev: true + /for-each@0.3.3: resolution: {integrity: sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==} dependencies: @@ -10175,6 +10674,10 @@ packages: engines: {node: '>=8'} dev: true + /mark.js@8.11.1: + resolution: {integrity: sha512-1I+1qpDt4idfgLQG+BNWmrqku+7/2bi5nLf4YwF8y8zXvmfiTBY3PV3ZibfrjBueCByROpuBjLLFCajqkgYoLQ==} + dev: true + /markdown-it@13.0.1: resolution: {integrity: sha512-lTlxriVoy2criHP0JKRhO2VDG9c2ypWCsT237eDiLqi09rmbKoUetyGHq2uOIRoRS//kfoJckS0eUzzkDR+k2Q==} hasBin: true @@ -10697,6 +11200,10 @@ packages: engines: {node: '>=16 || 14 >=14.17'} dev: true + /minisearch@6.3.0: + resolution: {integrity: sha512-ihFnidEeU8iXzcVHy74dhkxh/dn8Dc08ERl0xwoMMGqp4+LvRSCgicb+zGqWthVokQKvCSxITlh3P08OzdTYCQ==} + dev: true + /minizlib@2.1.2: resolution: {integrity: sha512-bAxsR8BVfj60DWXHE3u30oHzfl4G7khkSuPW+qvpd7jFRHm7dLxOjUk1EHACJ/hxLY8phGJ0YhYHZo7jil7Qdg==} engines: {node: '>= 8'} @@ -10773,6 +11280,11 @@ packages: engines: {node: '>=10'} dev: true + /mrmime@2.0.0: + resolution: {integrity: sha512-eu38+hdgojoyq63s+yTpN4XMBdt5l8HhMhc4VKLO9KM5caLIBvUm4thi7fFaxyTmCKeNnXZ5pAlBwCUnhA09uw==} + engines: {node: '>=10'} + dev: true + /ms@2.0.0: resolution: {integrity: sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==} dev: true @@ -10797,6 +11309,12 @@ packages: engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} hasBin: true + /nanoid@3.3.7: + resolution: {integrity: sha512-eSRppjcPIatRIMC1U6UngP8XFcz8MQWGQdt1MTBQ7NaAmvXDfvNxbvWV3x2y6CdEUciCSsDHDQZbhYaB8QEo2g==} + engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} + hasBin: true + dev: true + /natural-compare-lite@1.4.0: resolution: {integrity: sha512-Tj+HTDSJJKaZnfiuw+iaF9skdPpTo2GtEly5JHnWV/hfv2Qj/9RKsGISQtLh2ox3l5EAGw487hnBee0sIJ6v2g==} dev: true @@ -11587,6 +12105,19 @@ packages: picocolors: 1.0.0 source-map-js: 1.0.2 + /postcss@8.4.32: + resolution: {integrity: sha512-D/kj5JNu6oo2EIy+XL/26JEDTlIbB8hw85G8StOE6L74RQAVVP5rej6wxCNqyMbR4RkPfqvezVbPw81Ngd6Kcw==} + engines: {node: ^10 || ^12 || >=14} + dependencies: + nanoid: 3.3.7 + picocolors: 1.0.0 + source-map-js: 1.0.2 + dev: true + + /preact@10.19.3: + resolution: {integrity: sha512-nHHTeFVBTHRGxJXKkKu5hT8C/YWBkPso4/Gad6xuj5dbptt9iF9NZr9pHbPhBrnT2klheu7mHTxTZ/LjwJiEiQ==} + dev: true + /prelude-ls@1.2.1: resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} engines: {node: '>= 0.8.0'} @@ -12124,6 +12655,27 @@ packages: optionalDependencies: fsevents: 2.3.3 + /rollup@4.9.1: + resolution: {integrity: sha512-pgPO9DWzLoW/vIhlSoDByCzcpX92bKEorbgXuZrqxByte3JFk2xSW2JEeAcyLc9Ru9pqcNNW+Ob7ntsk2oT/Xw==} + engines: {node: '>=18.0.0', npm: '>=8.0.0'} + hasBin: true + optionalDependencies: + '@rollup/rollup-android-arm-eabi': 4.9.1 + '@rollup/rollup-android-arm64': 4.9.1 + '@rollup/rollup-darwin-arm64': 4.9.1 + '@rollup/rollup-darwin-x64': 4.9.1 + '@rollup/rollup-linux-arm-gnueabihf': 4.9.1 + '@rollup/rollup-linux-arm64-gnu': 4.9.1 + '@rollup/rollup-linux-arm64-musl': 4.9.1 + '@rollup/rollup-linux-riscv64-gnu': 4.9.1 + '@rollup/rollup-linux-x64-gnu': 4.9.1 + '@rollup/rollup-linux-x64-musl': 4.9.1 + '@rollup/rollup-win32-arm64-msvc': 4.9.1 + '@rollup/rollup-win32-ia32-msvc': 4.9.1 + '@rollup/rollup-win32-x64-msvc': 4.9.1 + fsevents: 2.3.3 + dev: true + /run-async@2.4.1: resolution: {integrity: sha512-tvVnVv01b8c1RrA6Ep7JkStj85Guv/YrMcwqYQnwjsAS2cTmmPGBBjAjpCW7RrSodNSoE2/qg9O4bceNvUuDgQ==} engines: {node: '>=0.12.0'} @@ -12215,6 +12767,10 @@ packages: resolution: {integrity: sha512-4AsO/FrViE/iDNEPaAQlb77tf0csuq27EsVpy6ett584EcRTp6pTDLoGWVxCD77y5iU5FauOvhsI4o1APwPoSQ==} dev: true + /search-insights@2.13.0: + resolution: {integrity: sha512-Orrsjf9trHHxFRuo9/rzm0KIWmgzE8RMlZMzuhZOJ01Rnz3D0YBAe+V6473t6/H6c7irs6Lt48brULAiRWb3Vw==} + dev: true + /semver@5.7.1: resolution: {integrity: sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==} hasBin: true @@ -12317,6 +12873,22 @@ packages: resolution: {integrity: sha512-6j1W9l1iAs/4xYBI1SYOVZyFcCis9b4KCLQ8fgAGG07QvzaRLVVRQvAy85yNmmZSjYjg4MWh4gNvlPujU/5LpA==} dev: true + /shikiji-core@0.9.15: + resolution: {integrity: sha512-7hqIcUKS15OMs/61Qp2GvO1fSajBB36bDqi8vexIg5kp80V6v6SGtBrlq+nLlo7erMG2d1kvIuTIq1bwKI6fEg==} + dev: true + + /shikiji-transformers@0.9.15: + resolution: {integrity: sha512-k0sQ6tX26/cdb8QV9CCwwr7QjRp6/AVP9C0oNIXNld3of+xCrpf74kD74piybG6vMfzBoHGsz/s60RVBJOUaYQ==} + dependencies: + shikiji: 0.9.15 + dev: true + + /shikiji@0.9.15: + resolution: {integrity: sha512-+inN4cN+nY7b0uCPOiqFHAk+cn2DEdM3AIQgPhAV7QKqhww/o7OGS5xvLh3SNnjke9C/HispALqGOQGYHVq7KQ==} + dependencies: + shikiji-core: 0.9.15 + dev: true + /side-channel@1.0.4: resolution: {integrity: sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==} dependencies: @@ -12943,7 +13515,7 @@ packages: dependencies: '@ampproject/remapping': 2.2.1 '@jridgewell/sourcemap-codec': 1.4.15 - '@jridgewell/trace-mapping': 0.3.18 + '@jridgewell/trace-mapping': 0.3.20 acorn: 8.11.2 aria-query: 5.3.0 axobject-query: 3.2.1 @@ -12976,6 +13548,10 @@ packages: resolution: {integrity: sha512-8ftwWd+XnQtZ/aGbatrN4QFNGrKJzmbtixW+ODpci7pyoTajg4sonPP8aFLESAcuVxaC1FyDESt+SpfFCH9rZQ==} dev: true + /tabbable@6.2.0: + resolution: {integrity: sha512-Cat63mxsVJlzYvN51JmVXIgNoUokrIaT2zLclCXjRd8boZ0004U4KCs/sToJ75C6sdlByWxpYnb5Boif1VSFew==} + dev: true + /table@6.8.1: resolution: {integrity: sha512-Y4X9zqrCftUhMeH2EptSSERdVKt/nEdijTOacGD/97EKjhQ/Qs8RTlEGABSJNNN8lac9kheH+af7yAkEWlgneA==} engines: {node: '>=10.0.0'} @@ -13652,6 +14228,97 @@ packages: optionalDependencies: fsevents: 2.3.3 + /vite@5.0.10(@types/node@20.8.10): + resolution: {integrity: sha512-2P8J7WWgmc355HUMlFrwofacvr98DAjoE52BfdbwQtyLH06XKwaL/FMnmKM2crF0iX4MpmMKoDlNCB1ok7zHCw==} + engines: {node: ^18.0.0 || >=20.0.0} + hasBin: true + peerDependencies: + '@types/node': ^18.0.0 || >=20.0.0 + less: '*' + lightningcss: ^1.21.0 + sass: '*' + stylus: '*' + sugarss: '*' + terser: ^5.4.0 + peerDependenciesMeta: + '@types/node': + optional: true + less: + optional: true + lightningcss: + optional: true + sass: + optional: true + stylus: + optional: true + sugarss: + optional: true + terser: + optional: true + dependencies: + '@types/node': 20.8.10 + esbuild: 0.19.5 + postcss: 8.4.32 + rollup: 4.9.1 + optionalDependencies: + fsevents: 2.3.3 + dev: true + + /vitepress@1.0.0-rc.33(@algolia/client-search@4.22.0)(@types/node@20.8.10)(postcss@8.4.31)(search-insights@2.13.0)(typescript@5.2.2): + resolution: {integrity: sha512-XMwr5eXEB3KB1uCuOkojVaqsVSijmd6N9QmaM2M6aqJqzXzxNwuvWSiEGYl4qbwRAX6/nFRofhx9+FndtCNjGQ==} + hasBin: true + peerDependencies: + markdown-it-mathjax3: ^4.3.2 + postcss: ^8.4.32 + peerDependenciesMeta: + markdown-it-mathjax3: + optional: true + postcss: + optional: true + dependencies: + '@docsearch/css': 3.5.2 + '@docsearch/js': 3.5.2(@algolia/client-search@4.22.0)(search-insights@2.13.0) + '@types/markdown-it': 13.0.7 + '@vitejs/plugin-vue': 5.0.1(vite@5.0.10)(vue@3.4.1) + '@vue/devtools-api': 6.5.1 + '@vueuse/core': 10.7.1(vue@3.4.1) + '@vueuse/integrations': 10.7.1(focus-trap@7.5.4)(vue@3.4.1) + focus-trap: 7.5.4 + mark.js: 8.11.1 + minisearch: 6.3.0 + mrmime: 2.0.0 + postcss: 8.4.31 + shikiji: 0.9.15 + shikiji-transformers: 0.9.15 + vite: 5.0.10(@types/node@20.8.10) + vue: 3.4.1(typescript@5.2.2) + transitivePeerDependencies: + - '@algolia/client-search' + - '@types/node' + - '@types/react' + - async-validator + - axios + - change-case + - drauu + - fuse.js + - idb-keyval + - jwt-decode + - less + - lightningcss + - nprogress + - qrcode + - react + - react-dom + - sass + - search-insights + - sortablejs + - stylus + - sugarss + - terser + - typescript + - universal-cookie + dev: true + /vitest@0.34.6(@vitest/ui@0.34.6): resolution: {integrity: sha512-+5CALsOvbNKnS+ZHMXtuUC7nL8/7F1F2DnHGjSsszX8zCjWSSviphCb/NuS9Nzf4Q03KyyDRBAXhF/8lffME4Q==} engines: {node: '>=v14.18.0'} @@ -13718,7 +14385,7 @@ packages: - terser dev: true - /vue-demi@0.14.6(@vue/composition-api@1.0.0)(vue@3.3.7): + /vue-demi@0.14.6(vue@3.3.7): resolution: {integrity: sha512-8QA7wrYSHKaYgUxDA5ZC24w+eHm3sYCbp0EzcDwKqN3p6HqtTCGR/GVsPyZW92unff4UlcSh++lmqDWN3ZIq4w==} engines: {node: '>=12'} hasBin: true @@ -13730,10 +14397,24 @@ packages: '@vue/composition-api': optional: true dependencies: - '@vue/composition-api': 1.0.0(vue@3.3.7) vue: 3.3.7(typescript@5.2.2) dev: false + /vue-demi@0.14.6(vue@3.4.1): + resolution: {integrity: sha512-8QA7wrYSHKaYgUxDA5ZC24w+eHm3sYCbp0EzcDwKqN3p6HqtTCGR/GVsPyZW92unff4UlcSh++lmqDWN3ZIq4w==} + engines: {node: '>=12'} + hasBin: true + requiresBuild: true + peerDependencies: + '@vue/composition-api': ^1.0.0-rc.1 + vue: ^3.0.0-0 || ^2.6.0 + peerDependenciesMeta: + '@vue/composition-api': + optional: true + dependencies: + vue: 3.4.1(typescript@5.2.2) + dev: true + /vue-eslint-parser@9.3.1(eslint@8.53.0): resolution: {integrity: sha512-Clr85iD2XFZ3lJ52/ppmUDG/spxQu6+MAeHXjjyI4I1NUYZ9xmenQp4N0oaHJhrA8OOxltCVxMRfANGa70vU0g==} engines: {node: ^14.17.0 || >=16.0.0} @@ -13797,6 +14478,22 @@ packages: '@vue/shared': 3.3.7 typescript: 5.2.2 + /vue@3.4.1(typescript@5.2.2): + resolution: {integrity: sha512-KWFPZC8TW+g/Gg4ALIVZixwhzqdRKjyfN3NdH9jiYGhWlOX8vT2d9wZhsShTjS9wkKyohtDhPFYiwV255TdANA==} + peerDependencies: + typescript: '*' + peerDependenciesMeta: + typescript: + optional: true + dependencies: + '@vue/compiler-dom': 3.4.1 + '@vue/compiler-sfc': 3.4.1 + '@vue/runtime-dom': 3.4.1 + '@vue/server-renderer': 3.4.1(vue@3.4.1) + '@vue/shared': 3.4.1 + typescript: 5.2.2 + dev: true + /w3c-hr-time@1.0.2: resolution: {integrity: sha512-z8P5DvDNjKDoFIHK7q8r8lackT6l+jo/Ye3HOle7l9nICP9lf1Ci25fy9vHd0JOWewkIFzXIEig3TdKT7JQ5fQ==} deprecated: Use your platform's native performance.now() and performance.timeOrigin.