【问题标题】:Mock an axios call in a vue method using Jest使用 Jest 在 vue 方法中模拟 axios 调用
【发布时间】:2020-07-23 15:39:35
【问题描述】:

我一直在寻找解决方案,但其他问题与我的用例并不匹配。 我在 Vue 文件中有一个函数:

getStatus () {
      const statusRetriveKey = 0
      // Sets parameters from external file
      const url = serverDetails.url
      const params = { ...serverDetails.params }
      axios
        .get(`${url}admin/${statusRetriveKey}`, {
          params
        })
        .then((response) => {
          this.systemStatus = response.data[0].systemStatus
          this.alert = response.data[0].alert
          this.awayMessage = response.data[0].awayMessage
        })
        // Catch and display errors
        .catch((error) => {
          this.error = error.toString()
          console.log('Error on check System status: ' + error)
        })
    },

我正在尝试在 Jest 中编写一个单元测试来检查数据变量;如果 GET 请求返回的是 systemStatus、alert 和 awayMessage 设置正确。

到目前为止,我有以下内容:

    it("Should call axios and return data", async () => {
        mockAxios.get.mockImplementationOnce(() => Promise.resolve({
            data:{
                systemStatus: true,
                //the other variables
              }
        }))
        const response = await wrapper.vm.getStatus();
        console.log(response)
        expect(wrapper.vm.$data.systemStatus).toBe(true)
        expect(mockAxios.get).toHaveBeenCalledTimes(1);
    })

但是我收到的是系统状态变量:

expect(received).toBe(expected) // Object.is equality
    Expected: true
    Received: null

我知道模拟没有将数据输入到方法中,但不确定如何解决。是不是因为我没有从 vue 文件中的方法显式返回,而是使用 this 来设置数据值?


解决方案:

// Import dependencies
import { shallowMount } from '@vue/test-utils'
import axios from 'axios'
// Import component
import Page from 'path'

jest.spyOn(axios, "get").mockImplementation(() => Promise.resolve({ data: [{ systemStatus: false, ...:..., ...:... }] }));


// Set Model data
const models = {
  ...
  }
}
describe('Page', () => {
  let wrapper
  beforeEach(() => {
    wrapper = shallowMount(Page, {
      propsData: {
        model: models
      },
    })
  })
  it("Should call axios and return data", async () => {
    await wrapper.vm.getStatus();
    expect(wrapper.vm.$data.systemStatus).toBe(false)
    expect(wrapper.vm.$data....).toBe('...')
    expect(wrapper.vm.$data....).toBe('...')
  },)
})

【问题讨论】:

    标签: javascript html unit-testing vue.js jestjs


    【解决方案1】:

    所以不确定这里的 mockAxios 是什么,是不是一些 npm 模块?

    一种方法是使用spyOn

    import axios from 'axios';
    
    jest.spyOn(axios, "get").mockImplementationOnce(() => Promise.resolve({data: {/* Here you can add your data */}));
    

    所以在你的测试中,注意mockImplementationOnce。 它只会被嘲笑一次

        it("Should call axios and return data", async () => {
            await wrapper.vm.getStatus();
        })
    

    编辑:

    在您记录响应的行上,您将始终未定义,因为您在函数 getStatus 中没有返回语句。

    【讨论】:

    • 谢谢,好像更接近了。现在我的测试是调用 vue 文件中的函数,但是为数据变量设置的值是来自 actual GET 请求的值,而不是 jest.spyOn 行中设置的值?
    • 因为这个测试数据变量不应该来自实际的 GET,所以您在 Promise.resolve 中传递的所有内容都应该被视为您的 GET 请求的响应。
    • 是的,但不是从 Promise.resolve 获取值,测试文件出于某种原因从实际 GET 中提取
    • hm.. 在这个例子中我们使用了 mockImplementationOnce,它只会模拟一次。您是否有机会发送一个以上的 GET 请求?如果是这种情况 jest.spyOn.. 在该测试中应该会有所帮助
    • 经过更多的摆弄之后,我得到了它的工作。感谢一百万,解决方案添加到问题
    猜你喜欢
    • 2020-01-04
    • 2019-07-22
    • 1970-01-01
    • 2020-11-06
    • 2023-04-02
    • 2019-11-22
    • 2022-07-21
    • 1970-01-01
    • 2020-03-07
    相关资源
    最近更新 更多