深入了解Vue Pinia持久化存储二次封装

 更新时间:2023年12月21日 16:52:36   作者:前端老K  
Pinia 是2019年由vue.js官方成员重新设计的新一代状态管理库,类似Vuex,下面我们就来学习一下如何通过Pinia实现持久化存储的相关知识,感兴趣的小伙伴可以了解下

什么是 Pinia 

Pinia 是2019年由vue.js官方成员重新设计的新一代状态管理库,类似Vuex。这里就不过多介绍,具体Pinia使用方法可以参考 Pinia 主页。

下面我们一起研究一下基于Pinia开发的持久化存储插件

什么是持久化存储

简单的说就是浏览器缓存与Store之间相互同步;我们在使用常规的Store存储的时候,会遇到刷新页面状态库就会被重置,这让我们很苦恼;
通常遇到这个问题,我们很容易想到用sessionStorage或者localStorage来存储相应的数据,当存储store变多时,就麻烦了,需要写一堆的废代码,不好阅读也不美观。

有没有更好的办法呢?pinia-plugin-persist 就很好的解决的这个问题; 但在实际使用中,发现一个不方便的地方,该插件是以模块来存储的,一个store就是一模块,有时候我们需要一个一个字段去存,比如登录我们就只需要存个userInfo字段就行;为了处理类似这种情况在pinia-plugin-persist基础上进行了升级改造。

相关源码

index.d.ts

interface PersistStrategy {
  key?: string
  storage?: Storage
  paths?: string[]
}
interface PersistOptions {
  enabled: true
  strategies?: PersistStrategy[]
}
declare module 'pinia' {
  interface DefineStoreOptionsBase<S, Store> {
    persist?: PersistOptions
  }
}

export { PersistOptions, PersistStrategy }

pinia-store-persist.ts

import { PiniaPluginContext } from 'pinia'
import { PersistStrategy } from '../pinia-persist'

type Store = PiniaPluginContext['store']
type PartialState = Partial<Store['$state']>

// 更新本地缓存
export const updateStorage = (strategy: PersistStrategy, store: Store) => {
  const storage = strategy?.storage || sessionStorage
  const paths = strategy?.paths || []
  if (strategy.key) {
    // 判断是否按照模块缓存
    const state = paths.reduce((obj, key) => {
      obj[key] = store.$state[key]
      return obj
    }, {} as PartialState)
    storage.setItem(strategy.key, JSON.stringify(state))
  } else {
    // 单个缓存
    paths.forEach((key) => {
      const state = store.$state[key]
      storage.setItem(key, JSON.stringify(state))
    })
  }
}

export default ({ options, store }: PiniaPluginContext): void => {
  // 判断插件功能是否开启
  if (options.persist?.enabled) {
    // 默认策略实例
    const defaultStrategy = [
      {
        key: store.$id,
        storage: sessionStorage,
        paths: []
      }
    ]

    const strategies = options.persist?.strategies?.length ? options.persist?.strategies : defaultStrategy

    strategies.forEach((strategy) => {
      const storage = strategy?.storage || sessionStorage
      const paths = strategy?.paths || []
      if (strategy.key) {
        const result = storage.getItem(strategy.key)
        result && store.$patch(JSON.parse(result))
      } else {
        paths.forEach((key) => {
          const result = storage.getItem(key)
          if (result) {
            const obj: { [key: string]: any } = {}
            obj[key] = JSON.parse(result)
            // 同步更新store数据
            store.$patch(obj)
          }
        })
      }
    })

    // 监听state变化,同步更新storage
    store.$subscribe(() => {
      strategies.forEach((strategy) => {
        updateStorage(strategy, store)
      })
    })
  }
}

引入

store/index.ts

import { createPinia } from 'pinia'
import piniaStorePersist from '@/plugins/pinia-persist/pinia-store-persist'

const store = createPinia().use(piniaStorePersist)

export default store

使用

export const CommonStore = defineStore('common', {
  //...
  persist: {
    enabled: true,
    strategies: [
      {
        storage: localStorage,
        paths: ['userInfo']
      }
    ]
  }
})

到此这篇关于深入了解Vue Pinia持久化存储二次封装的文章就介绍到这了,更多相关Vue Pinia存储内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Vue3中的事件总线详解

    Vue3中的事件总线详解

    在Vue3中,推荐使用CompositionAPI和第三方库mitt来实现事件总线,而不是Vue2中使用Vue实例的方式
    2026-01-01
  • 详解vuex数据传输的两种方式及this.$store undefined的解决办法

    详解vuex数据传输的两种方式及this.$store undefined的解决办法

    这篇文章主要介绍了vuex数据传输的两种方式 及 this.$store undefined的解决办法,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2019-08-08
  • vue自定义数字输入框组件

    vue自定义数字输入框组件

    这篇文章主要为大家详细介绍了vue自定义数字输入框组件,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2022-06-06
  • 前端vue3使用axios调用后端接口的实现方法

    前端vue3使用axios调用后端接口的实现方法

    vue本身不支持ajax接口的请求,所以在vue中经常使用axios这个接口请求工具,下面这篇文章主要给大家介绍了关于前端vue3使用axios调用后端接口的实现方法,需要的朋友可以参考下
    2022-12-12
  • Vue中使用eslint和editorconfig方式

    Vue中使用eslint和editorconfig方式

    这篇文章主要介绍了Vue中使用eslint和editorconfig方式,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-05-05
  • vue一步到位的实现动态路由

    vue一步到位的实现动态路由

    这篇文章主要介绍了vue一步到位的实现动态路由,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-06-06
  • Vue消息订阅与发布过程

    Vue消息订阅与发布过程

    发布-订阅模式是一种设计模式,通过事件中心实现对象间的解耦通信,在Vue中,Vue2使用Vue实例作为事件总线,Vue3推荐使用mitt库,发布-订阅模式适用于广播通知、解耦组件和复杂状态管理,在选择工具时,建议根据场景选择合适的工具
    2025-11-11
  • vue实现图片平铺方式

    vue实现图片平铺方式

    在Vue中,实现图片或组件的平铺布局并允许用户进行修改,可以通过数据绑定、模板编写与交互设计来实现图片平铺,使用v-for指令和动态组件,可以创建可编辑的组件平铺布局,允许用户通过点击触发编辑操作,通过外部编辑面板修改属性后保存更改
    2024-10-10
  • VUE.CLI4.0配置多页面入口的实现

    VUE.CLI4.0配置多页面入口的实现

    这篇文章主要介绍了VUE.CLI4.0配置多页面入口的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2019-11-11
  • 使用element组件table表格实现某条件下复选框无法勾选

    使用element组件table表格实现某条件下复选框无法勾选

    这篇文章主要介绍了使用element组件table表格实现某条件下复选框无法勾选问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-03-03

最新评论