Angular 单元测试 - Mat Dialog 元素始终为 null

时间:2021-07-15 15:37:36

标签: angular angular-material karma-jasmine

我正在尝试修复由于向组件添加对话框而失败的单元测试。

这种情况是,当点击按钮时,会出现一个警告对话框,询问该过程是否应该继续进行,或者用户是否希望不做任何更改就返回。

这是我的组件方法的代码片段:

onDoSomething(): void {
    if (someConfition) {
        doSomething();
    } else {
        const dialogRef = this.dialog.open(DialogComponent);
        dialogRef.componentInstance.dialogText = this.WARNING_TEXT;
        dialogRef.componentInstance.isConfirmDialog = true;
        dialogRef.afterClosed().subscribe(rp => {
            if (rp.confirmed) {
                doA();
            } else {
                doB();
            }
        });
    }
}

这是我的 dialog-component.html:

<div>
<div mat-dialog-content>
    <p>{{ dialogText }}</p>
</div>
<div *ngIf="!isConfirmDialog; else warningDialog" mat-dialog-actions align="center">
    <button mat-button (click)="onNoClick()" cdkFocusInitial>OK</button>
</div>
<ng-template #warningDialog>
    <div mat-dialog-actions align="center">
        <button id="okButton" mat-button (click)="onDoConfirm()" cdkFocusInitial>OK</button>
        <button mat-button (click)="onNoClick()">Abbrechen</button>
    </div>
</ng-template>

和 ts 文件...:

@Component({
selector: 'app-dialog',
templateUrl: './dialog.component.html',
styleUrls: ['./dialog.component.css']

}) 导出类 DialogComponent 实现 OnInit {

public dialogText;

public isConfirmDialog;

constructor(
    protected dialogRef: MatDialogRef<DialogComponent>
) { }

ngOnInit(): void {
}

onNoClick(): void {
    this.dialogRef.close({ confirmed: false });
}

onDoConfirm(): void {
    this.dialogRef.close({ confirmed: true });
}

}

当我运行单元测试时,该对话框在浏览器中可见: enter image description here

但是当我尝试在我的单元格中单击它时,无论我写什么查询都找不到该按钮。

这是我的测试:

fit('test my method', async () => {
    selectANnumber();
    fixture.detectChanges();
    const headerCheckbox = fixture.nativeElement.querySelectorAll('tbody tr:not(.emptyCol) checkbox');
    expect(headerCheckbox).toBeTruthy();
    const checkbox = fixture.nativeElement.querySelectorAll('tbody tr:not(.emptyCol) td checkbox');
    expect(checkbox).toBeTruthy();
    const rowCheckbox = fixture.debugElement.queryAll(By.css('input'))[1].nativeElement as HTMLInputElement;
    expect(rowCheckbox.checked).toBeFalse();
    rowCheckbox.click();
    fixture.detectChanges();
    await fixture.whenStable();
    const myButton = fixture.nativeElement.querySelectorAll('button')[1];
    myButton.click();
    fixture.detectChanges();
    await fixture.whenStable();
    fixture.detectChanges();

    const okButton = fixture.debugElement.query(By.css('#okButton')).nativeElement as HTMLInputElement;
    okButton.click();


    fixture.detectChanges();
    await fixture.whenStable();

    const card = fixture.nativeElement.querySelectorAll('.mat-card');
    expect(card).toBeTruthy();
    expect(card[0].innerText.trim()).toEqual('My job has been successfully done');
});

会不会是对话框内容没有渲染到 DOM 或类似的东西中? 我没有任何线索...

附言当我在浏览器中手动单击按钮时,它就会发生它应该发生的事情。所以这不是功能,而是测试什么不起作用......

有什么建议吗?我真的很感激... 谢谢!


编辑

测试结果:

TypeError: Cannot read property 'click' of null

注意:

enter image description here

enter image description here


解决方案:

在查阅了数百万篇文章后,我找到了这篇对我有帮助的文章:

Bootstrap modal DOM element not available in Angular unit test

我的对话框容器不在fixture.debugElement中,也不在fixture nativeElement中,所以我必须按如下方式引用我的按钮:

const okButton = document.body.querySelector<HTMLInputElement>('button#okButton');

0 个答案:

没有答案