使用 Jest 为 Vue 组件中的方法编写单元测试

时间:2021-06-22 06:21:09

标签: vue.js unit-testing jestjs

我开始使用 Jest Vue 进行单元测试。我想测试 Vue 组件中的现有方法,我编写了一个测试但它没有通过。而且我不知道如何在测试中模拟和调用该方法。

如何编写一个好的单元测试,以通过“goPage()”方法的功能?

我的方法是:

goPage(id, name, categoryId) {
   this.headerSearchInput = name
   this.$router.push({
      path: '/categories/' + categoryId + '/courses/' + id,
      query: { query: this.headerSearchInput },
   })
}

我的测试是:

import { shallowMount, createLocalVue } from '@vue/test-utils'
import HeaderSearch from '../../components/header/HeaderSearch.vue'

const localVue = createLocalVue()
localVue.use(VueRouter)
const router = new VueRouter()

describe('Header search component', () => {
   const mockRoute = {
      path: '/categories/' + 2 + '/courses/' + 4,
      query: {
        query: searchedText,
      },
   }
   const mockRouter = {
      push: jest.fn(),
   }
   const wrapper = shallowMount(HeaderSearch, {
      router,
      localVue,
      stubs: {
        NuxtLink: true,
      },
      global: {
        mocks: {
          $route: mockRoute,
          $router: mockRouter,
        },
      },
   })
   test('redirect to course page, goPage', async () => {
      const courseId = 4
      const courseTitle = 'Inbound Marketing'
      const categoryId = 2

      const mockedFunction = jest.fn()
      wrapper.vm.goPage(courseId, courseTitle, categoryId)
      await wrapper.setData({
        headerSearchInput: courseTitle,
      })
      const expectedRouter = {
        path: '/categories/3/courses/4',
        query: { query: wrapper.vm.headerSearchInput },
      }
      expect(mockedFunction).toBeCalledWith(courseId, courseTitle, categoryId)
      expect(wrapper.vm.$router.path).toEqual(expectedRouter.path)
   })
})

2 个答案:

答案 0 :(得分:1)

当您测试路由时,您应该只使用模拟而不在您的 VueRouter 实例上安装 local Vue。正如官方 documentation 所说:

<块引用>

在 localVue 上安装 Vue Router 也会将 $route 和 $router 作为只读属性添加到 localVue。这意味着在使用安装了 Vue Router 的 localVue 挂载组件时,您不能使用 mocks 选项来覆盖 $route 和 $router。

所以你需要在 localVue 调用中获得 shallowMount 并且只留下 $router 嘲讽:

然后在测试中,您只需调用 goPage 方法并检查 $router.push() 是否使用特定参数调用。 不检查 $route.path 是否已更改,将其留给端到端测试。

let wrapper
describe('HelloWorld.vue', () => {
  beforeEach(() => {
    wrapper = shallowMount(HelloWorld, {
      global: { mocks: { $router: { push: jest.fn() } } }
    })
  })

  test('redirect to course page, goPage', async () => {
    const courseId = 4
    const courseTitle = 'Inbound Marketing'
    const categoryId = 2
    const expectedRouter = {
      path: '/categories/' + categoryId + '/courses/' + courseId,
      query: { query: 'Inbound Marketing' }
    }
    wrapper.vm.goPage(courseId, courseTitle, categoryId)
    expect(wrapper.vm.$router.push).toBeCalledWith(expectedRouter)
  })
})

答案 1 :(得分:0)

我解决了我的问题,如下所示:

let wrapper
describe('HeaderSearch', () => {
   const $route = {
     path: '/categories/2/courses/4',
   }
   const $router = {
     push: jest.fn(),
   }
   beforeEach(() => {
   wrapper = shallowMount(HeaderSearch, {
      mocks: {
        $route,
        $router,
      },
  })
})

test('go to each course page', () => {
  const courseId = 4
  const categoryId = 2
  const courseTitle = 'Inbound Marketing'

  wrapper.vm.goPage(courseId, courseTitle, categoryId)
  const expectedRouter = {
    path: '/categories/' + categoryId + '/courses/' + courseId,
    query: { query: courseTitle },
  }
  expect(wrapper.vm.$router.push).toBeCalledWith(expectedRouter)
  })
})
相关问题