问题描述
我正在尝试编写一个单元测试,以证明用户的每次按键操作都会触发一个(ngModelChange)
事件,我将其设置为调用名为onValueChange()
的函数。此函数更新组件的内部值
我可以证明,在测试环境中,在实际键盘上的实际按键上,此事件在每个按键上触发,并更新了组件的formGroup值,这是预期的结果,但是我想为我的单元测试自动化此按键。我也不能使用jQuery。
我尝试过手动设置nativeElement.value
,并且尝试了多种模拟按键的方法,但是没有一种方法可以像物理按键一样触发ngModelChange
事件按。
这是我的规格初稿,它不会触发ngModelChange
,但是输入文本框中的任何物理按键都可以:
fit('should call onValueChange after new input is entered',fakeAsync(() => {
let textInputEl: DebugElement = fixture.debugElement.query(
By.css('input.form-control')
);
let HTMLInput = textInputEl.nativeElement;
HTMLInput.value = 'world';
tick();
fixture.detectChanges();
expect(component.formGroup.value.textInputState).toEqual('world');
}));
这是我的另一本规范草案,试图模拟物理按键(因此ngModelChange
)无效:
fit('should call onValueChange after new input is entered',fakeAsync(() => {
let textInputEl: DebugElement = fixture.debugElement.query(
By.css('input.form-control')
);
let HTMLInput = textInputEl.nativeElement;
HTMLInput.value = 'world';
HTMLInput.select();
document.addEventListener('keydown',function(e){
console.log('keydown detected');
})
const event = new KeyboardEvent("keypress",{
"key": "Enter"
});
HTMLInput.dispatchEvent(event);
HTMLInput.dispatchEvent(new KeyboardEvent('keypress',{'key':'a'}));
HTMLInput.dispatchEvent(new KeyboardEvent('keydown',{'key':'b'}));
tick();
fixture.detectChanges();
HTMLInput.dispatchEvent(new KeyboardEvent('keyup',{'key':'b'}));
tick();
fixture.detectChanges();
expect(component.formGroup.value.textInputState).toEqual('world');
}));
组件内部的两个相关功能:
onValueChange(newValue: T) {
console.log('onValueChange() just called!');
this.value = newValue;
this.valueChange.emit(this.value);
this.emitSerializableStateChange();
}
onClick(value){
console.log('button clicked');
console.log('current this.value inside textBox component: ',this.value);
}
运行此测试时,文本框中的实际文本实际上是设置为“世界”,但组件中的formGroup实际值仍然是默认的“ hello”。我假设我跳过了一些触发ngModelChange
的事件。
我希望按键事件能够触发该事件,但是我编写的所有按键事件均未真正通过。我知道它们根本不会触发,因为不仅文本框内的文本保持默认值,而且我编写的侦听器根本不会触发。但是在物理按键之后,ngModelChange和我的事件侦听器都会执行。
Here's a screenshot of the results of the test immediately after running
其余部分是代码的其他部分。我认为它们无关紧要,但您可能比我更了解Angular哈哈
这是HTML Angular绑定的重要部分:
<div class="col-sm-9" [formGroup]="group"
><input
class="form-control"
[class.q-ngc-form-validation-border]="
control.errors && control.touched
"
[formControlName]="name"
[type]="type"
[id]="name"
[placeholder]="options.placeholder || ''"
(ngModelChange)="onValueChange($event)"
/>
<q-ngc-validation-text
*ngIf="control.touched"
[controlName]="name"
[label]="options.label"
[formControlErrors]="control.errors"
[formGroupErrors]="group.errors"
[asyncValidations]="asyncValidations"
></q-ngc-validation-text>
</div>
<button (click)="onClick(this.value)">Print current value</button>
这里是我设置组件的DynamicFormSpec:
const testTextInputForm: DynamicFormSpec = {
formName: 'testTextInputForm',formControlSpecs: [
{
name: 'textInputState',type: DynamicFormControlType.TEXT,valuePath: 'textInputState',options: {
label: 'Text Input Test',disabled: false
}
}
]
};
最后,这是我配置测试台的地方:
interface TestTextInputviewmodel {
textInputState: string;
}
fdescribe('textInputComponent',() => {
let component: TestDynamicFormComponent<TestTextInputviewmodel>;
let fixture: ComponentFixture<TestDynamicFormComponent<TestTextInputviewmodel>>;
beforeEach(async(() => {
Testbed.configureTestingModule({
imports: [TestCoreFormsModule]
}).compileComponents();
fixture = Testbed.createComponent<
TestDynamicFormComponent<TestTextInputviewmodel>
>(TestDynamicFormComponent);
component = fixture.componentInstance;
component.testDynamicFormSpec = cloneDeep(testTextInputForm);
component.viewmodel = { textInputState: 'hello' };
fixture.detectChanges();
}));
任何有关如何实现模拟按键或在替换值后以编程方式触发(ngModelChange)
事件的其他方法的提示,将不胜感激!
非常感谢您!
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)