文章目录

Vue 状态管理:Vuex 与 Pinia

发布于 2026-04-06 21:12:07 · 浏览 30 次 · 评论 0 条

Vue 状态管理:Vuex 与 Pinia


阶段一:评估需求与确定技术栈

  1. 核对 当前项目使用的 Vue 框架版本。Vue 3 项目默认推荐 Pinia;Vue 2 项目若未启用 Composition API 组合式 API,继续使用 Vuex 3.x 即可。
  2. 评估 跨组件通信的复杂度。仅涉及简单父子传值或基础配置读取时,直接使用 Vue 内置的 provide 提供与 inject 注入;涉及复杂业务流、全局拦截或大型团队协作时,引入 独立状态管理库。
  3. 查阅 团队现有技术规范。若项目已存在大量 Vuex 模块且维护成本可控,保留 现有架构;新建模块或重构旧代码时,优先选择 Pinia,因其原生支持类型推断、打包体积更小且无需嵌套 Mutation 修改数据。
特性维度 Vuex Pinia
核心架构 单一全局 Store 树 + 嵌套 Module 模块 扁平化独立 Store 实例设计
数据修改路径 强制通过 Mutation 同步提交,Action 处理异步请求 直接在 Action 中修改,彻底取消 Mutation 概念
类型推断支持 需额外安装插件或手动定义复杂接口声明 完整支持 TypeScript,函数调用即可自动推导类型
核心打包体积 11 KB(Gzip 压缩后) 1 KB(Gzip 压缩后)

阶段二:安装与初始化项目

  1. 打开 终端或命令行窗口,切换 至前端项目根目录。
  2. 执行 包管理器安装命令。若确定使用 Pinia,输入 npm install pinia;若维持 Vuex 体系,输入 npm install vuex@next 以适配 Vue 3。
  3. 创建 状态库入口目录。在项目 src 文件夹下 新建 名为 store 的目录,并在其内部 生成 文件 index.js
  4. 编写 根应用挂载逻辑。打开 src/main.js导入 状态库创建函数并 注册 至 Vue 实例。以 Pinia 为例:
    
    import { createApp } from 'vue'
    import { createPinia } from 'pinia'
    import App from './App.vue'

const app = createApp(App)
const pinia = createPinia()

app.use(pinia)
app.mount('#app')

若使用 `Vuex`,需替换为 `import { createStore } from 'vuex'`,并将 `createPinia()` 替换为 `createStore({ state: {}, mutations: {} })`,**调用** `app.use()` 传入实例对象。

---

## 阶段三:编写状态管理核心逻辑

1. **定义** 独立状态模块。进入 `src/store` 目录,**新建** 业务文件 `userStore.js`。
2. **初始化** Store 实例结构。`Pinia` 采用组合式函数 API,**调用** `defineStore` 并传入唯一标识符 `id`、响应式状态 `state` 与操作方法:
```javascript
import { defineStore } from 'pinia'
import { ref, computed } from 'vue'

export const useUserStore = defineStore('user', () => {
  // 定义响应式状态
  const userInfo = ref({ name: '', token: '', role: '' })

  // 定义派生状态(计算属性)
  const isLoggedIn = computed(() => Boolean(userInfo.value.token))

  // 定义同步与异步操作
  async function fetchProfile() {
    const response = await fetch('/api/me')
    const data = await response.json()
    userInfo.value = data
  }

  function clearSession() {
    userInfo.value = { name: '', token: '', role: '' }
  }

  return { userInfo, isLoggedIn, fetchProfile, clearSession }
})
  1. 编写 Vuex 等效实现。若项目强制使用 Vuex,必须严格拆分同步与异步层:
    
    import { createStore } from 'vuex'

export const userModule = {
namespaced: true,
state: () => ({
userInfo: { name: '', token: '' }
}),
mutations: {
updateProfile(state, payload) {
state.userInfo = payload
}
},
actions: {
async fetchProfile({ commit }) {
const res = await fetch('/api/me')
const data = await res.json()
commit('updateProfile', data)
}
},
getters: {
isLoggedIn: (state) => !!state.userInfo.token
}
}

4. **合并** 模块至主入口。在 `src/store/index.js` 中 **导入** 刚定义的模块,**导出** 统一状态树配置。

---

## 阶段四:在组件中调用与监听状态

1. **打开** 需要消费全局状态的 Vue 单文件组件(如 `src/views/Home.vue`)。
2. **导入** 状态函数。在 `<script setup>` 标签顶部 **添加** 引用语句:`import { useUserStore } from '@/store/userStore.js'`。
3. **实例化** Store 对象。在组件顶层作用域内 **调用** 函数并 **接收** 返回值:`const userStore = useUserStore()`。注意:必须在 `setup` 语法环境或组件生命周期内调用,**禁止** 在外部 JS 文件中全局调用。
4. **读取** 响应式数据。在模板 `{{ }}` 插值表达式中 **直接使用** `userStore.userInfo.name`;在 `<script>` 逻辑中 **绑定** `userStore.isLoggedIn` 控制条件渲染。
5. **触发** 状态更新。为交互元素(如按钮或表单)**绑定** 事件回调,**执行** 异步请求方法:`userStore.fetchProfile()`。若使用 `Vuex`,需通过 `import { useStore } from 'vuex'` 获取根实例,并 **调用** `store.dispatch('user/fetchProfile')`。
6. **监听** 数据流转。在 `<script setup>` 中 **引入** Vue 的监听器:`import { watch } from 'vue'`,并 **配置** 响应式观测:
```javascript
watch(() => userStore.isLoggedIn, (isLogged, wasLogged) => {
  if (isLogged && !wasLogged) {
    // 执行登录成功后的路由跳转或埋点逻辑
  }
})

阶段五:调试追踪与持久化配置

  1. 启用 官方浏览器调试工具。访问 Chrome 或 Edge 扩展商店,搜索 Vue.js devtools 并完成插件安装。
  2. 捕获 状态变更轨迹。刷新目标页面,按 F12 调出开发者面板,切换Vue 专属选项卡。在左侧面板 点击 PiniaVuex 分类,右侧视图将渲染当前全局状态快照树。
  3. 回溯 历史数据版本。在插件时间轴控件上 点击 任意灰色节点,验证 页面数据是否精准还原至该节点记录时刻。测试完毕后,拖动 滑块至最右侧恢复实时状态。
  4. 拆分 巨型状态文件。当单个模块逻辑行数突破 300 行时,采用 组合策略将购物车、权限、主题等子状态抽离为独立 .js 文件,并在 index.js 中统一聚合导出。
  5. 挂载 本地持久化插件。若需在页面刷新后保留登录态或用户偏好,运行 npm install pinia-plugin-persistedstate修改 src/main.js 注册流程:
    
    import { createPinia } from 'pinia'
    import piniaPluginPersistedstate from 'pinia-plugin-persistedstate'

const pinia = createPinia()
pinia.use(piniaPluginPersistedstate)


在状态定义中 **附加** 配置项,于 `defineStore` 返回值平级 **添加** `__persist: true` 或完整对象 `{ key: 'app-user', storage: sessionStorage }`,**指定** 浏览器存储引擎。

评论 (0)

暂无评论,快来抢沙发吧!

扫一扫,手机查看

扫描上方二维码,在手机上查看本文