在 Nuxt 3 文档中,有一个 example 展示了如何使用服务器中间件通过
event.context
使用附加信息来注释请求:
export default defineEventHandler((event) => {
event.context.auth = { user: 123 }
})
但是,没有示例说明如何为此进行相应的 TypeScript 键入。我希望我的
event.context.auth
不是 any
类型。
标准 TypeScript 库类型扩展方法在这里似乎无法正常工作。我尝试制作一个包含以下内容的
shims.d.ts
:
declare module 'h3' {
interface H3EventContext {
auth: AuthSession
}
}
但是,这会破坏
defineEventHandler
函数的类型推断,使所有 event
参数变成隐式 any
。如何在不破坏内容的情况下声明我的事件上下文类型?
为此,我们可以使用 TypeScript 的声明合并。由于 Nuxt 在幕后使用
h3
模块,因此我们需要扩展 h3
模块并添加自定义类型。我们可以做这样的事情:
type MyFancyAuthType = {
user: number
}
declare module 'h3' {
interface H3EventContext {
auth: MyFancyAuthType;
// any other type
}
}
export default defineEventHandler((event) => {
// Here you will be able to access .auth on context with proper intellisense
event.context.auth = { user: 123 }
})
您可以在单独的文件中明确定义它,例如
shim.d.ts
。如果你这样做,你需要告诉 TypeScript 编译器。
tsconfig.json
{
...
"files": ["shim.d.ts"]
...
}
此外,您需要确保必须添加
export default {}
。应该是这样的:
shim.d.ts
...
declare module 'h3' {
...
}
// this is important
export default {};
请注意,虽然这是 TypeScript 社区中广泛采用的约定,但它并不是 TypeScript 本身记录的官方语言功能。
我不确定为什么您的事件会被输入为any。它不应该这样做,为了测试这一点,我在 StackBlitz 上创建了一个示例,证明您所做的应该按预期工作。
https://stackblitz.com/edit/nuxt-starter-uhgayq?file=server%2Fapi%2Ftest.ts
事件的类型为H3Event,event.context为H3EventContext,event.context.authenticatedUser为User。用户在 /server/user.ts 中定义
也许我错过了一些东西,但正如你所看到的,它应该按照你的方式工作得很好。