我不太确定为什么会这样,我有一个非常简单的组件和测试,但是在✖ should call getState on TestStore
上失败了。但是随着getStateFromStores
被调用,它也应该被调用,对吗?我无能为力。
import React, { PropTypes } from 'react'
import TestStore from '../stores/TestStore'
export default class TestComponent extends React.Component {
static propTypes = {
}
static getStateFromStores() {
return TestStore.getState()
}
constructor(props) {
super(props)
this.state = TestComponent.getStateFromStores()
}
render() {
return (
<div>
<img src='' alt=''/>
</div>
)
}
}
测试:
var React = require('react')
var TestUtils = require('react/lib/ReactTestUtils')
var Immutable = require('immutable')
const mockTestStoreData = Immutable.fromJS({
one: {
foo: 'bar'
},
two: {
bar: 'baz'
}
})
describe('TestComponent.jsx', () => {
var TestStore
var TestComponent
var TestComponentEl
var renderedRootElement
var renderedDOMNode
beforeEach(() => {
TestStore = require('../../stores/TestStore')
spyOn(TestStore, 'getState') // .and.returnValue(mockTestStoreData)
TestComponent = require('../TestComponent.jsx')
spyOn(TestComponent, 'getStateFromStores')
TestComponentEl = React.createElement(TestComponent)
renderedRootElement = TestUtils.renderIntoDocument(TestComponentEl)
renderedDOMNode = React.findDOMNode(renderedRootElement)
})
it('should be rendered within a div', () => {
expect(renderedDOMNode.tagName.toUpperCase()).toEqual('DIV')
})
it('should have a static getStateFromStores function', () => {
expect(TestComponent.getStateFromStores).toBeDefined()
})
it('should call getStateFromStores on construction', () => {
expect(TestComponent.getStateFromStores).toHaveBeenCalled()
})
it('should call getState on TestStore', () => {
expect(TestStore.getState).toHaveBeenCalled()
})
})
最佳答案
应该从TestStore.getState()
调用TestComponent.getStateFromStores()
,但是您正在监视TestComponent.getStateFromStores()
:
...
spyOn(TestComponent, 'getStateFromStores');
...
因此在测试过程中不会调用实际的实现。要监视一个函数并调用它,可以更改为:
spyOn(TestComponent, 'getStateFromStores').and.callThrough();
Documentation for callThrough()。
话虽这么说,测试方法是否在要测试的模块内部被调用可能也是特定于实现的。最好让测试更注重因果关系。因此,我建议的解决方案是进行以下调整:
var React = require('react')
var TestUtils = require('react/lib/ReactTestUtils')
var Immutable = require('immutable')
const mockTestStoreData = Immutable.fromJS({
one: {
foo: 'bar'
},
two: {
bar: 'baz'
}
})
describe('TestComponent.jsx', () => {
var TestStore
var TestComponent
var TestComponentEl
var renderedRootElement
var renderedDOMNode
beforeEach(() => {
TestStore = require('../../stores/TestStore')
spyOn(TestStore, 'getState').and.returnValue(mockTestStoreData);
TestComponent = require('../TestComponent.jsx')
// don't spyOn(TestComponent, 'getStateFromStores')
TestComponentEl = React.createElement(TestComponent)
renderedRootElement = TestUtils.renderIntoDocument(TestComponentEl)
renderedDOMNode = React.findDOMNode(renderedRootElement)
})
it('should be rendered within a div', () => {
expect(renderedDOMNode.tagName.toUpperCase()).toEqual('DIV')
})
it('should have a static getStateFromStores function', () => {
expect(TestComponent.getStateFromStores).toBeDefined()
})
// don't
//it('should call getStateFromStores on construction', () => {
// expect(TestComponent.getStateFromStores).toHaveBeenCalled()
//})
// don't
//it('should call getState on TestStore', () => {
// expect(TestStore.getState).toHaveBeenCalled()
//})
// instead
it( 'should get its initial state from TestStore', () => {
expect(TestStore.getState).toHaveBeenCalled(); // I'd say optional
expect( TestComponent.state ).toEqual( mockTestStoreData );
})
})
现在,您可以随意更改实现并测试重要的内容:TestComponent初始化后的状态。
关于javascript - React/Flux + Jasmine -预期的 spy 被称为失败,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/30171054/