网站首页 > 精选文章 正文
在编程界有句老话:“命名和缓存失效是世上两大难题。” 我得说,在现代Web应用的状态管理上,这难题得排第三!
今天,咱们来深挖一下Vue的状态管理之道,并介绍一个超直观的解决方案——Pinia。
Vue状态管理:那些坑和局限性
自Vue 2起,我们用data属性来定义组件的状态,就像这样:
<template>
<div>{{ user.name }}</div>
</template>
<script>
export default {
data() {
return { user: { name: 'John', age: 25 } };
}
};
</script>
这就是所谓的 选项 API,在Vue 3中依然可用。Vue 3还带来了 组合式 API,它用reactive和ref等新招数来定义状态。用这新API,我们可以这样写组件脚本:
<script setup>
import { reactive } from 'vue'
const user = reactive({ name: 'John', age: 25 });
</script>
但如果要跨组件访问状态,比如在导航栏显示用户名,在个人资料页展示详细信息,这就尴尬了。通常,我们用props逐层传递,但层级一多,就得在每个组件里加props,不管用不用得上。这叫prop 穿透,真不推荐。
更新共享数据时,子组件不能直接改props,得发事件让父组件来更新,再传下去。这...感觉有点笨。
Vue 3的救星来了:组合式 API 让我们能在任何脚本里用ref和reactive,还能导出状态,整个应用都能用。
我们可以把这状态叫做存储 (store)。比如,创建个store/user.js:
import { reactive } from 'vue'
const user = reactive({ name: 'John', age: 25 });
export { user };
然后在组件里这么用:
<script setup>
import { user } from './stores/user.js';
</script>
<template>
<h1>Hello, {{ user.name }}! You are {{ user.age }} years old.</h1>
</template>
看,现在状态有单一来源,组件间还能共享。
但这种模式虽简单,却不适合服务器端渲染 (SSR),因为状态只创建一次,可能导致数据泄露。而且,随着应用变大,可能需要更强大的状态管理。
Pinia:现代Vue应用的存储解决方案
Pinia 不仅支持SSR,还有Vue Devtools集成、热更新、TypeScript友好等优点。
Pinia由Vue Router的开发者Eduardo打造,现已取代Vuex,成为Vue 3官方推荐的状态管理库。
安装和设置
安装Pinia就一行命令:
npm install pinia
然后创建Pinia实例,传给Vue应用:
import { createApp } from 'vue'
import { createPinia } from 'pinia'
import App from './App.vue'
const pinia = createPinia()
const app = createApp(App)
app.use(pinia)
app.mount('#app')
现在,创建和管理存储就这么简单。
创建存储
用defineStore方法创建Pinia存储,第一参数是名,第二参数是配置。比如,我们改写下user存储:
import { defineStore } from 'pinia'
export const useUserStore = defineStore('user', {
state: () => ({ name: 'John', age: 25 }),
getters: {
canVote: (state) => state.age >= 18,
},
actions: {
blowCandles() {
this.age++;
}
}
});
这就是选项存储 (Option Stores)。
喜欢组合式 API?Pinia也支持。用设置存储 (Setup Stores),用ref、computed定义状态和计算属性,函数返回要公开的:
import { defineStore } from 'pinia'
import { ref, computed } from 'vue'
export const useUserStore = defineStore('user', () => {
const name = ref('John');
const age = ref(25);
const canVote = computed(() => age.value >= 18);
const blowCandles = () => age.value++;
return { name, age, canVote, blowCandles };
});
设置存储的好处包括定义观察器、使用其他组合函数、注入属性等。
使用存储
定义了Pinia存储后,就可以在组件或组合函数里导入使用了:
<script setup>
import useUserStore from './stores/user.js'
const user = useUserStore();
</script>
<template>
<button @click="user.blowCandles">
I am {{ user.name }} and it's my birthday!
</button>
</template>
通过user对象访问状态和操作,简单直观。解构时,用storeToRefs保持反应性。
真实例子
实际应用中,我们不会用固定值初始化存储。来看个登录示例:
import { ofetch } from 'ofetch'
import { defineStore } from 'pinia'
export const useUserStore = defineStore('user', () => {
const data = ref();
const token = ref();
const isLoggedIn = computed(() => Boolean(token.value));
async function login({ email, password }) {
const { data, token: tok } = await ofetch('https://example.com/login', {
method: 'POST',
body: { email, password }
});
data.value = data;
token.value = tok;
}
// ... logout, other methods
});
存储是封装应用逻辑的好地方。比如,登录操作请求API,保存用户数据和令牌。
然后在组件里这么用:
<script setup>
import useUserStore from './stores/user.js'
const user = useUserStore();
// ... form, error, handleSubmit
</script>
<template>
<!-- ... template code -->
</template>
Pinia不仅管理用户会话,还能跟踪其他数据,减少服务器请求,让应用更快。
Pinia也适用于Vue 2
Pinia完全兼容Vue 2,所以如果你的Vue 2应用用Vuex,迁移到Pinia是升级到Vue 3的好起点。
Pinia Vue Devtools 插件
如果你用Vue Devtools,Pinia会有个新标签让你浏览存储,检查状态,甚至导入导出JSON。
总结
状态管理可能看起来有点吓人,但一旦掌握了,就简单多了。Pinia帮你组织数据,轻松访问。开发体验棒,集成简单。想试试?去官网看看。
猜你喜欢
- 2024-12-20 开发者的常见陷阱:你不可不知的调试技巧
- 2024-12-20 微信网页开发者工具正式发布
- 2024-12-20 微信发布web开发者工具 模拟微信客户端
- 2024-12-20 从Vue2快速上手Vue3,这份指南已经给您准备好了
- 2024-12-20 Chrome Dev Tools
- 2024-12-20 ?Chrome DevTools 使用指?北 - 来源面板之查看当前调用堆栈 ??
- 2024-12-20 MikuTools轻量在线工具系统源码/含几十款工具
- 2024-12-20 第01节: 检查环境 创建项目
- 2024-12-20 vue 开发规范
- 2024-12-20 深入浅出Vue,全网最全笔记
- 最近发表
- 标签列表
-
- 向日葵无法连接服务器 (32)
- git.exe (33)
- vscode更新 (34)
- dev c (33)
- git ignore命令 (32)
- gitlab提交代码步骤 (37)
- java update (36)
- vue debug (34)
- vue blur (32)
- vscode导入vue项目 (33)
- vue chart (32)
- vue cms (32)
- 大雅数据库 (34)
- 技术迭代 (37)
- 同一局域网 (33)
- github拒绝连接 (33)
- vscode php插件 (32)
- vue注释快捷键 (32)
- linux ssr (33)
- 微端服务器 (35)
- 导航猫 (32)
- 获取当前时间年月日 (33)
- stp软件 (33)
- http下载文件 (33)
- linux bt下载 (33)