一个用于 UniApp 项目的 Pinia 持久化插件

一个面向 UniApp 的 Pinia 持久化插件:pinia-plugin-uni-persist-next

在 Vue 3 + Pinia 项目中,store 默认只存在于内存里。页面刷新、App 重启或小程序重新进入后,状态都会回到初始值。

UniApp 项目通常需要同时兼容 H5、App 和小程序,直接依赖 localStorage 并不合适。因此,这个插件基于 UniApp 的 storage API,提供了一套 Pinia 状态持久化方案。

@rdeam/pinia-plugin-uni-persist-next 主要用于在 UniApp 项目中自动保存和恢复 Pinia store。

安装

perl 复制代码
pnpm add @rdeam/pinia-plugin-uni-persist-next

基本使用

先在 Pinia 初始化时注册插件:

javascript 复制代码
import { createPinia } from 'pinia';
import { createUniPersistPlugin } from '@rdeam/pinia-plugin-uni-persist-next';

const pinia = createPinia();

pinia.use(
  createUniPersistPlugin({
    keyPrefix: 'app_storage_',
  }),
);

然后在需要持久化的 store 里开启 persist

javascript 复制代码
import { defineStore } from 'pinia';

export const useUserStore = defineStore('user', {
  state: () => ({
    token: '',
    userInfo: null,
  }),
  persist: {
    enabled: true,
    strategies: [
      {
        key: 'user',
        paths: ['token'],
      },
    ],
  },
});

上面这个例子只会持久化 token,不会保存整个 userInfo

为什么需要 paths

不是所有状态都适合持久化。

比如用户 token、语言设置、主题设置,这类数据通常可以保存。

但列表数据、临时弹窗状态、接口返回的大对象,不一定适合长期放进 storage。

所以插件提供了 paths

yaml 复制代码
persist: {
  enabled: true,
  strategies: [
    {
      key: 'user',
      paths: ['token'],
    },
  ],
}

paths 目前只支持顶层字段。也就是说,['token'] 可以,['user.info.name'] 这种深层路径不是当前版本的能力。

多策略保存

一个 store 可以配置多个保存策略:

css 复制代码
persist: {
  enabled: true,
  strategies: [
    {
      key: 'user_token',
      paths: ['token'],
    },
    {
      key: 'user_profile',
      paths: ['userInfo'],
    },
  ],
}

这适合把不同字段拆到不同 storage key 里。比如 token 和用户资料可以分开管理。

同步恢复,默认异步写入

插件恢复数据时使用 uni.getStorageSync,这样 store 初始化时就可以尽快拿到本地数据。

写入时默认使用 uni.setStorage

yaml 复制代码
persist: {
  enabled: true,
  async: true,
}

如果希望写入也使用同步 API,可以这样配置:

yaml 复制代码
persist: {
  enabled: true,
  async: false,
}

也可以在单个策略上覆盖:

yaml 复制代码
persist: {
  enabled: true,
  strategies: [
    {
      key: 'user',
      paths: ['token'],
      async: false,
    },
  ],
}

恢复前后的钩子

插件提供了两个钩子:

javascript 复制代码
persist: {
  enabled: true,
  beforeRestore(ctx) {
    console.log('恢复前', ctx.store.$id);
  },
  afterRestore(ctx) {
    console.log('恢复后', ctx.store.$id);
  },
}

这两个钩子适合做日志、埋点,或者在恢复前后处理一些简单逻辑。

清理 storage

插件也提供了两个工具方法:

javascript 复制代码
import { clearAll, clearStore } from '@rdeam/pinia-plugin-uni-persist-next';

clearStore('app_storage_user');
clearAll();

需要注意:clearAll() 调用的是 uni.clearStorageSync(),会清空当前应用的 storage,不只清理这个插件写入的数据。业务项目里使用时要谨慎。

数据序列化说明

storage 最终保存的是字符串,所以插件内部会做 JSON 序列化。

当前版本对以下数据做了处理:

  • Date:保存时会转成带标记的对象,恢复时再转回 Date
  • BigInt:保存时会转成字符串,避免 JSON.stringify 报错
  • 循环引用:保存时会使用占位字符串,避免序列化直接失败

这里需要说清楚:BigInt 当前恢复后是字符串,不是 bigint。如果业务强依赖 bigint 类型,需要在读取后自行转换,或者等待后续版本支持完整还原。

适合什么场景

这个插件比较适合这些场景:

  • UniApp 项目使用 Pinia 管理状态
  • 需要保存 token、用户偏好、简单配置
  • 希望 store 初始化时自动恢复本地数据
  • 不想在每个 store 里手写 uni.setStorage

不太适合这些场景:

  • 需要保存大量列表数据
  • 需要复杂的深层字段选择
  • 需要加密、过期时间、版本迁移等高级能力
  • 对 BigInt、Map、Set 等复杂类型有完整还原要求

这些能力可以在业务层处理,也可以作为插件后续版本的演进方向。

小结

@rdeam/pinia-plugin-uni-persist-next 不是一个复杂插件,它主要解决的是 UniApp 项目里 Pinia 状态持久化的基础问题:

  • store 开启配置后自动保存
  • 应用启动时自动恢复
  • 支持 key 前缀
  • 支持字段筛选
  • 支持同步或异步写入
  • 基于 UniApp storage API,适合多端项目

如果项目里只是想稳定保存 token、设置项、用户偏好这类轻量状态,它可以减少不少重复代码。对于更复杂的数据持久化需求,建议结合业务场景继续封装。

相关推荐
凌涘1 小时前
JS 八大基本类型:一场内存视角的冒险之旅
前端·javascript
心之所向vjuif1 小时前
使用 Gemini 解决前端代码报错问题
前端
数据知道1 小时前
视觉伪装(上):Canvas 指纹生成原理与 Skia 图形库底层注入噪声
开发语言·javascript·ecmascript·数据采集·指纹浏览器
文阿花1 小时前
Echarts实现自定旋转3D饼状图
javascript·3d·echarts·饼状图
San813_LDD2 小时前
[深度学习] 数据序列化格式对比:以日志级别配置为例
xml·java·前端
meilindehuzi_a2 小时前
深入理解 JavaScript 的同步与异步机制:从单线程设计到 Promise 核心应用
开发语言·javascript·ecmascript
如烟花的信页2 小时前
加速乐cookie逆向分析
javascript·爬虫·python·js逆向
永远的WEB小白2 小时前
css改变svg图标的颜色
前端·javascript·css
lfwh2 小时前
探针程序技术解析:基于 Spring Boot 非 Web 模式的云服务监控告警系统
前端·spring boot·后端