自学内容网 自学内容网

vue3如何使用pinia设置全局状态,附常见面试题

1. stores/index.ts 文件

index.ts 中创建 store 实例并封装了注册逻辑,这样可以方便地将整个 Pinia 实例注册到 Vue 应用中。代码如下:

import type { App } from 'vue'
import { createPinia } from 'pinia'

const store = createPinia()

// 全局注册 store
export function setupStore(app: App<Element>) {
  app.use(store)
}

export * from './modules/blockAuthor'
  • createPinia 实例化了一个 Pinia 状态管理对象。
  • setupStore 函数将 store 注册到传入的 Vue 应用实例 app 上,使得整个应用都可以访问到 store。
  • export * from './modules/blockAuthor' 导出了 blockAuthor 模块中定义的内容,这样其他文件就可以直接从 stores 中引入它。

 

2. stores/modules/blockAuthor.ts 文件

blockAuthor.ts 定义了一个具体的 store,用于管理用户的“网格权限”。具体代码如下:

import { defineStore } from 'pinia'
import { StoreName } from '../storesName'
import { ref } from 'vue'
import { sysGridAPI } from '@/api/gridBlock/api'

export const useBlockAuthorStore = defineStore(StoreName.BLOCKAUTHOR, () => {
  /**
   * 用户网格权限
   */
  const authorList = ref([])

  /**
   * 更新 userBlockAuthor
   */
  async function updateUserBlockAuthor() {
    try {
      const res = await sysGridAPI.findGridBlockByUser()
      authorList.value = res.data.map((item) => item.id)
      console.log('pinia-store: updateUserBlockAuthor', updateUserBlockAuthor)
    } catch (error) {
      console.error('Failed to update user block author:', error)
    }
  }
  
  updateUserBlockAuthor()
  
  return {
    authorList
  }
})
  • authorList 是一个 ref 类型的响应式数组,用于保存用户的权限列表。
  • updateUserBlockAuthor 是一个异步函数,调用 sysGridAPI.findGridBlockByUser() 接口获取用户权限数据并将其存入 authorList 中。
  • 最后返回了 authorList,使得在其他组件中可以访问。

3. 在组件中使用

你在组件中这样使用 useBlockAuthorStore

import { useBlockAuthorStore } from '@/stores'

const authorList = authorStore.authorList

useBlockAuthorStore 通过 import 引入,并使用后即可访问 authorList 等数据,组件内就可以通过 authorList 实现响应式的数据展示或操作。

4. stores/storesName.ts

这种做法有助于集中管理 store 名称,使得在多个文件中引用 store 时保持一致,避免了硬编码字符串带来的拼写错误风险。这种方式非常适合在项目中有多个 store 模块时使用,便于维护和扩展。

export const enum StoreName {

  BLOCKAUTHOR = 'blockAuthor'
}
解释
  • const enum 是 TypeScript 提供的特性,用于定义常量枚举,它会在编译时直接内联字符串值(如 'blockAuthor'),减少运行时的额外代码开销。
  • BLOCKAUTHOR 是一个键,'blockAuthor' 是它的值。通过这种方式,BLOCKAUTHOR 可以直接代表 'blockAuthor' 字符串。
好处
  1. 避免硬编码字符串:在代码中不直接写 'blockAuthor',而是通过 StoreName.BLOCKAUTHOR 来引用,这样减少了手动输入字符串带来的错误。
  2. 提升可读性:通过在枚举中添加注释,可以清晰表达每个值的含义。
  3. 提高性能const enum 在编译时会直接替换为对应的字符串,不会生成多余的对象,因此性能更好。

面试题

1. Pinia 是什么?为什么要用它?

  • :Pinia 是 Vue 3 的官方状态管理库,它是 Vuex 的替代品,专为 Vue 3 和 Composition API 设计。与 Vuex 相比,Pinia 提供了更简洁的 API,更好的 TypeScript 支持,以及更小的体积和更高的性能。它允许我们定义 store、管理状态和处理逻辑,使得 Vue 应用的状态管理更加灵活、模块化和可扩展。

2. 如何在 Vue 3 中使用 Pinia?

  • :在 Vue 3 中使用 Pinia,首先需要创建 Pinia 实例并将其传递给 Vue 应用。然后,可以通过 defineStore 定义 store,并通过 useStore 在组件中访问 store。
    • 步骤
  • main.ts 中创建 Pinia 实例并注册:
    import { createPinia } from 'pinia'
    const pinia = createPinia()
    app.use(pinia)
    

    2. 使用 defineStore 定义一个 store:

    import { defineStore } from 'pinia'
    
    export const useUserStore = defineStore('user', {
      state: () => ({
        name: 'John Doe',
        age: 30
      }),
      actions: {
        setName(name: string) {
          this.name = name
        }
      }
    })
    

    3. 在组件中使用 store:

    import { useUserStore } from '@/stores/user'
    
    const userStore = useUserStore()
    userStore.setName('Jane Doe')
    console.log(userStore.name)
    

    3. Pinia 与 Vuex 有什么区别?

  • :Pinia 和 Vuex 都是用于管理全局状态的库,但它们有一些关键区别:
    • 响应式系统:Pinia 使用 Vue 3 的 Proxy 实现响应式,性能和灵活性上更优。Vuex 使用 Object.defineProperty,相比之下不如 Pinia 高效。
    • API 设计:Pinia 的 API 更简洁、直观。它使用 Composition API 风格,支持 defineStore 和直接返回对象的方式来定义 store,而 Vuex 更加偏向于 options API 风格。
    • TypeScript 支持:Pinia 提供了更好的 TypeScript 支持,能够更好地推导类型,减少手动声明类型的需求。
    • 模块化:Pinia 的 store 是通过 defineStore 定义的,每个 store 都是一个独立的模块,具有清晰的结构。

  • 4. 如何在 Pinia 中使用异步操作?

  • :在 Pinia 中,异步操作通常通过 actions 来处理。在 actions 中定义异步函数,可以像操作同步数据一样处理异步逻辑。示例如下:
    import { defineStore } from 'pinia'
    import { api } from '@/api'
    
    export const useUserStore = defineStore('user', {
      state: () => ({
        userData: null
      }),
      actions: {
        async fetchUserData() {
          try {
            const response = await api.getUserData()
            this.userData = response.data
          } catch (error) {
            console.error('Failed to fetch user data', error)
          }
        }
      }
    })
    

    5. 如何在 Pinia 中使用 getters?

  • :Pinia 支持使用 getters 来派生状态数据。getters 允许我们定义基于状态的计算值。例如,如果你有一个 user 的 store,你可以定义一个 getter 来计算用户的全名:
    import { defineStore } from 'pinia'
    
    export const useUserStore = defineStore('user', {
      state: () => ({
        firstName: 'John',
        lastName: 'Doe'
      }),
      getters: {
        fullName: (state) => `${state.firstName} ${state.lastName}`
      }
    })
    


原文地址:https://blog.csdn.net/weixin_51687565/article/details/143558975

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!