[axios]用nock拦截请求

2024-05-15 21 views
9

你好,我想知道是否可以通过 nock 拦截 axios 发出的请求以进行测试,有人尝试过吗?

预先感谢您的帮助

回答

8

我在https://github.com/mzabriskie/axios/issues/175上写了这篇文章,但是您是否在处理来自 axios 的 POST 请求时失败了?我的诺克不匹配,因为诺克似乎试图匹配 OPTIONS 方法。https://github.com/mzabriskie/axios/issues/225

我正在使用 axios 0.10.0 和 nock 8.0.0。

这是我的 nok 拦截代码:

nock('http://localhost:5000')
  .post(`/path`, data)
  .log(console.log)
  .reply(200, { id: 1 })

我的 axios 初始化:

import axios from 'axios'

const instance = axios.create({
  baseURL: (process.env.NODE_ENV === 'production') ? 'https://foo.com/' : 'http://localhost:5000/',
  headers: {
    ...
  }
})

export default instance

调用axios:

axios.post('/path', {})

然后我就去Network Error考试了。log(console.log)on nok 输出:

matching http://localhost:5000 to POST http://localhost:5000/foo: false 

当我运行它时,DEBUG=nock.*我得到: https://gist.github.com/chibicode/39a17e2e7aa46899865b8b10379b26f4

我看到一堆 OPTIONS 请求,也许 nock 没有正确匹配它?

1

@chibicode 是的,这可能就是正在发生的事情,你能解决这个问题吗?

6

同样的问题在这里无法用 nock 进行测试。

6

我对 nock 没有太多经验,但我对它的价值有一些建议。

  • 如果您想避免OPTIONS方法并在节点中运行,您可以强制使用节点适配器:axios.defaults.adatper = require('axios/lib/adapters/http');
  • 尝试使用moxios来模拟您的测试,这是我专门为测试 axios 客户端而创建的。
8

因不活跃而关闭。希望这moxios能为每个人解决问题:)

3

编辑:哦,天啊。我刚刚意识到拼写defaults.adapter = ...错误。Network Error至少消失了!

使用:

  • axios 0.14.0
  • react 15.3.1
  • nock 8.0.0

我尝试了axios.defaults.adatper = require('axios/lib/adapters/http');正在测试的特定文件,但仍然遇到问题。

我还用于nock模拟 API 请求,并axios在 React.js 生命周期方法中测试请求。

我可能错误地使用了所有这些,但很想阅读其他人的想法。 ?

这是我收到的错误:

{ [Error: Network Error]
      config:
       { transformRequest: { '0': [Function: transformRequest] },
         transformResponse: { '0': [Function: transformResponse] },
         headers: { Accept: 'application/json, text/plain, */*' },
         timeout: 0,
         xsrfCookieName: 'XSRF-TOKEN',
         xsrfHeaderName: 'X-XSRF-TOKEN',
         maxContentLength: -1,
         validateStatus: [Function: validateStatus],
         adatper: [Function: httpAdapter],
         method: 'get',
         params: { initial: true },
         url: 'http://localhost:8080/api/test,
         data: undefined },
      response: undefined }
6

经过三天的“把头撞在墙上”之后,我找到了这篇文章并尝试了 moxios。第一次工作。感谢 @mzabriskie 阻止我作为一名开发人员退休并成为一名咖啡师;)

5

对我有用:

import {expect} from 'chai'
import axios from 'axios' // v0.15.3
import httpAdapter from 'axios/lib/adapters/http'
import nock from 'nock' // v9.0.2

const host = 'http://localhost';

axios.defaults.host = host;
axios.defaults.adapter = httpAdapter;

describe('suite', () => {
  it('test', done => {
    nock(host)
      .get('/test')
      .reply(200, 'test data');

    axios.get('/test').then(response => {
      expect(response.data).to.be.equal('test data');
      done();
    });
  });
});
6

为了测试 React 生命周期,我需要添加 axios.defaults.adapter = httpAdapter;

不在测试文件中,而是在其他文件中(我的操作创建者导入了 axios,因此在测试中添加该行将无济于事),这意味着当我不进行测试时,该行也将运行。它会影响 axios 的工作方式并会导致生产问题吗?

3

好的。这样做的坏处是,现在你的测试需要了解 axios 而不仅仅是 nock。但很高兴您找到了一种混合解决方案,可以让您仍然使用诺克。

我不喜欢我的测试必须了解 axios。当我使用 superagent 时,我的测试使用 nock 并且不知道 jack 有关 superagent 的信息,这意味着我的测试与他们正在测试的实际实现更加解耦

7

如果您使用axios v18.0,请确保将nock主机设置为与axios baseURL相同

// Instead of 
axios.defaults.host = host;
axios.defaults.baseURL = host;
// Then
nock(host)...
6

TL;DR - 如果您正在使用 Jest 并在 node.js env 下进行测试,请将其添加到您的jest.config.js testEnvironment: 'node'

幕后花絮

根据我的经验,有同样的问题,当 Axios 在所有其他方法之前启动 OPTIONS 调用时,nock 失败。所以使用adapter/http帮助,但这不是完整的图片。因为在 Node 中,我们默认使用 http 适配器:

取自 axios.js

    function getDefaultAdapter() {
      var adapter;
      if (typeof XMLHttpRequest !== 'undefined') {
        // For browsers use XHR adapter
        adapter = __webpack_require__(12);
      } else if (typeof process !== 'undefined' && Object.prototype.toString.call(process) === '[object process]') {
        // For node use HTTP adapter
        adapter = __webpack_require__(12);
      }
      return adapter;
    }

所以这里的问题是测试环境确实XMLHttpRequest在全局范围内存在,因为 jest 默认在 jsdom 下运行。如果您的测试在基本环境下运行,node您可以将其添加到您的jest.config testEnvironment: 'node'