我有一个使用contentEditable
作为输入法的组件。感兴趣组件的部分是:
<div className="enter-edit-mode" onClick={view.enterEditMode}>
<div className="user-input" ref="content" contentEditable onInput={view.textChanged}></div>
</div>
该组件工作正常 - 它进入用户输入的textChanged
方法。该方法如下所示:
textChanged: function (e) {
var view = this,
textValue = e.target.innerHTML;
view.setState({
enteringText: textValue.length,
temporaryValue: textValue
});
}
当我尝试测试输入行为时, 我正面临的问题出现。设置使用酶, chai , sinon 完成。我正在使用一个简单的renderComponent
函数渲染组件,使用酶的mount
方法。
beforeEach(function () {
view = renderComponent(card);
viewReact = view.get(0);
});
it('should enter text changed method on input', function () {
let spy = sinon.spy(viewReact, 'textChanged');
view.find('.user-input').simulate('input');
expect(spy).to.have.been.called;
spy.restore();
});
它输出预期的textChanged至少被调用一次,但它从未被调用。 奇怪的部分是,如果我在组件的方法中放置console.log
,它就会到达那里。
我试图让它发挥作用
sinon.stub
代替spy
,因为我的方法可能无法正常使用view.find('.user-input').simulate('input', {target: {value: "lorem"})
或.simulate('input', {key: 'a'})
如果不是模拟输入而是viewReact.textChanged()
,它显然有效。
我猜测它是contentEditable的输入方法导致了这个问题。有什么建议?如何在onInput
方法中正确输入文字? (即使它进入textChanged
方法,文本为空)
答案 0 :(得分:1)
我可以重现您的问题,尝试测试以下组件(看起来与您的类似):
<div class="col-lg-4 col-md-4 col-sm-6 col-xs-12">
Your content here
</div>
我还设法以一种有点复杂的方式让测试工作:
const MyComponent = React.createClass({
textChanged(e) { console.log('text changed') },
render() {
return (
<div className="enter-edit-mode">
<div className="user-input" ref="content" contentEditable onInput={ this.textChanged }></div>
</div>
);
}
});
这个组件的it('should enter text changed method on input', () => {
let view = mount(<MyComponent/>);
let spy = sinon.spy(view.instance(), 'textChanged');
view = view.mount();
view.find('.user-input').simulate('input');
expect(spy).to.be.called;
spy.restore();
});
到re-mount似乎可以解决这个问题。
我根本不熟悉Enzyme(尽管我喜欢它:),但看起来它在组件周围添加了各种层,在这种情况下,Sinon间谍很容易“丢失”。
一个可能的警告:我使用view.mount()
在Node中进行了所有这些测试,而不是在浏览器中。
答案 1 :(得分:0)
我做了一点测试,我没有sinon但是我发现了一个用例:
class Home extends Component {
state = {
status: 'default'
}
textChanged = () => {
this.setState({
status: 'changed'
})
}
render () {
return (
<div className="enter-edit-mode" >
<div className="user-input" ref="content" contentEditable onInput={this.textChanged}>Hello</div>
<span>{this.state.status}</span>
</div>
)
}
}
和测试
describe('component', () => {
it('should say changed', () => {
const component = shallow(<Home />);
expect(component.find('span').text()).toEqual('default');
component.find('.user-input').simulate('input', {key: 'a'})
expect(component.find('span').text()).toEqual('changed');
});
});
它通过所有预期