当前位置: 首页 > news >正文

vue3项目使用pinia状态管理器----通俗易懂

1、首先安装pinia

yarn add pinia
# 或使用npm
npm install pinia

2、在项目的src目录下新建store文件夹,然后store目录下新建index.js / index.ts :

我这里是index,js

import { createPinia } from "pinia"// 创建 Pinia 实例
const pinia  = createPinia()// 导出 Pinia 实例以便将其与应用程序实例关联
export default pinia

3、 接着在项目入口文件main.js 或 main.ts 引入并使用:

import { createApp } from 'vue'
import './style.css'
import App from './App.vue'
import router from './router/router'
import store from './store/index'createApp(App).use(router).use(store).mount('#app')

4、然后使用defineStore来定义状态存储模块,一般使用useXXXXXStore 来约定俗成的命名规范, 我这里是user.js:

import { defineStore } from "pinia"export const useUserStore = defineStore({//id 是为了更好地区分模块id: 'user',state: () => ({name: 'Tony',age: 18,count: 0}),getters: {doubleCount: (state) => state.count * 2,},actions: {// 定义操作或异步请求increment() {// 这里访问state的数据不再是state.XXX,而是通过thisthis.count++}}
})

 5、在组件内使用store:

<template><div><h3>我是测试pinia状态存储的组件,我有一个子组件</h3><div>userStore里的state数据:</div><span>姓名: {{ name }}</span>&nbsp;&nbsp; <span>年龄: {{ age }}</span><div><button @click="handleIncre">修改count:</button>count: {{ count }}</div><!-- 直接调用getters的方法 --><div> Double count is: {{ doubleCount }}</div></div>
</template>

js:

<script setup>
import { ref, reactive } from 'vue'
import TestChild1 from './component/TestChild1.vue'
import { useUserStore } from '../../store/user';
import { storeToRefs } from 'pinia'const userStore = useUserStore()
// 通过storeToRefs包裹,解构出来的属性/方法才有响应式
const { name, age, count,  doubleCount} = storeToRefs(userStore)
// console.log('userStore:', userStore.name, userStore.age, userStore.count)
// console.log(name.value, age.value, count.value);// 调用store的actions的increment方法
const handleIncre = () => {userStore.increment()
}</script>

解构store的变量或方法时,如果没有通过storeToRefs包裹,就失去了响应式:

具有响应式:

6、在store中定义异步获取用户信息方法:

6.1 首先新建一个api文件夹定义模拟异步登录获取用户登录信息接口方法:

~~src/api/index

// 模拟异步登录获取用户信息
const loginUser = () => {return new Promise((resolve, reject) => {setTimeout(() => {resolve({name: 'Tony',age: 18})}, 2000)})
}export default {loginUser
}
6.2 在store,user.js中: 

引入api文件,在actions中定义getUserInfo方法,异步查询时,通常都是async和await一起搭配使用的。

import { defineStore } from "pinia"
import API from '../api/index'export const useUserStore = defineStore({//id 是为了更好地区分模块id: 'user',state: () => ({name: 'Tony',age: 18,count: 0,userInfo: {}}),getters: {doubleCount: (state) => state.count * 2,},actions: {// 定义操作或异步请求increment() {// 这里访问state的数据不再是state.XXX,而是通过thisthis.count++},// 在actions中异步获取loginUser的数据async getUserInfo() {this.userInfo = await API.loginUser()console.log('user-info', this.userInfo);}}
})
 6.3 在vue组件中使用:
<!-- 点击---异步登录获取userInfo --><button @click="getUser">异步登录获取userInfo</button><div>userInfo: {{ userInfo }}</div>
// 调用store的actions的getUserInfo方法异步获取用户登录信息
const getUser = () => {userStore.getUserInfo()
}

 

7、此外,在actions中,方法也可以互相调用:

在actions中定义updateUserName方法,通过传入的新名字newName去改变state中的userInfo的name

actions: {// 定义操作或异步请求increment() {// 这里访问state的数据不再是state.XXX,而是通过thisthis.count++},// 在actions中异步获取loginUser的数据async getUserInfo(newName) {this.userInfo = await API.loginUser()console.log('user-info', this.userInfo);this.updateUserName(newName)},updateUserName(name) {if(name) {this.userInfo.name = name}}}

 组件内调用actions的getUserInfo方法时传入newName:

// 调用store的actions的getUserInfo方法异步获取用户登录信息
const newName = ref('小白很白')const getUser = () => {userStore.getUserInfo(newName.value)
}

8、pinia数据持久化

数据持久化之前,刷新页面,pinia的数据会丢失,跟vuex一样,但是pinia做数据持久化是可以通过插件快速完成。

该插件的默认配置如下:

  • 使用 localStorage 进行存储
  • store.$id 作为 storage 默认的 key
  • 使用 JSON.stringify/JSON.parse 进行序列化/反序列化
  • 整个 state 默认将被持久化’
8.1 pnpm安装:
pnpm i pinia-plugin-persistedstate
8.2  将插件添加到 pinia 实例上:

~~store/index:

import { createPinia } from "pinia"
import piniaPluginPersistedstate from 'pinia-plugin-persistedstate'// 创建 Pinia 实例
const pinia  = createPinia()
pinia.use(piniaPluginPersistedstate)// 导出 Pinia 实例以便将其与应用程序实例关联
export default pinia
8.3 在对应的store中,将 persist 选项设置为 true 。
import { defineStore } from "pinia"
import API from '../api/index'export const useUserStore = defineStore({//id 是为了更好地区分模块id: 'user',state: () => ({name: 'Tony',age: 18,count: 0,userInfo: {name: '',age: null,info:[]}}),getters: {doubleCount: (state) => state.count * 2,},actions: {// 定义操作或异步请求...// 在actions中异步获取loginUser的数据...},persist: true,
})

现在,你的整个 Store 将使用默认持久化配置保存。

控制台Application 的 localStorage如图:

9、pinia的modules模块化:

9.1 先在store目录下创建modules文件夹,把之前的user.js复制到里面,在创建个counter.js文件: 

9.2  把对应的user.js和counter.js文件的方法和属性修好,导出给外面组件使用:

~user.js:

import { defineStore } from "pinia"
import API from '@/api/index'export const useUserStore = defineStore({//id 是为了更好地区分模块id: 'user',state: () => ({name: 'Tony',age: 18,count: 0,userInfo: {name: '',age: null,info:[]}}),getters: {doubleCount: (state) => state.count * 2,},actions: {// 定义操作或异步请求increment() {// 这里访问state的数据不再是state.XXX,而是通过thisthis.count++},// 在actions中异步获取loginUser的数据async getUserInfo(newName) {this.userInfo = await API.loginUser()console.log('user-info', this.userInfo);this.updateUserName(newName)},updateUserName(name) {if(name) {this.userInfo.name = name}}},persist: true,
})

~counter.js: 

import {  defineStore} from 'pinia'export const useCounterStore = defineStore({id: 'counter',state: () => ({counterCount: 21}),getters: {tenCount: (state) => {return state.counterCount *10}},actions: {decrement() {this.counterCount--}},// 持久化persist: true,
})
9.3 main.js

模块化统一导出

import { createPinia } from "pinia"
// pinia持久化插件
import piniaPluginPersistedstate from 'pinia-plugin-persistedstate'// 创建 Pinia 实例
const pinia  = createPinia()
pinia.use(piniaPluginPersistedstate)// 导出 Pinia 实例以便将其与应用程序实例关联
export default pinia// 模块化导出
// import { useUserStore } from '@/store/modules/user.js'
// export { useUserStore }
// import { useCounterStore } from '@/store/modules/counter.js'
// export { useCounterStore }// 模块化统一导出,简写
export * from './modules/user'
export * from './modules/counter'
9.4 在页面中使用

先引入store/index

// import { useUserStore } from '../../store/user';
import { useUserStore, useCounterStore } from '../../store/index'

 通过storeToRefs解构出counterCount, tenCount属性,方法可直接调用

// store的模块化使用,调用useCounterStore的属性/方法
const counterStore = useCounterStore()
const { counterCount, tenCount } = storeToRefs(counterStore)const handleDecre = () => {counterStore.decrement()
}

模板:

<div>################################ start ==> pinia modules模块化 #############################</div><!-- store的模块化使用,调用useCounterStore的counterCount属性 --><div>counterStore的counterCount:{{ counterCount }}</div><button @click="handleDecre">修改counterCount</button><div>10倍counterCount:{{ tenCount }}</div><div>################################ end ==> pinia modules模块化 #############################</div>

 效果:

​​​​​​​

 以上就是pinia的vue3使用。

相关文章:

vue3项目使用pinia状态管理器----通俗易懂

1、首先安装pinia yarn add pinia # 或使用npm npm install pinia 2、在项目的src目录下新建store文件夹&#xff0c;然后store目录下新建index.js / index.ts &#xff1a; 我这里是index,js import { createPinia } from "pinia"// 创建 Pinia 实例 const pinia …...

零基础学Java第二十五天之Lambda表达式

Lambda表达式 简介 Lambda是一个匿名函数(方法)&#xff0c; 允许把函数作为一个方法的参数 。利用Lambda表达式可以写出更简洁、更灵活的代码。作为一种更紧凑的代码风格&#xff0c;使Java的语言表达能力得到了提升。一般都是优化匿名内部类 基础语法 无参数、无返回值的抽…...

VSCode配置Lua5.4安装

参考&#xff1a;VSCode 配置 Lua 开发环境(清晰明了)_lua vscode-CSDN博客 1.下载 Lua Binaries Download (sourceforge.net) 2.配置环境变量 解压放到某文件夹&#xff1a; 环境变量&#xff1a; 3.VSCode安装插件 4.配置 5.测试...

CI/CD:持续集成/持续部署

1. 安装docker、docker-compose # 安装Docker yum install -y yum-utils device-mapper-persistent-data lvm2 yum-config-manager --add-repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo sed -i sdownload.docker.commirrors.aliyun.com/docker-ce /…...

ComfyUI工作流网站

https://openart.ai/home https://comfyworkflows.com/ https://civitai.com/...

【机器学习】机器学习基础概念与初步探索

❀机器学习 &#x1f4d2;1. 引言&#x1f4d2;2. 机器学习概述&#x1f4d2;3. 机器学习基础概念&#x1f389;2.1 机器学习的分类&#x1f389;2.2 数据预处理&#x1f308;数据清洗与整合&#x1f308; 特征选择和特征工程&#x1f308;数据标准化与归一化 &#x1f4d2;4. …...

学英语材料:单口喜剧、讲故事、短剧喜剧以及广播剧和播客节目

学习英语节目 有名的单口喜剧、讲故事、短剧喜剧以及广播剧和播客节目&#xff1a; 单口喜剧&#xff08;Stand-up Comedy&#xff09; 描述&#xff1a;这是最接近相声的形式&#xff0c;表演者独自一人站在舞台上&#xff0c;用幽默的方式讲述个人经历、观察到的社会现象或…...

Docker Compose使用

Docker-Compose是什么 docker建议我们每一个容器中只运行一个服务,因为doker容器本身占用资源极少&#xff0c;所以最好是将每个服务单独分割开来&#xff0c;但是这样我们又面临了一个问题&#xff1a; 如果我需要同时部署好多个服务&#xff0c;难道要每个服务单独写Docker…...

如何优雅的卸载linux上的todesk

要优雅地卸载Linux上的ToDesk&#xff0c;您可以按照以下步骤操作&#xff1a; 打开终端。 输入以下命令来停止ToDesk服务&#xff08;如果它正在运行的话&#xff09;&#xff1a; sudo systemctl stop todesk 然后&#xff0c;使用包管理器卸载ToDesk。如果您使用的是apt&…...

【Vue】el-checkbox多选框实现单选效果,选中一个选项则自动取消其他勾选

&#x1f935; 作者&#xff1a;coderYYY &#x1f9d1; 个人简介&#xff1a;前端程序媛&#xff0c;目前主攻web前端&#xff0c;后端辅助&#xff0c;其他技术知识也会偶尔分享&#x1f340;欢迎和我一起交流&#xff01;&#x1f680;&#xff08;评论和私信一般会回&#…...

Linux中使用vi编辑器自动缩进4个字符

平常在Linux操作系统下书写shell脚本内容&#xff0c;或是把写好的shell内容直接复制到vi编辑器中&#xff0c;本来缩进好的字符&#xff0c;会自动变乱&#xff0c;这是因为Linux的vi编辑器默认是缩进8个字符造成&#xff0c;可以使用下面2个方法解决该问题的发生。 1、本用户…...

#笔记#笔记#其他

大鱼论文是一款非常靠谱、方便、值得推荐的论文写作工具。无论是在学术研究中还是在日常写作中&#xff0c;大鱼论文都能够帮助用户轻松完成论文的写作工作。 首先&#xff0c;大鱼论文提供了强大的查重降重功能&#xff0c;能够帮助用户快速定位论文中可能存在的抄袭问题&…...

gtask笔记

1、创建Task GTask *g_task_new (gpointer source_object, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer callback_data); source_object&#xff1a;GObject对象&#xff0c;拥有者 cancellable&#xff1a;可否取消 callback&#xff1a;task完成后…...

【Linux学习】深入探索进程等待与进程退出码和退出信号

文章目录 退出码return退出 进程的等待进程等待的方法 退出码 main函数的返回值&#xff1a;进程的退出码。 一般为0表示成功&#xff0c;非0表示失败。 每一个非0退出码都表示一个失败的原因&#xff1b; echo $&#xff1f;命令 作用&#xff1a;查看进程退出码。&#xf…...

Linux:线程

文章目录 前言1. 线程概念1.1 什么是线程1.2 线程比进程更加轻量化1.3 虚拟地址到物理地址的转化物理内存的管理页表 1.4 线程的优点1.5 线程的缺点1.6 线程异常1.7 线程用途 2. 进程 vs 线程3. 线程控制3.1 线程创建3.2 线程退出3.3 线程等待3.4 分离线程3.5 线程取消 4. 线程…...

卡到BUG了:删除重发白得积分(以前删除会扣减积分)

以前是&#xff1a;删除文章&#xff0c;积分减少&#xff0c;点赞积分减少&#xff0c;从回收站恢复文章&#xff0c;积分恢复&#xff0c;点赞数恢复但点赞积分不恢复。也就是删除重发总积分减少点赞的积分&#xff0c;有损失。 今天是&#xff1a;删除文章&#xff0c;积分不…...

轻松拿捏C语言——【字符函数】字符分类函数、字符转换函数

&#x1f970;欢迎关注 轻松拿捏C语言系列&#xff0c;来和 小哇 一起进步&#xff01;✊ &#x1f308;感谢大家的阅读、点赞、收藏和关注&#x1f495; &#x1f339;如有问题&#xff0c;欢迎指正 感谢 目录&#x1f451; 一、字符分类函数&#x1f319; 二、字符转换函数…...

【Rust日报】ratatui版本更新

[new ver] ratatui v0.26.3 一个构建终端用户界面的库。新版本包括&#xff1a; 修复Unicode 截断 bug对颜色更好地序列化更快的渲染弃用assert_buffer_eq宏暴露错误类型常量函数和类型 官网: https://ratatui.rs/ 链接: https://ratatui.rs/highlights/v0263/ [new lib] ansi2…...

力扣每日一题 5/28

题目&#xff1a;2951-找出峰值 给你一个下标从 0 开始的数组 mountain 。你的任务是找出数组 mountain 中的所有 峰值。 以数组形式返回给定数组中 峰值 的下标&#xff0c;顺序不限 。 注意&#xff1a; 峰值 是指一个严格大于其相邻元素的元素。数组的第一个和最后一个元…...

async函数和await函数

一、async函数 async是一个加在函数前的修饰符&#xff0c;被async定义的函数会默认返回一个Promise对象resolve的值。 因此对async函数可以直接then&#xff0c;返回值就是then方法传入的函数。 // async基础语法 async function fun0(){console.log(1);return 1; } fun0()…...

Linux操作系统故障应急场景及对应排查方法

001&#xff1a;系统CPU负载高并触发监控报警 005 查看系统CPU使用情况,&#xff0c;确认CPU数量&#xff0c;确认系统负载&#xff0c;确认CPU高对系统的影响 006 定位占用CPU资源最多的进程&#xff0c;根据进程判断是应用进程还是系统进程还是第三方工具进程。 014 查看…...

数据湖是什么?数据湖和数据仓库的区别是什么?

目录 一、数据湖是什么 &#xff08;一&#xff09;数据湖的定义 &#xff08;二&#xff09;数据湖的特点 二、数据仓库是什么 &#xff08;一&#xff09;数据仓库的定义 &#xff08;二&#xff09;数据仓库的特点 三、数据湖和数据仓库的区别 &#xff08;一&#…...

2025年06月07日Github流行趋势

项目名称&#xff1a;netbird 项目地址url&#xff1a;https://github.com/netbirdio/netbird项目语言&#xff1a;Go历史star数&#xff1a;14824今日star数&#xff1a;320项目维护者&#xff1a;mlsmaycon, braginini, pascal-fischer, lixmal, pappz项目简介&#xff1a;使…...

STM32开发,创建线程栈空间大小判断

1. 使用RTOS提供的API函数&#xff08;以FreeRTOS为例&#xff09; 函数原型&#xff1a;UBaseType_t uxTaskGetStackHighWaterMark(TaskHandle_t xTask)功能&#xff1a;获取指定任务堆栈中剩余的最小空间&#xff08;以字为单位&#xff0c;非字节&#xff09;。使用步骤&am…...

MongoDB检查慢查询db.system.profile.find 分析各参数的作用

db.system.profile.find() 是分析 MongoDB 性能的关键工具,其返回的文档包含丰富的性能指标。下面是对各参数的详细解释和优化建议: {"op": "query", // 操作类型(query/update/remove)"ns": "test.users", // 命名…...

DeepSeek 赋能智能养老:情感陪伴机器人的温暖革新

目录 一、引言二、智能养老情感陪伴机器人的市场现状与需求2.1 市场现状2.2 老年人情感陪伴需求分析 三、DeepSeek 技术详解3.1 DeepSeek 的技术特点3.2 与其他类似技术的对比优势 四、DeepSeek 在智能养老情感陪伴机器人中的具体应用4.1 自然语言处理与对话交互4.2 情感识别与…...

如何区分 “通信网络安全防护” 与 “信息安全” 的考核重点?

“通信网络安全防护” 与 “信息安全” 的考核重点可以从以下几个方面进行区分&#xff1a; 保护对象 通信网络安全防护&#xff1a;重点关注通信网络系统本身&#xff0c;包括网络基础设施&#xff0c;如路由器、交换机、基站等&#xff0c;以及网络通信链路和相关设备。同…...

第5章:Cypher查询语言进阶

在掌握了Cypher的基础知识后&#xff0c;本章将深入探讨更高级的查询技术。这些进阶技能将帮助您构建更复杂、更高效的查询&#xff0c;解决实际业务中的复杂问题&#xff0c;并充分发挥Neo4j的图数据处理能力。 5.1 复杂查询构建 随着业务需求的复杂性增加&#xff0c;查询也…...

固定ip和非固定ip的区别是什么?如何固定ip地址

在互联网中&#xff0c;我们常会接触到固定IP和非固定IP的概念。它们究竟有何不同&#xff1f;如何固定IP地址&#xff1f;让我们一起来探究这个问题。 一、固定IP和非固定IP的区别是什么 固定IP&#xff08;静态IP&#xff09;和非固定IP&#xff08;动态IP&#xff09;是两种…...

【区块链基础】区块链的 Fork(分叉)深度解析:原理、类型、历史案例及共识机制的影响

区块链的 Fork(分叉)全面解析:原理、类型、历史案例及共识机制的影响 在区块链技术的发展过程中,Fork(分叉)现象是不可避免且极具影响力的一个环节。理解区块链分叉的形成原因、具体表现以及共识机制对分叉的作用,对于深入把握区块链技术架构及其治理机制至关重要。 本…...