Pinia
Pinia是一个全新的Vue状态管理库,是Vuex的代替者,尤雨溪强势推荐
- Vue2 和 Vue3 都能支持
- 抛弃传统的
Mutations,只有state, getter和actions,简化状态管理库 - 不需要嵌套模块,符合 Vue3 的 Composition api,让代码扁平化
- TypeScript支持
- 代码简介,很好的代码自动分割
- 足够轻量,压缩后的体积只有1.6kb;
语法
安装
bash
cnpm i pinia@2.0.4 -S注册
src/main.ts
js
import {createPinia} from 'pinia'
const store = createPinia()
app.use(store)定义仓库
pinia仓库有三个配置项:
- state:用来定义数据
- getters:用来定义计算属性
- getters里的计算属性有一个形参state,可以通过
state.键访问state数据,也可以通过this.键访问
- getters里的计算属性有一个形参state,可以通过
- actions:用来定义方法
src/store/users.ts
js
// 导入 defineStore
import {defineStore} from 'pinia'
// 标识代表模块化
export const useUserStore = defineStore(标识, {
state: () => { // 定义数据
return {
num:1,
num2:2
}
},
getters: { // 定义计算属性
get(state){
// return this.num+this.num2
return state.num+state.num2
}
},
actions: { //定义方法
async fn() {
this.state键 = 数据
},
fn2() {
// 调用自身方法
this.fn()
}
}
})使用数据
注意:需要使用storeToRefs()将pinia数据变成响应式
vue
<script setup>
// 导入
import { useUserStore } from 'src/store/users.ts'
import { storeToRefs } from 'pinia'
// 创建store
const store = useUserStore()
// 获取state数据
store.键
// 获取getters数据
const 键 = computed( () => store.键 )
// 获取state数据并变成响应式
const 键 = ref(store.键)
// 解构变成响应式
const {键1,....,键n} = storeToRefs(store)
</script>使用action中的方法
js
store.action中的方法名()更新数据
js
// 单条直接改
store.键 = 数据
// 多条批量改
store.$patch({
键: 数据,
键2:数据2,
// ...
})响应式数据
通过传统的解构赋值,获得的值不具有响应性
需要使用storeToRefs()解构
js
import { storeToRefs } from "pinia";
import { useCommonStore } from "@/store/useCommonStroe";
const commonStore = useCommonStore();
const { num, num2 } = storeToRefs(commonStore);
// 更新单条数据,仍需要使用store.键=?更新
const handleUpd = () => {
store.num1++
};
// 更新多条数据
const handleUpd = () => {
commonStore.$patch({
num: num.value + 1,
num2: num2.value + 1,
});
};函数写法
pinia的函数写法可以使用vue3的composition api定义数据
注意:函数写法的每一个需要用到的数据都必须return出去
定义数据
js
import { ref, computed } from 'vue'
import { defineStore } from 'pinia'
export const useCounterStore = defineStore('counter', () => {
//定义属性
const num1 = ref(5)
const num2 = ref(10)
//定义计算属性
const sum = computed(() => {
return num1.value + num2.value
})
//定义方法
const add = () => {
num1.value++
}
return {
num1,
num2,
sum,
add
}
})使用数据
vue
<script setup>
import { useCounterStore } from './stores/counter'
const store = useCounterStore()
// 调用store方法
const addNum1 = () => {
store.add()
}
// 直接修改store数据
const addNum2 = () => {
store.num2++
}
</script>
<template>
<div class="">num1:{{ store.num1 }}</div>
<div class="">num2:{{ store.num2 }}</div>
<div class="">num2:{{ store.sum }}</div>
<button @click="addNum1">num1++</button>
<button @click="addNum2">num2++</button>
</template>数据持久化
安装
sh
npm i pinia-plugin-persist使用
src/main.js
js
import { createPinia } from 'pinia'
import piniaPluginPersist from 'pinia-plugin-persist'
const store = createPinia()
store.use(piniaPluginPersist)
app.use(store)开启缓存
对象写法
js
export const useUserStore = defineStore({
id: 'user',
state: () => {
return {
name: '张三'
}
},
// 开启数据缓存
persist: {
enabled: true
}
})函数写法
js
import {ref} from 'vue'
export const useUserStore = defineStore(
'user',
()=>{
const conut=ref(10)
return {count}
},
{
persist: {
enabled: true
}
}
)自定义key
开启数据缓存默认存储在sessionStorage中
可以在persist的strategies 里自定义 key 值,并将存放位置由 sessionStorage 改为 localStorage。
js
persist: {
enabled: true,
strategies: [
{
key: 'my_user',
storage: localStorage,
},
]
}持久化部分state
默认所有 state 都会进行缓存,可以通过 paths 指定要持久化的字段,其他的则不会进行持久化。
js
state: () => {
return {
name: '张三',
age: 18,
gender: '男'
}
},
persist: {
enabled: true,
strategies: [
{
storage: localStorage,
paths: ['name', 'age']
}
]
}上面我们只持久化 name 和 age,并将其改为localStorage, 而 gender 不会被持久化,如果其状态发生更改,页面刷新时将会丢失,重新回到初始状态,而 name 和 age 则不会。
