// import { defineStore } from 'pinia'
// const useCounterStore = defineStore('counter', {
// state: () => {
// return {
// count: 0,
// }
// },
// actions: {
// increment() {
// this.count++
// },
// reset() {
// this.count = 0
// },
// },
// })
// export default useCounterStore
// store/counterStore.ts
import { defineStore } from 'pinia'
export const useCounterStore = defineStore('counter', {
state: () => ({
count: 0, // 初始值
}),
actions: {
increment() {
this.count++ // 递增逻辑
},
reset() {
this.count = 0 // 重置逻辑
},
},
})
这两种暴露方式有什么区别,为什么用上面那个会标红
这两种暴露方式的核心区别在于模块导出方式的不同,而标红问题通常与TypeScript类型推断或模块导出规范有关。
1. 两种导出方式的区别
第一种方式:默认导出(export default
)
// 先定义变量,再默认导出
const useCounterStore = defineStore(/* ... */)
export default useCounterStore
- 这是默认导出(default export),一个模块只能有一个默认导出。
- 导入时可以自定义名称,例如:
import MyCounter from '../store/counterStore.ts' // 名称可自定义
第二种方式:命名导出(export const
)
// 直接命名导出
export const useCounterStore = defineStore(/* ... */)
- 这是命名导出(named export),一个模块可以有多个命名导出。
- 导入时必须使用相同的名称(需加
{}
):import { useCounterStore } from '../store/counterStore.ts' // 名称必须一致
2. 第一种方式标红的可能原因
如果第一种方式(默认导出)出现标红,通常与以下原因有关:
(1)TypeScript类型推断问题
Pinia的defineStore
函数会返回一个带类型的函数,默认导出时,TypeScript有时无法正确推断其类型,导致导入时出现类型错误(标红)。
(2)导入方式不匹配
如果使用默认导出,却用命名导入的语法,会直接报错:
// 错误示例:默认导出却用命名导入
import { useCounterStore } from '../store/counterStore.ts'
// 正确示例:默认导出需要对应默认导入
import useCounterStore from '../store/counterStore.ts'
(3)ES模块规范冲突
某些项目配置(如tsconfig.json
中的module
或moduleResolution
)可能更严格,要求使用命名导出以保证类型一致性,默认导出可能触发类型检查警告。
3. 推荐用法
在Pinia中,更推荐使用命名导出(第二种方式),原因如下:
- 符合Pinia官方示例的推荐写法,社区共识更强。
- 类型推断更可靠,减少TypeScript类型错误。
- 便于在一个模块中导出多个Store(如果需要)。
- 导入时明确指定名称,代码可读性更高。
如果坚持使用默认导出,需确保导入方式匹配(不用{}
),并检查项目的TypeScript配置是否兼容。