angular - Protractor 一直在等待完成的 HTTP 请求

标签 angular typescript protractor

我有一个 RESTful API,现在我正在开发一个使用数据服务调用 API 的 angular2 应用程序。然后我想使用 Protractor 实现端到端测试。我想从非常低的级别开始,所以我进行了测试以检查单击链接时我的组件是否存在。测试看起来像这样:

describe('my-webclient', () => {
    it('app should load', () => {
        browser.get('/');
        expect(element(by.css('my-app')).isPresent()).toBe(true);
    });

    it('app should have a top navigation', () => {
        expect(element(by.css('my-nav-top')).isPresent()).toBe(true);
    });

    it('app should have a side navigation', () => {
        expect(element(by.css('my-nav-side')).isPresent()).toBe(true);
    });

    it('app should have a content', () => {
        expect(element(by.css('my-content')).isPresent()).toBe(true);
    });

    it('app should load the overview for route "/"', () => {
        expect(element(by.css('my-overview')).isPresent()).toBe(true);
    });
});

问题是,概览组件使用某些数据服务在 ngOnInit 函数中发出 HTTP 请求。 Protractor 将永远阻塞,尽管 HTTP 请求早已完成。

当我监控测试时,我可以看到应用程序的加载方式,包括从我的 API 获取的所有数据。然后什么也没有发生, Protractor 最终会崩溃,说超时了。

准确的错误信息是:

Failed: Timed out waiting for Protractor to synchronize with the page after 11 seconds. Please see https://github.com/angular/protractor/blob/master/docs/faq.md                                                                                                                                                            
While waiting for element with locator - Locator: By(css selector, my-app)

在 google 上搜索帮助时,我遇到了几个提示,即 Protractor 将等待 angular 完成所有操作。嗯,这正是我想要的。当我在 chrome 的开发者工具 (F12) 中监控网络选项卡时,应用程序加载后不久什么也没有出现。因此,不再有待处理的请求或 Protractor 要等待的任何东西。仍然如此,我只是不知道为什么。

那么,这是我的问题:在处理发出 HTTP 请求的数据服务时,我是否必须考虑任何特殊事项?或者:我能做些什么来调试为什么 Protractor 仍在等待超时。

顺便说一句,它绝对是数据服务。如果我注释掉 OverviewComponent::ngOnInit 中的所有内容,那么测试将顺利通过,并且符合我的预期。

最佳答案

(简短回答 - 任何长时间运行的任务(超时、间隔、Promises 或 Observables)如果处理不当,都会阻止测试。Http 会自行清理,因此这可能不是您的问题。 )

Http 很可能不是您的问题。

Angular 2 使用区域来检测它的稳定/不稳定状态,而 Protractor 使用特定的可注入(inject)类 - Testability Class - 确定应用程序状态。页面中所有现有 Angular2 应用程序的可测试性都暴露给窗口对象,这就是 Protractor 密切关注 Angular 2 的方式。

Angular 使用区域来维护变更检测。在用户区,我们可以通过 NgZone 控制代码发生的位置(在 Angular 内或 Angular 外),这对两件事很有用 - 测试和性能。在 Angular 区域中运行的任何任务(除非我们另有说明,否则会发生这种情况)将触发更改检测,并且我们等待的任何异步任务都会将可测试性标记为不稳定。

这意味着许多因素可能会干扰您应用的稳定性:

  • 在幕后运行超时的管道(可能在您的特定情况下,如讨论的 here )
  • 监听连续异步任务的组件或服务:
    • 监听 Route.params observable
    • 设置重复超时或间隔
    • ...

要解决此问题,您需要使用 NgZone 在 Angular 之外运行您的任务:

this.ngZone.runOutsideAngular(() => {
  this._sub = Observable.timer(2000)
    .subscribe(() => this.ngZone.run(() => {this.content = "Loaded!"}));
})

查看工作示例 in this plunk , 和 this talk by Julie Ralph了解更多详情 - 她是 Protractor 背后的大脑。

关于angular - Protractor 一直在等待完成的 HTTP 请求,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39184073/

相关文章:

reactjs - 从父级调用功能组件的子级方法

angular - Angular 编译器中的错误需要 TypeScript >=3.1.1 和 <3.2.0,但找到了 3.2.1

javascript - 如何使用 Protractor 验证下拉框中的年份?

angular - e2e如何在 Angular Protractor 中测试登录成功案例

javascript - 在 Angular 2 应用程序中返回 Observable,但仍然收到错误 : "Property ' subscribe' does not exist on type 'void'

node.js - 如何使用 Angular2 将图像保存在本地文件夹中?

angular - Angular 7 的简单 ModalService 打不开 : No component factory found for

javascript - 具有依赖类型的 Typescript 联合

javascript - Protractor :如何在 ui-grid 中滚动几次

angular - ng-serve 失败,yarn 作为包管理器