在Nuxt中间件中调用自定义composable触发实例访问合规性错误的问题求助
在Nuxt中间件中调用自定义composable触发实例访问合规性错误的问题求助
看起来你遇到的问题主要有两个关键点,咱们一步步来排查解决:
1. 页面Meta定义的错误(最可能的根源)
你在页面的setup()函数内部调用definePageMeta,这是不符合Nuxt 3规范的!definePageMeta是编译时宏,必须放在组件的顶级作用域(比如<script setup>的最外层,或者传统选项式API的组件根对象里),不能嵌套在setup()函数中。
错误写法:
<script lang="ts"> export default { setup() { definePageMeta({ middleware: ["auth", "org"], layout: 'dashboard' }) } } </script>
正确写法二选一:
选项式API写法
<script lang="ts"> export default { middleware: ["auth", "org"], layout: 'dashboard' } </script>
<script setup>写法(更推荐)
<script setup lang="ts"> definePageMeta({ middleware: ["auth", "org"], layout: 'dashboard' }) </script>
这个错误会导致Nuxt无法正确识别页面的中间件绑定,进而让中间件在非预期的上下文环境中执行,触发“composable在中间件外调用”的错误。
2. useNewSession组合式函数的逻辑优化
即使修复了页面Meta,你的useNewSession里还有几个可能导致上下文丢失的小问题:
- 你在调用
navigateTo之后才创建toast,这时候导航已经触发,上下文可能被销毁,导致useToast无法获取Nuxt实例 navigateTo返回的是一个Promise,直接调用而不处理的话,后续的throw error可能会中断导航逻辑
优化后的useNewSession.ts:
export default async function() { const supabase = useNuxtApp().$supabase const { data, error } = await supabase.auth.refreshSession() if (error || !data.session) { // 先创建toast,再触发导航 const toast = useToast() toast.add({ title: 'Session error', description: error?.message || 'Failed to refresh session', color: 'error', }) // 用await确保导航逻辑执行完成,同时终止后续代码 await navigateTo('/login') throw error || new Error('No session available') } return data.session }
3. 中间件的小优化
在你的org中间件中,useFetch返回的error如果抛出的话,最好处理一下避免未捕获的Promise rejection:
export default defineNuxtRouteMiddleware(async () => { try { const newSession = await useNewSession() const accessToken = newSession.access_token const { data, error } = await useFetch('/api/organization', { headers: { authorization: `Bearer ${accessToken}` } }) if (error.value) { throw error.value } const organizationCookie = useCookie('organization') organizationCookie.value = JSON.stringify(data.value) } catch (err) { console.error('Org middleware error:', err) // 可以在这里添加统一的错误处理,比如跳转到错误页 await navigateTo('/error') } })
总结
先修复页面Meta的definePageMeta调用位置,这应该能解决“composable不在中间件中”的错误提示。如果还有问题,再替换优化后的useNewSession代码,确保上下文不会提前丢失。
内容来源于stack exchange
相关产品推荐
相关产品推荐

