引言
--
在Vue.js开发中,状态管理是一个重要的问题。为了更好地管理应用程序的状态,开发者们通常会使用Vuex。然而,随着Vue 3的发布,一个新的状态管理库Pinia也逐渐崭露头角。本文将深入介绍Pinia的使用方式,并与Vuex进行比较,以帮助开发者更好地理解和选择适合自己项目的状态管理库。
为什么要使用pinia?
Pinia 是 Vue 的存储库,它允许您跨组件/页面共享状态。 如果您熟悉 Composition API,您可能会认为您已经可以通过一个简单的 export const state = reactive({})
. 这对于单页应用程序来说是正确的,但如果它是服务器端呈现的,会使您的应用程序暴露于安全漏洞。 另外:即使在小型单页应用程序中,您也可以从使用 Pinia 中获得很多好处:
- dev-tools 支持
* 跟踪动作、突变的时间线
* Store 出现在使用它们的组件中
* time travel 和 更容易的调试热模块更换
代码语言:txt复制* 在不重新加载页面的情况下修改您的 Store
* 在开发时保持任何现有状态插件:使用插件扩展 Pinia 功能
- 为 JS 用户提供适当的 TypeScript 支持或 autocompletion
- 服务器端渲染支持
安装和配置
- 使用你所常用的包管理器进行安装
yarn add pinia
# 或者使用 npm
npm install pinia
- 在应用程序中注册store:在Vue应用程序的入口文件中使用
createPinia
函数创建一个Pinia实例,并将其作为插件注册到Vue应用程序中。
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')
核心用法
1. 定义Store
首先,我们需要定义一个Store来管理应用程序的状态。一个Store是一个包含了state、getters、mutations和actions等属性和方法的对象。可以通过创建一个类来定义Store,然后使用defineStore
函数将其转换为Pinia Store。
import { defineStore } from 'pinia';
// useMyStore 可以是 useUser、useCart 之类的任何东西
// 第一个参数是应用程序中 store 的唯一 id
export const useMyStore = defineStore('myStore', {
state: () => ({
count: 0,
}),
getters: {
doubleCount: (state) => state.count * 2,
},
actions: {
increment() {
this.count ;
},
},
});
这个 name,也称为 id,是必要的,Pinia 使用它来将 store 连接到 devtools。 将返回的函数命名为 use... 是跨可组合项的约定,以使其符合你的使用习惯。
2. 创建和使用Store
在Vue组件中,可以通过useStore
函数来创建和使用我们定义的Store。
import { useMyStore } from './my-store';
export default {
setup() {
const store = useMyStore();
return {
// 您可以返回整个 store 实例以在模板中使用它
store,
};
},
};
您可以根据需要定义任意数量的 store ,并且您应该在不同的文件中定义每个 store以充分利用 pinia(例如自动允许您的包进行代码拆分和 TypeScript 推理)。
3. 访问State和Getters
在组件中,可以通过访问store对象来获取state和getters。
代码语言:javascript复制export default {
setup() {
const store = useMyStore();
console.log(store.count); // 访问state
console.log(store.doubleCount); // 访问getter
// ❌ 这不起作用,因为它会破坏响应式
// 这和从 props 解构是一样的, count的值不会变化
const { count } = store
return {
store,
};
},
};
代码语言:javascript复制为了从 Store 中提取属性同时保持其响应式,您需要使用
storeToRefs()
。 它将为任何响应式属性创建 refs。 当您仅使用 store 中的状态但不调用任何操作时,这很有用!
import { storeToRefs } from 'pinia'
export default {
setup() {
const store = useMyStore();
console.log(store.count); // 访问state
console.log(store.doubleCount); // 访问getter
const { count, doubleCount } = storeToRefs(store)
return {
count,
doubleCount,
store,
};
},
};
大多数时候,getter 只会依赖状态,但是,他们可能需要使用其他 getter。 正因为如此,我们可以在定义常规函数时通过 this
访问到 整个 store 的实例。
4. 调用Actions
在组件中,可以通过调用store对象的actions来执行一些异步操作或者修改state。
代码语言:javascript复制export default {
setup() {
const store = useMyStore();
store.increment(); // 调用action
return {
store,
};
},
};
Actions 相当于组件中的 methods。 它们可以使用 defineStore()
中的 actions
属性定义,并且它们非常适合定义业务逻辑
5. 使用插件
Pinia还支持使用插件来扩展其功能。可以通过use
函数来使用插件。
import { useMyStore } from './my-store';
import { myPlugin } from './my-plugin';
export default {
setup() {
const store = useMyStore();
store.use(myPlugin); // 使用插件
return {
store,
};
},
};
与Vuex相比
与Vuex相比,Pinia具有以下优点:
1. 更好的类型推断:Pinia使用了Vue 3的Composition API,可以更好地推断出store中的状态、操作和getter的类型。 2. 更好的性能:Pinia使用了Vue 3的响应式系统,可以更高效地追踪状态的变化,并且只在需要时更新相关组件。 3. 更简洁的代码:相比Vuex,使用Pinia可以写出更简洁、可读性更高的代码。 4. 更好的扩展性:Pinia支持模块化和插件机制,可以轻松地扩展和组织store。
然而,与Vuex相比,Pinia也存在一些缺点:
1. 生态系统相对较小:由于是一个相对较新的库,与Vuex相比,Pinia在生态系统方面可能还不够成熟。
总结
--
Pinia是一个简单、直观且性能优越的Vue.js状态管理库。通过使用Vue 3的Composition API,Pinia提供了更好的类型推断和更好的性能。与Vuex相比,Pinia具有更简洁的代码和更好的扩展性。然而,学习曲线较陡峭和生态系统相对较小是其缺点。在选择状态管理库时,开发者可以根据项目需求和团队经验来选择适合自己的库。
我正在参与2023腾讯技术创作特训营第三期有奖征文,组队打卡瓜分大奖!