javascript 用 Sinon 存根 React 组件方法

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/24280428/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-28 02:30:05  来源:igfitidea点击:

Stubbing a React component method with Sinon

javascriptreactjsstubsinon

提问by NiKo

I'm trying to stub a Reactcomponent method for testing purpose:

我正在尝试为测试目的存根React组件方法:

var Comp = React.createClass({
  displayName: "Comp",

  plop: function() {
    console.log("plop");
  },

  render: function() {
    this.plop();
    return React.DOM.div(null, "foo");
  }
});

var stub = sinon.stub(Comp.type.prototype, "plop");
React.addons.TestUtils.renderIntoDocument(Comp());
sinon.assert.called(stub); // throws

This sadly keeps printing "plop" onto the console… and the assertion fails.

可悲的是,这一直在控制台上打印“扑通”……并且断言失败了。

Note: Directly stubbing the spec object method works, but then you have to export the component constructor and the spec separately so they're both available in tests… Also, you'd need to stub the spec before even creating the component class; not so convenient:

注意:直接存根 spec 对象方法是可行的,但是您必须分别导出组件构造函数和规范,以便它们在测试中都可用……此外,您甚至需要在创建组件类之前存根规范;不太方便:

var CompSpec = {
  displayName: "Comp",

  plop: function() {
    console.log("plop");
  },

  render: function() {
    this.plop();
    return React.DOM.div("foo");
  }
};

var stub = sinon.stub(CompSpec, "plop");
var Comp = React.createClass(CompSpec);
React.addons.TestUtils.renderIntoDocument(Comp());

// plop() is properly stubbed, so you can
sinon.assert.called(stub); // pass

Can you think of another strategy to easily stub a React component method?

你能想到另一种轻松地存根 React 组件方法的策略吗?

回答by danvk

You're running up against React's auto-binding feature, which caches the .bind(this)which is wrapped around your class methods. You can get your code to work by stubbing the cached version of the method in React's __reactAutoBindMap:

您遇到了 React 的自动绑定功能,该功能会缓存.bind(this)包裹在您的类方法周围的 。您可以通过存根 React 中方法的缓存版本来使您的代码工作__reactAutoBindMap

var Comp = React.createClass({
  displayName: "Comp",

  plop: function() {
    console.log("plop");
  },

  render: function() {
    this.plop();
    return React.DOM.div(null, "foo");
  }
});

// with older versions of React, you may need to use
// Comp.type.prototype instead of Comp.prototype
var stub = sinon.stub(Comp.prototype.__reactAutoBindMap, "plop");  // <--
React.addons.TestUtils.renderIntoDocument(React.createElement(Comp));
sinon.assert.called(stub);  // passes

回答by Ron

Which test framework are you using?

您使用的是哪个测试框架?

If you use jasmine, I've found jasmine-reactto be a useful library for spying on React methods as well as replacing Components with test stubs.

如果您使用 jasmine,我发现jasmine-react是一个有用的库,用于监视 React 方法以及用测试存根替换组件。

In this case, you can spy on your method easily outside component definition.

在这种情况下,您可以轻松地在组件定义之外监视您的方法。

//Component Definition
var Comp = React.createClass({

    displayName: "Comp",

    plop: function() {
       console.log("plop");
    },

    render: function() {
       this.plop();
       return React.DOM.div(null, "foo");
    }
});

//test
it("should call plop method on render", function(){
   //spy on method
   jasmineReact.spyOnClass(Comp, "plop");
   React.addons.TestUtils.renderIntoDocument(Comp());
   expect(Comp.plop).toHaveBeenCalled();
})

jasmineReact.spyOnClassreturns an ordinary jasmine spy that you can use to track calls to it and its arguments.

jasmineReact.spyOnClass返回一个普通的茉莉花间谍,你可以用它来跟踪对它的调用及其参数。

If you want to actually stub the method and make it return something, you can do something like jasmineReact.spyOnClass(Comp, "plop").andReturn('something')

如果您想实际存根该方法并使其返回某些内容,则可以执行以下操作 jasmineReact.spyOnClass(Comp, "plop").andReturn('something')

Alternatively Facebook have recently launched a test framework Jest(also has jasmine as a dependency) which they use themselves for testing React components. Component methods can easily be stubbed using this framework. This looks like its worth checking out as well, but probably comes into its own a bit more when you write your components inside commonJS modules

或者,Facebook 最近推出了一个测试框架Jest(也有 jasmine 作为依赖项),他们用它自己来测试 React 组件。使用此框架可以轻松地对组件方法进行存根。这看起来也值得一试,但是当您在 commonJS 模块中编写组件时,它可能会变得更有意义