Vue状态管理库-Pinia

一、Pinia是什么?

Pinia 是 Vue 的专属状态管理库,它允许支持跨组件或页面共享状态,即共享数据,他的初始设计目的是设计一个支持组合式API的 Vue 状态管理库(因为vue3一个很大的改变就是组合式API),当然这并不是说Pinia只支持vue3,他是同时支持vue2和vue3的,本文倾向于拥抱Vue3,所以代码语法都是倾向用组合式api的写法

二、在vue3中使用Pinia

下面的流程和相关代码均基于vue3项目

1、安装pinia

javascript 复制代码
npm install pinia

或用yarn安装

javascript 复制代码
yarn add pinia

package.json中看到pinia表示安装成功

2、创建pinia实例并将其传递给应用

javascript 复制代码
//src/main.js

//创建应用实例
import { createApp } from "vue";
import App from "./App.vue";
let app = createApp(App);

//pinia实例
import { createPinia } from "pinia";
let pinia = createPinia();
app.use(pinia);

app.mount("#app");

挂载完成后,我们就可以在Vue的devtools里看到Pinia了

3、定义Store

Store 是用 defineStore() 定义的,它的第一个参数要求是一个独一无二的 名字,在整个应用中保持唯一, 返回的函数命名为 use... 是一个符合组合式函数风格的约定

javascript 复制代码
import { defineStore } from "pinia";

//命名规则,建议以 `use` 开头且以 `Store` 结尾,即 use~~~Store
export const useMapStore = () => {

    // 其他配置...
}

Setup store(Option Store可以查看官方,本文不列举)

javascript 复制代码
import { defineStore } from "pinia";
import { reactive, computed } from "vue";
import type { City, Province } from "@/interface/common";

export const useMapStore = defineStore("mapStore", () => {
  //state
  let cityList = reactive<Array<City>>([]);
  let provinceList = reactive([]);

  //getter
  const simpleCityList = computed(() => {
    return cityList.filter((item) => item.code != "110000");
  });

  //actions
  function changeCityList(list: City[]) {
    console.log("修改城市列表数据的事件被触发");
    cityList = Object.assign(cityList, list);
  }
  function changeProviceList(list: Province[]) {
    console.log("修改省份列表数据的事件被触发");
    provinceList = Object.assign(provinceList, list);
  }

  return {
    cityList,
    provinceList,
    simpleCityList,
    changeCityList,
    changeProviceList,
  };
});

4、使用store

javascript 复制代码
<template>
    <div>您好!欢迎来到星野的小世界</div>
    <div>星野的目标是走遍中国的每一个省,中国的省如下:</div>
    <div>
        <ul>
            <li v-for="city in cityList" :key="city.code">
                {{ city.name }}
            </li>
        </ul>
    </div>
</template>

<script setup lang='ts' name='Login'>
import { onMounted} from 'vue';
import { storeToRefs } from 'pinia';
import { getCityList } from "@/utils/common";
import { useMapStore } from '@/stores/map'

let mapStore = useMapStore()
let { cityList } = storeToRefs(mapStore) //为了从 store 中提取属性时保持其响应性,需要使用 storeToRefs()。它将为每一个响应式属性创建引用

onMounted(async () => {
    let list = await getCityList()
    mapStore.changeCityList(list) //修改store里的属性数据
})
</script>
<style lang='scss' scoped></style>

getCityList是一个工具函数,调用一个免费api获取中国的城市数据

Setup Store 中:

  • ref() /reactive ( ) 就是 state 属性
  • computed() 就是 getters
  • function() 就是 actions

页面效果

5、修改store中的state

例如store中的state有一个城市统计属性: cityCount

在业务组件里,就可以通过mapStore.cityCount 直接修改数量

如果state有很多属性,还可以调用**$patch** 方法。它允许你用一个 state 的补丁对象在同一时间更改多个属性

javascript 复制代码
 mapStore.$patch({
        cityCount: mapStore.cityCount + 1,
        provinceCount: mapStore.provinceCount + 1
    })

好啦,Pinia 满足基础使用的读写改操作已经描述完毕,关于搭配 Nuxt 的 Pinia 完成SSR,后续会单独出文,敬请期待!😁

ps: 学习成长过程的简单记录,如有不恰当之处,欢迎交流

相关推荐
沉默璇年13 分钟前
react中useMemo的使用场景
前端·react.js·前端框架
yqcoder19 分钟前
reactflow 中 useNodesState 模块作用
开发语言·前端·javascript
2401_8827275728 分钟前
BY组态-低代码web可视化组件
前端·后端·物联网·低代码·数学建模·前端框架
会发光的猪。1 小时前
css使用弹性盒,让每个子元素平均等分父元素的4/1大小
前端·javascript·vue.js
天下代码客1 小时前
【vue】vue中.sync修饰符如何使用--详细代码对比
前端·javascript·vue.js
猫爪笔记1 小时前
前端:HTML (学习笔记)【1】
前端·笔记·学习·html
前端李易安2 小时前
Webpack 热更新(HMR)详解:原理与实现
前端·webpack·node.js
红绿鲤鱼2 小时前
React-自定义Hook与逻辑共享
前端·react.js·前端框架
周全全2 小时前
Spring Boot + Vue 基于 RSA 的用户身份认证加密机制实现
java·vue.js·spring boot·安全·php
Domain-zhuo2 小时前
什么是JavaScript原型链?
开发语言·前端·javascript·jvm·ecmascript·原型模式