【问题标题】:How to mock API calls with axios in Jest?如何在 Jest 中使用 axios 模拟 API 调用?
【发布时间】:2020-03-13 04:24:02
【问题描述】:

我是测试新手,对使用 ES6 类模拟 API 和 axios 实例有一些疑问。

我有一个index.js

import axios from 'axios';

export default class Pushkin {
  constructor() {
    this.con = undefined;
  }

  connect(quizAPIUrl) {
    this.con = axios.create({
      baseURL: quizAPIUrl,
    });
  }
  
  prepExperimentRun(userID) {
    const postData = {
      user_id: userID,
    };
    return this.con.post('/startExperiment', postData);
  }
  
  // ......
}

我尝试了几种方法来测试它:

import axios from 'axios';
import Pushkin from '../src/index';

jest.mock('axios');

const quizURL = './api/quiz';
axios.create.mockImplementation(() => Promise.resolve(quizURL));

const pushkinClient = new Pushkin();

test('connect to quiz api url', () => {
  pushkinClient.connect(quizURL);
  // Pushkin { con: Promise { './api/quiz' } }
  pushkinClient.con.then((data) => expect(data).toEqual(quizURL));
});

test('prepExp', () => {
  const postData = { data: [{ user_id: 123456 }] };
  axios.post.mockImplementation(() => Promise.resolve(postData));
  pushkinClient.prepExperimentRun(123456).then((data) => expect(data).toBe(postData));
});

当我运行第二个测试prepExp 时,它会抛出错误TypeError: this.con.post is not a function。而this.con 就是Promise { './api/quiz' }

我应该如何模拟connect(quizAPIurl) 中的quizAPIurl 而不仅仅是硬编码?之后,模拟 axios 实例和测试 POST 请求的正确方法是什么?谢谢。

【问题讨论】:

  • 我不会测试 axios'post() - 可以肯定地假设它可以正常工作。不过,测试 post() 是否使用正确的参数调用是有效的。
  • @Yorkshireman 您能否更具体地说明我该怎么做?谢谢!
  • jestjs.io/docs/en/mock-functions.html expect(mockCallback.mock.calls[0][0]).toBe(42); 之类的东西(calls[0][0] 就是你所说的 mockCallback() ——特别是第一次调用的第一个参数)

标签: javascript jestjs axios


【解决方案1】:

那是因为你没有正确地模拟你的 create() 方法

axios.create.mockImplementation(() => Promise.resolve(quizURL));

这只会返回一个不包含post() 方法的Promise<string>。所以,当然,这将是“不是一个函数”。

一种解决方案是您可以使用 post 方法模拟对象:

axios.create.mockImplementation(() => { get: () => {...} });

另一种可能更聪明但我没有测试的方法,只是返回 axois 本身。

axios.create.mockImplementation(() => axios);

...

axios.post.mockImplementation(() => Promise.resolve(postData));

【讨论】:

  • 我会避开“模拟 axios 的行为,然后测试模拟的行为是否正常”,这基本上是这里所做的。当然,mock 的 getpost 方法会返回数据——你已经对 mock 进行了编程。
猜你喜欢
  • 2020-11-06
  • 2020-01-04
  • 2019-07-22
  • 1970-01-01
  • 2020-07-25
  • 2023-04-02
  • 2020-05-09
  • 2022-06-30
  • 2022-07-21
相关资源
最近更新 更多