在 angularjs 测试粘贴和按键事件中使用 element.triggerHandler() 似乎没有效果
Using element.triggerHandler() in angularjs tests for paste and keypress events doesn't seem to have an effect
想知道是否有人可以阐明如何在 angularjs 单元测试中为 paste
和 keypress
事件正确使用 element.triggerHandler()
。
我有两个指令,一个用于限制用户在达到长度限制后继续触发元素中的 keypress
事件的能力。第二个是防止用户在文本长度超过限制时将文本粘贴到元素中。
请参阅以下 plunker 以获取包含我失败测试的完整示例:https://plnkr.co/edit/5Yyv2cnn3dRKzsj2Lj61?p=preview
对于 paste
测试,我知道我没有使用正确的语法,但一直无法找到正确的方法。有什么建议吗?
element.triggerHandler('paste', 'astring')
对于 keypress
测试,我相信我正确地触发了事件,但它似乎没有更新元素的值(使用 element.val()
检索)
在此问题上停留了一段时间,如有任何帮助,我们将不胜感激。谢谢!
让我们首先简要分析当用户按下并释放带有焦点的 1
键时可能发生的情况(真正取决于浏览器实现)输入:
- 事件
keydown
已触发
- 事件
keypress
已触发
- 输入值更改为
1
并触发事件 input
- 事件
keyup
已触发
JS 没有办法真正模拟用户按下一个键。您可以模拟的是用户这样做时(通常)发生的事情,例如上面的步骤。
triggerHandler
函数为特定元素上的指定事件类型执行与 jQuery 绑定的所有处理程序。
所以使用 triggerHandler
和 keypress
不会模拟用户按下一个键,它只会触发事件,就像上面的第 2 步一样。该值不会更改,因为那是在另一步中发生的。
现在,有人会认为在 limitKeypressLength
指令的测试中,您可以自己简单地模拟上面步骤 3 的第一部分(只需手动设置值):
for (var i = 0; i < 10; i++) {
element.triggerHandler({type: 'keypress', keyCode: 49});
element.val(element.val() + '1');
}
expect(element.val()).toBe('1111111111');
element.triggerHandler('keypress', {which: 49});
element.val(element.val() + '1');
expect(element.val()).toBe('1111111111');
但这不会起作用,因为即使在您的指令中捕获了第十一个按键事件,下面的代码仍会执行并更新值。
limitKeypressLength
指令的基本功能是监听按键事件并调用 event.preventDefault
或不基于。这就是你要测试的。
例如:
// Set value to something longer than allowed
element.val('123456789123456789');
// Create the event
var e = jQuery.Event('keypress', {
keyCode: 49
});
// Create a spy
spyOn(e, 'preventDefault');
// preventDefault should not have been called yet
expect(e.preventDefault).not.toHaveBeenCalled();
// Trigger the event
element.triggerHandler(e);
// Assert that preventDefault has been called
expect(e.preventDefault).toHaveBeenCalled();
演示: https://plnkr.co/edit/ktmcBGSuTdMnvqVRlkeQ?p=preview
现在您可以轻松测试何时将元素值设置为 equal/below 允许值。
limitPasteLength
指令基本上也是如此,因为它的目的也是根据条件调用 preventDefault
,只是需要做一些额外的模拟。
想知道是否有人可以阐明如何在 angularjs 单元测试中为 paste
和 keypress
事件正确使用 element.triggerHandler()
。
我有两个指令,一个用于限制用户在达到长度限制后继续触发元素中的 keypress
事件的能力。第二个是防止用户在文本长度超过限制时将文本粘贴到元素中。
请参阅以下 plunker 以获取包含我失败测试的完整示例:https://plnkr.co/edit/5Yyv2cnn3dRKzsj2Lj61?p=preview
对于 paste
测试,我知道我没有使用正确的语法,但一直无法找到正确的方法。有什么建议吗?
element.triggerHandler('paste', 'astring')
对于 keypress
测试,我相信我正确地触发了事件,但它似乎没有更新元素的值(使用 element.val()
检索)
在此问题上停留了一段时间,如有任何帮助,我们将不胜感激。谢谢!
让我们首先简要分析当用户按下并释放带有焦点的 1
键时可能发生的情况(真正取决于浏览器实现)输入:
- 事件
keydown
已触发 - 事件
keypress
已触发 - 输入值更改为
1
并触发事件input
- 事件
keyup
已触发
JS 没有办法真正模拟用户按下一个键。您可以模拟的是用户这样做时(通常)发生的事情,例如上面的步骤。
triggerHandler
函数为特定元素上的指定事件类型执行与 jQuery 绑定的所有处理程序。
所以使用 triggerHandler
和 keypress
不会模拟用户按下一个键,它只会触发事件,就像上面的第 2 步一样。该值不会更改,因为那是在另一步中发生的。
现在,有人会认为在 limitKeypressLength
指令的测试中,您可以自己简单地模拟上面步骤 3 的第一部分(只需手动设置值):
for (var i = 0; i < 10; i++) {
element.triggerHandler({type: 'keypress', keyCode: 49});
element.val(element.val() + '1');
}
expect(element.val()).toBe('1111111111');
element.triggerHandler('keypress', {which: 49});
element.val(element.val() + '1');
expect(element.val()).toBe('1111111111');
但这不会起作用,因为即使在您的指令中捕获了第十一个按键事件,下面的代码仍会执行并更新值。
limitKeypressLength
指令的基本功能是监听按键事件并调用 event.preventDefault
或不基于。这就是你要测试的。
例如:
// Set value to something longer than allowed
element.val('123456789123456789');
// Create the event
var e = jQuery.Event('keypress', {
keyCode: 49
});
// Create a spy
spyOn(e, 'preventDefault');
// preventDefault should not have been called yet
expect(e.preventDefault).not.toHaveBeenCalled();
// Trigger the event
element.triggerHandler(e);
// Assert that preventDefault has been called
expect(e.preventDefault).toHaveBeenCalled();
演示: https://plnkr.co/edit/ktmcBGSuTdMnvqVRlkeQ?p=preview
现在您可以轻松测试何时将元素值设置为 equal/below 允许值。
limitPasteLength
指令基本上也是如此,因为它的目的也是根据条件调用 preventDefault
,只是需要做一些额外的模拟。