重生之我在学Vue--第6天 Vue 3 状态管理(Pinia)
重生之我在学Vue–第6天 Vue 3 状态管理(Pinia)
文章目录
- 重生之我在学Vue--第6天 Vue 3 状态管理(Pinia)
- 前言
- 一、Pinia 核心概念速览
- 1.1 为什么需要状态管理?
- 1.2 Pinia 核心三要素
- 二、Pinia 快速上手
- 2.1 安装与初始化
- 2.2 创建第一个 Store
- 三、模块化状态管理
- 3.1 多 Store 场景
- 3.2 Store 间通信
- 四、在组件中使用 Pinia
- 4.1 状态访问与修改
- 4.2 状态解构的陷阱
- 五、进阶开发技巧
- 5.1 持久化存储插件
- 5.2 状态重置与订阅
- 六、常见问题解答
- Q1:Pinia 和 Vuex 有什么区别?
- Q2:如何调试 Pinia 状态?
- 今日任务:构建任务管理模块
前言
当项目发展到多组件共享状态时,单纯依靠父子组件通信会变得难以维护。Pinia 作为 Vue 3 官方推荐的状态管理工具,提供更清晰的逻辑分层和响应式状态管理。今天我们将学习如何用 Pinia 实现全局状态管理,并构建可维护的任务管理模块。
Vue3 官方中文文档传送点: 简介 | Vue.js
Vue3 的中文官方文档学习笔记很全还有练习场,推荐去官网学习
Vue前端成仙之路:Vue 前端成仙之路_野生的程序媛的博客-CSDN博客
GO后端成神之路:Go 后端成神之路_野生的程序媛的博客-CSDN博客
一、Pinia 核心概念速览
1.1 为什么需要状态管理?
当遇到以下场景时,需引入状态管理:
- 多个组件依赖同一状态(如用户登录信息)
- 跨层级组件需要修改同一状态
- 需要跟踪复杂的状态变更历史
1.2 Pinia 核心三要素
概念 | 作用 | 示例场景 |
---|---|---|
State | 存储全局响应式数据 | tasks: [] 任务列表 |
Getters | 基于 State 的派生数据(计算属性) | completedTasksCount |
Actions | 修改 State 的业务逻辑 | addTask() , deleteTask() |
二、Pinia 快速上手
2.1 安装与初始化
bash
npm install pinia
javascript
// main.js
import { createPinia } from 'pinia'
const app = createApp(App)
app.use(createPinia())
app.mount('#app')
2.2 创建第一个 Store
javascript
// stores/taskStore.js
import { defineStore } from 'pinia'
export const useTaskStore = defineStore('task', {
state: () => ({
tasks: [],
filter: 'all' // all/completed/active
}),
getters: {
filteredTasks() {
return this.tasks.filter(task => {
if (this.filter === 'completed') return task.completed
if (this.filter === 'active') return !task.completed
return true
})
}
},
actions: {
addTask(title) {
this.tasks.push({
id: Date.now(),
title,
completed: false
})
},
toggleTask(id) {
const task = this.tasks.find(t => t.id === id)
if (task) task.completed = !task.completed
}
}
})
三、模块化状态管理
3.1 多 Store 场景
bash
src/
stores/
taskStore.js # 任务管理模块
userStore.js # 用户模块
configStore.js # 系统配置模块
3.2 Store 间通信
javascript
// stores/userStore.js
export const useUserStore = defineStore('user', {
actions: {
logout() {
const taskStore = useTaskStore()
taskStore.$reset() // 退出时清空任务状态
}
}
})
四、在组件中使用 Pinia
4.1 状态访问与修改
vue
<script setup>
import { useTaskStore } from '@/stores/taskStore'
const taskStore = useTaskStore()
// 直接访问状态
console.log(taskStore.tasks)
// 调用 Action
const handleAdd = () => taskStore.addTask(newTask.value)
</script>
<template>
<div v-for="task in taskStore.filteredTasks" :key="task.id">
{{ task.title }}
<button @click="taskStore.toggleTask(task.id)">切换状态</button>
</div>
</template>
4.2 状态解构的陷阱
javascript
// ❌ 错误:破坏响应性
const { tasks } = storeToRefs(taskStore)
// ✅ 正确方式
import { storeToRefs } from 'pinia'
const { tasks } = storeToRefs(taskStore)
五、进阶开发技巧
5.1 持久化存储插件
bash
npm install pinia-plugin-persistedstate
javascript
// main.js
import { createPinia } from 'pinia'
import piniaPluginPersistedstate from 'pinia-plugin-persistedstate'
const pinia = createPinia()
pinia.use(piniaPluginPersistedstate)
javascript
// 在 Store 中启用
export const useTaskStore = defineStore('task', {
persist: true, // 开启持久化
state: () => ({ /* ... */ })
})
5.2 状态重置与订阅
javascript
// 重置单个 Store
taskStore.$reset()
// 订阅状态变化
taskStore.$subscribe((mutation, state) => {
console.log('状态变化:', mutation.type, state)
})
六、常见问题解答
Q1:Pinia 和 Vuex 有什么区别?
特性 | Pinia | Vuex |
---|---|---|
Vue 3 支持 | 原生支持 | 需要兼容版本 |
TypeScript | 完美支持 | 需要额外配置 |
代码结构 | 更简洁的 Composition API | 基于 Options API |
模块化 | 天然多 Store 设计 | 需要分 modules |
Q2:如何调试 Pinia 状态?
- 安装 Vue Devtools
- 在浏览器开发者工具中查看 Pinia 标签页
- 实时查看状态变化和时间旅行调试
今日任务:构建任务管理模块
-
创建
taskStore
实现以下功能:- 任务增删改查
- 按状态过滤任务
- s任务统计(总数/完成数)
-
在组件中集成:
vue
<template> <div> <input v-model="newTask" @keyup.enter="addTask"> <select v-model="taskStore.filter"> <option value="all">全部</option> <option value="completed">已完成</option> <option value="active">未完成</option> </select> <div v-for="task in taskStore.filteredTasks" :key="task.id"> {{ task.title }} <button @click="taskStore.toggleTask(task.id)"> {{ task.completed ? '✅' : '⬜' }} </button> </div> </div> </template>