Vue报错:inject()仅可在setup()或函数式组件内使用,求代码修改方案
问题:inject()只能在setup()或函数式组件内使用的报错处理
报错信息
[Vue warn]: inject() can only be used inside setup() or functional components.
触发场景
该报错出现在使用await关键字后调用涉及inject()的逻辑时,useRoute()和useRouter()内部会调用inject(),推测await是诱因,但不清楚具体修改方式。
相关代码
router.js
import * as VueRouter from 'vue-router' import CategoryHome from './components/CategoryHome.vue' import CategoryShow from './components/CategoryShow.vue' const routes = [ // 省略路由配置 ] const router = VueRouter.createRouter({ // 省略路由创建配置 }) export default router
function.js
import { ref } from "vue" import router from './router.js' let categoryId = '' export async function initial() { try { const res = await axios.get('/api/max') categoryId = res.data.id router.push({name: 'category.show', params: { categoryId: categoryId }}) } catch(err) { console.log('error handling') } }
CategoryHome.vue
<script setup> import { onMounted, ref } from "vue" import * as func from '../functions.js' import router from '../router.js' const newCategory = ref('') onMounted(() => { func.initial() }) </script>
解决方案
核心原因分析
如果你的实际代码中使用了useRouter()而非直接导入全局路由实例,报错本质是:useRouter()属于Vue组合式API,必须在组件的setup()上下文(包括<script setup>、组件生命周期钩子)内调用。await会跳出当前上下文,后续再调用useRouter()就脱离了setup环境,触发inject()报错。
具体修改方案
方案1:通过组件传递路由实例(推荐)
- 修改
CategoryHome.vue,在setup上下文内获取路由实例并传给initial函数:
<script setup> import { onMounted, ref } from "vue" import { useRouter } from 'vue-router' import * as func from '../functions.js' const newCategory = ref('') const router = useRouter() // 在setup内获取路由实例 onMounted(() => { func.initial(router) // 传递路由实例 }) </script>
- 修改
function.js,接收传入的路由实例,并补充axios导入:
import axios from 'axios' // 必须导入axios,否则会报错 let categoryId = '' export async function initial(router) { try { const res = await axios.get('/api/max') categoryId = res.data.id router.push({name: 'category.show', params: { categoryId }}) } catch(err) { console.log('error handling') } }
方案2:确保全局路由实例正确使用
如果你坚持直接使用全局路由实例,需做以下检查和修改:
- 在
function.js顶部补充axios导入(当前代码缺失) - 检查
main.js中路由挂载顺序,确保先挂载路由再挂载应用:
import { createApp } from 'vue' import App from './App.vue' import router from './router.js' const app = createApp(App) app.use(router) // 先挂载路由 app.mount('#app') // 再挂载应用
内容的提问来源于stack exchange,提问作者sakamoto sora
相关产品推荐
相关产品推荐

