Vue3全家桶三: pinia状态管理
概述
Pinia 是一个轻量级、响应式的状态管理库,用于 Vue.js 应用程序中。基于 Vue3 的状态管理,它的设计理念是简单、轻量和可扩展。与 Vuex 和其他一些状态管理库不同,Pinia 不需要通过特定的插件或模块来完成应用程序状态的存储,它可以独立使用,并且与 Vue3 生态系统无缝集成。Pinia本质上依然是一个状态管理的库,用于跨组件、跨页面进行状态共享。这点与VueX不一样!
优点
- 更好的ts类型支持
- 极致轻量化
- 更加灵活的状态管理
- 代码结构直观清晰
pinia中主要使用的几个组件
- Store:相当于 Vuex 中的 Store,它用于存储全局状态数据。
- State:相当于 Vuex 中的 State,它用于存储 Store 中的状态数据。
- Getter:相当于 Vuex 中的 Getter,它用于获取 Store 中的状态数据。
- Action:相当于 Vuex 中的 Action,它用于处理异步操作。
- Mutation:相当于 Vuex 中的 Mutation,它用于改变 Store 中的状态数据。
createPinia
createPinia
是 Pinia 的一个工厂函数,用于创建一个全局的 Pinia 实例。它可以在 Vue 应用程序中使用,以便将 Pinia 集成到应用程序的任何组件中。createPinia
的目的是为了确保所有的 Store 都能够共享同一个状态树,并且在应用程序中可以方便地进行访问和维护。
全局pinia实例的作用
全局pinia实例在 Vue 应用程序中更方便地进行状态管理
- 支持多 Store:使用全局的 Pinia 实例可以支持多个 Store,并且可以在应用程序的任何组件中使用。
- 提供统一的状态树:Pinia 的全局实例可以确保所有的 Store 都共享同一个状态树,这使得组件之间的数据交互更加简洁高效。
- 代码风格更加优雅:使用全局的 Pinia 实例可以让我们在组件中更加专注于业务逻辑的实现,而不必关注状态管理的具体细节。
- 状态管理更加灵活:使用全局的 Pinia 实例可以灵活地组合和管理不同的 Store,使得我们可以将应用程序的状态分解为多个模块,并根据需要加载或卸载不同的模块。
defineStore
它用于定义一个 Store。使用此 API 可以创建一个 Store 实例,其中包含了状态数据、操作等。defineStore
的作用有以下几个:
- 定义状态:使用
state
选项可以定义 Store 的状态数据,Pinia 将这些数据存储在响应式对象中。 - 定义 Getter:使用
getters
选项可以定义 Store 的 Getter,Getter 可以用于计算或获取 Store 状态的值。 - 定义 Action:使用
actions
选项可以定义 Store 的 Action,Action 用于执行异步操作并更改 Store 中的状态数据。 - 定义 Mutation:使用
mutations
选项可以定义 Store 的 Mutation,Mutation 用于同步更改 Store 中的状态数据。 - 共享状态:通过 Pinia 提供的 API,可以轻松地从一个 Store 中读取或更改另一个 Store 的状态数据。
- TypeScript 支持:
defineStore
支持 TypeScript,并且会在编辑器中提供良好的代码提示和类型检查。
pinia的使用
安装
npm install pinia
//或者
yarn add pinia
创建全局pinia实例并集成到VueApp中
import { createPinia } from "pinia";
const pinia = createPinia()
export default pinia
import { createApp } from 'vue'
import App from './App.vue'
import pinia from './stores'
createApp(App).use(pinia).mount('#app')
创建store实例跟踪应用各自组件状态
import { getcityData } from "@/serivices/index";
import { defineStore } from "pinia";
const useCityStore = defineStore("city", {
state() {
return {
allCities: {},
clickCity: { cityName: "广州" }
}
},
actions: {
async fetchAllCityDataAction() {
const res = await getcityData()
this.allCities = res.data.data
}
}
})
export default useCityStore
使用store(状态)
注意Store获取到后不能被解构,那么会失去响应式: 为了从 Store 中提取属性同时保持其响应式,您需要使用storeToRefs()。
import { storeToRefs } from 'pinia';
import useCityStore from '@/store/modules/home-city'
const cityStore = useCityStore()
cityStore.fetchAllCityDataAction()
const { allCities } = storeToRefs(cityStore)
state的使用
其他的方法也是类似, 直接使用即可, 类似state的使用。
store
import { defineStore } from "pinia";
const useUser = defineStore("user", {
state: () =>({
name: "messi",
age: 33,
club: "巴黎圣日尔曼"
}),
getters: {
useName(state) {
return state.name
}
}
})
export default useUser
在逻辑中使用
<script setup>
import useUser from '@/stores/user';
const userStore = useUser()
function changeUse() {
// 一次性修改多个store中的状态
userStore.$patch({
name: "kobe",
age: 37,
club: "Lakers"
})
}
function reSet() {
// 回到上一次操作之前
userStore.$reset()
}
</script>
在模板中使用
<template>
<div class="app">
<h2>name: {{ userStore.name }}</h2>
<h2>age: {{ userStore.age }}</h2>
<h2>club: {{ userStore.club }}</h2>
</div>
</template>
会使用到的一些方法
$reset()
是 Vue.js 组件实例上的一个方法,用于重置组件的状态。
$patch()
是 Vue.js 组件实例上的一个方法,用于部分更新组件状态。
转载自:https://juejin.cn/post/7233231723210965050