Cypress.io テストでページがアイドル状態になるのを確実に待つにはどうすればいいですか? 質問する

Cypress.io テストでページがアイドル状態になるのを確実に待つにはどうすればいいですか? 質問する

cypress.io を使用して Angular Web ページをテストする場合、ページが完全に読み込まれてアイドル状態になったことを検出する最良かつ最も信頼性の高い方法は何ですか。onload イベントだけではありません。すべての XHR リクエスト、Angular ダイジェスト サイクルの完了、すべてのアニメーションの完了を含むすべてのレンダリングの完了を含める必要があります。

その理由は、この時点ではページに要素が含まれていないことをテストしたいのですが、上記のすべてが完了するまでそれをテストできないからです。

ベストアンサー1

記録のために、これについて私たちがやったこと(AngularJS用waitforpageidle) は、次のように使用できる新しいコマンドを追加することでした。

cy.waitforpageidle();

タイプスクリプトは次のとおりです。

Cypress.Commands.add(
    "waitforpageidle",
    () => {
        console.warn("Waiting for page idle state");

        const pageIdleDetector = new PageIdleDetector();

        pageIdleDetector.WaitForPageToBeIdle();
    }
);

PageIdleDetector は次のとおりです。

export class PageIdleDetector
{   
    defaultOptions: Object = { timeout: 60000 };

    public WaitForPageToBeIdle(): void
    {
        this.WaitForPageToLoad();
        this.WaitForAngularRequestsToComplete();
        this.WaitForAngularDigestCycleToComplete();
        this.WaitForAnimationsToStop();
    }

    public WaitForPageToLoad(options: Object = this.defaultOptions): void
    {
        cy.document(options).should((myDocument: any) =>
        {
            expect(myDocument.readyState, "WaitForPageToLoad").to.be.oneOf(["interactive", "complete"]);
        });
    }

    public WaitForAngularRequestsToComplete(options: Object = this.defaultOptions): void
    {
        cy.window(options).should((myWindow: any) =>
        {
            if (!!myWindow.angular)
            {
                expect(this.NumberOfPendingAngularRequests(myWindow), "WaitForAngularRequestsToComplete").to.have.length(0);
            }
        });
    }

    public WaitForAngularDigestCycleToComplete(options: Object = this.defaultOptions): void
    {
        cy.window(options).should((myWindow: any) =>
        {
            if (!!myWindow.angular)
            {
                expect(this.AngularRootScopePhase(myWindow), "WaitForAngularDigestCycleToComplete").to.be.null;
            }
        });
    }

    public WaitForAnimationsToStop(options: Object = this.defaultOptions): void
    {
        cy.get(":animated", options).should("not.exist");
    }

    private getInjector(myWindow: any)
    {
        return myWindow.angular.element(myWindow.document.body).injector();
    }

    private NumberOfPendingAngularRequests(myWindow: any)
    {
        return this.getInjector(myWindow).get('$http').pendingRequests;
    }

    private AngularRootScopePhase(myWindow: any)
    {
        return this.getInjector(myWindow).get("$rootScope").$$phase;
    }
}

おすすめ記事