我试图理解用 Vitest 模拟 Vue-Router 的逻辑。
为此,我尝试在一个非常简单的项目上设置并模拟我的测试环境。当我尝试按照Vue-Test-Utils的官方文档进行操作时,总是出现错误。我不知道是不是因为他们使用 Jest。
使用真正的 vue-router 解决了我的问题,但我认为模拟 vue-router 更好。
下面我先传达一下项目的源码,然后是我收到的错误。
<script setup lang="ts">
import {onMounted} from "vue";
import {useRoute} from "vue-router";
const route = useRoute()
onMounted(() => {
console.log(route.query)
})
</script>
<template>
<div>Home</div>
</template>
import {expect, it, vi} from "vitest";
import {mount} from "@vue/test-utils";
import Home from "../src/components/Home.vue"
it('Home Test', async () => {
const wrapper = mount(Home)
expect(wrapper.exists()).toBeTruthy()
})
/// <reference types="vitest" />
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
// https://vitejs.dev/config/
export default defineConfig({
plugins: [vue()],
test: {
environment: 'jsdom',
include: ['./test/**/*.spec.ts'],
exclude: ['node_modules', 'dist'],
globals: true
}
})
我尝试像下面这样模拟 vue-router
vi.mock('vue-router', () => ({
useRoute: vi.fn(),
}))
或者只是
vi.mock('vue-router')
import {expect, it, vi} from "vitest";
import {mount} from "@vue/test-utils";
import Home from "../src/components/Home.vue"
vi.mock('vue-router')
it('Home Test', async () => {
const wrapper = mount(Home, {
global: {
stubs: ["router-link", "router-view"]
}
})
expect(wrapper.exists()).toBeTruthy()
}) Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号
首先,我希望在
Home.vue中看到router-link或router-view:<script setup lang="ts"> import { onMounted } from 'vue'; import { useRoute } from 'vue-router'; const route = useRoute(); onMounted(() => { console.log(route.query); }); </script> <template> <router-link to="home">Go to home</router-link> <router-view /> </template>因此,
Home.spec.ts应该是这样的:import { expect, it, vi } from 'vitest'; import { mount } from '@vue/test-utils'; import * as VueRouter from 'vue-router'; import Home from '../src/components/Home.vue'; describe('./path/to/Home.vue', () => { const useRouteSpy = vi.spyOn(VueRouter, 'useRoute'); const getWrapper = () => mount(Home as any, { global: { stubs: { 'router-link': { template: '<div/>' }, 'router-view': { template: '<div/>' }, }, }, }); it('the component should be mounted', () => { // ARRANGE const useRouteMock = useRouteSpy.mockImplementationOnce({ query: 'query' }); // ACT const wrapper = getWrapper(); // ASSERT expect(useRouteMock).toHaveBeenCalled(); expect(wrapper.exists()).toBeTruthy(); }); });一些评论/建议:
.spyOn()和.mockImplementation...()进行监视和模拟.toHaveBeenCalled...()检查模拟是否按预期工作mount()函数中的存根应与模板中使用的组件相关(因此,如果您不使用,它不应该被列为存根)希望有帮助, 干杯!