为什么现在更推荐使用Pinia?深入了解Pinia,解锁响应式数据的新姿势

1. pinia的安装和使用

csharp 复制代码
yarn add pinia
# 或者使用 npm
npm install pinia
javascript 复制代码
import App from './App.vue'
import { createApp } from 'vue'
import { createPinia } from 'pinia'

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

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

具体详细步骤可以参照Pinai官方文档

2. pinin与vuex的异同

同:

  1. 状态管理:Pinia 和 Vuex 都是状态管理的工具,允许你在应用中统一管理和共享数据。
  2. 响应式:它们都利用 Vue 的响应式系统来跟踪状态的变化,并更新相关的组件。
  3. 插件化:都可以通过插件的形式扩展功能。

异:

  1. API 设计:Pinia 更面向未来,使用了更现代的 API 设计,提供了更简单和直观的方法来定义和使用状态。
  2. 模块化:Pinia 支持模块化的状态管理,每个模块都有自己的状态、操作和订阅者,使代码更易维护和组织。
  3. 性能:Pinia 在某些情况下可能比 Vuex 更高效,因为它使用了 Vue 3 的 reactivity system,可以更好地利用原生的响应式特性。
  4. TypeScript 支持:Pinia 对 TypeScript 的支持更好,提供了更好的类型推断和类型安全。

总的来说,Pinia 更加现代化并且在 Vue 3 中得到了更好的集成,如果你正在开发 Vue 3 项目并且喜欢模块化的状态管理,那么 Pinia 可能是一个更好的选择。而对于传统的 Vue 2 项目,或者需要与大量现有 Vuex 代码交互的项目,则可以继续使用 Vuex。

3. 功能实现

3.1 定义 state 和 getter

js 复制代码
// stores/counter.js
// 导入一个 defineStore 方法
import { defineStore } from 'pinia'
import { computed, ref } from 'vue'

// 抛出方法
export const useCounterStore = defineStore('counter',() => {
    // 定义数据 (state)
    const count = ref(0)
    
    // state定义修改数据方法(action 同步操作)
    const increment = () => {
        count.value++
    }
    
    // getter定义
    const doubleCounter = computed(() => {
        return count.value * 2
    })
    
    // 以对象的方式return提供数组使用
    return { 
        count,
        increment,
        doubleCounter
        }
})
html 复制代码
<template>
    <button @click="counterStore.increment">{{ counterStore.count }}</button>
    <p>{{ counterStore.doubleCounter }}</p>
</template>

<script setup>
// 1. 导入 useCounterStore 方法
import { useCounterStore } from '@/stores/counter.js'

// 2. 执行方法得到 store 实例对象
const counterStore = useCounterStore()

console.log(counterStore)
// 打印Proxy

</script>

我们可以看到响应式对象count成功在vue文件中显示,并实现了getter中的doubleCounter方法,点击后count*2,我们再来看看执行方法得到 store 实例对象counterStore的打印结果是一个Proxy对象,而我们在stores/counter.js文件中定义的countincrementdoubleCounter也全部传入到vue文件中供实例对象counterStore使用。

3.2 定义action异步方法

先导入axios

复制代码
npm install axios
js 复制代码
// stores/counter.js
// 导入一个方法 defineStore
import { defineStore } from 'pinia'
import { computed, ref } from 'vue'
import axios from 'axios'

// 抛出方法
export const useCounterStore = defineStore('counter',() => {
    // 定义数据 (state)
    const count = ref(0)
    // 接口调用
    const API_URL = 'http://geek.itheima.net/v1_0/channels'
    
    // state定义修改数据方法 (action 同步操作)
    const increment = () => {
        count.value++
    }

    // getter定义
    const doubleCounter = computed(() => {
        return count.value * 2
    })

    // action定义异步方法
    const list = ref([])
    // getlist 方法从API 获取数据并存储到 list 中,它是一个异步的操作,利用 axios 发起了一个 HTTP GET 请求。
    const getlist = async () => {
        const res = await axios.get(API_URL)
        list.value = res.data.data.channels
    }

    // 以对象的方式return提供数组使用
    return { 
        count,
        increment,
        doubleCounter,
        list,
        getlist}
})
html 复制代码
<template>
  <div>
    <button @click="counterStore.increment">{{ counterStore.count }}</button>
    <p>{{ counterStore.doubleCounter }}</p>
    
    <ul>
      <li v-for="item in counterStore.list" :key="item.id">{{ item.name }}</li>
    </ul>
    
  </div>
</template>

<script setup>
// 导入 useCounterStore 方法
import { useCounterStore } from '@/stores/counter.js'
// 导入生命周期函数
import { onMounted } from 'vue';

// 执行方法得到 store 实例对象
const counterStore = useCounterStore()

console.log(counterStore)
// 打印Proxy

// 使用异步操作 getlist 并渲染到列表中
onMounted(()=>{
  counterStore.getlist()
})

</script>

<style lang="scss" scoped>
</style>

我们在stores/counter.js文件中定义异步方法getlist 成功从远程 API 获取数据并存储到 list 中,所有功能全部传入到vue文件中供实例对象counterStore使用。

在 Pinia 中,mutation 不是必须的,但可以作为一种可选的方式来修改状态。相比于 Vuex,Pinia 更加灵活,你可以直接在 action 中修改状态,而无需显式地定义 mutation。这样可以简化代码结构并减少一些模板代码。如果你希望更明确地追踪状态的变更,并且想要确保状态的修改是同步的,那么也可以使用 mutation。

4. 提问与归纳

  1. Pinia是用来做什么的? 答:集中状态管理工具,新一代的vuex。

  2. Pinia中还需要mutation吗? 答:不需要,action既支持同步也支持异步

  3. Pinia如何实现getter? 答:computed计算属性函数

  4. Pinia产生的Store如何解构赋值数据保持响应式? 答:storeToRefs

关于第四点问题,可以来看看笔者的Pinia 状态管理利器:探秘 storeToRefs 的神奇魔力

相关推荐
庸俗今天不摸鱼2 分钟前
【万字总结】前端全方位性能优化指南(十)——自适应优化系统、遗传算法调参、Service Worker智能降级方案
前端·性能优化·webassembly
QTX187302 分钟前
JavaScript 中的原型链与继承
开发语言·javascript·原型模式
黄毛火烧雪下9 分钟前
React Context API 用于在组件树中共享全局状态
前端·javascript·react.js
Apifox19 分钟前
如何在 Apifox 中通过 CLI 运行包含云端数据库连接配置的测试场景
前端·后端·程序员
一张假钞22 分钟前
Firefox默认在新标签页打开收藏栏链接
前端·firefox
高达可以过山车不行22 分钟前
Firefox账号同步书签不一致(火狐浏览器书签同步不一致)
前端·firefox
m0_5937581023 分钟前
firefox 136.0.4版本离线安装MarkDown插件
前端·firefox
掘金一周26 分钟前
金石焕新程 >> 瓜分万元现金大奖征文活动即将回归 | 掘金一周 4.3
前端·人工智能·后端
三翼鸟数字化技术团队1 小时前
Vue自定义指令最佳实践教程
前端·vue.js
Jasmin Tin Wei1 小时前
蓝桥杯 web 学海无涯(axios、ecahrts)版本二
前端·蓝桥杯