mneumann
mneumann

Reputation: 786

Using cy.tick() together with rxjs auditTime

We have an e2e test for a feature that uses ngrx state management. The feature collects user inputs over 60 seconds via the auditTime() operator and posts them to an API endpoint.

Since I don't want to wait for 60 seconds each run, I was thinking of using the cy.tick(58000) function to skip time forward. However, it appears that time is not skipped at all.

it('should send a http post request after 60 seconds', () => {
        cy.intercept('POST', '**/my-page').as('my-post'); // intercept the post
        cy.clock(); // instantiate clock object
        cy.visit('/home'); // visit page

        // some inputs here
        cy.tick(58000); // skip 58 seconds

        // this wait command times out
        cy.wait('@my-post', { timeout: 15000 }).then((interception: any) => {
            const statusCode = interception.response.statusCode;
            expect(statusCode).equal(200);
       });
});

The observable itself that uses the auditTime operator is created within an ngrx effect:

postObservable$ = createEffect(() =>
    this.store.select(FromData.selectData).pipe(
        auditTime(60_000), // important part
        filter((data) => data.length > 0),
        map((result) => [
            ...result.map((dataElement) =>
                toDataDTO({
                    dataId: dataElement.postId,
                    createdAt: dataElement.createdAt,
                })
            ),
        ]),
    ...
});

Each time, the test times out after 15 seconds. It works if I reduce the auditTime() period to one second or similar.

How can I make sure Cypress ticks work for rxjs operators such as auditTime()?

Upvotes: 1

Views: 442

Answers (1)

TesterDick
TesterDick

Reputation: 10570

One way is to make a mock of the time parameter.

const timeParam = window.Cypress ? 300 : 60_000;

postObservable$ = createEffect(() =>
    this.store.select(FromData.selectData).pipe(

        auditTime(timeParam), 

        filter((data) => data.length > 0),
        map((result) => [
            ...result.map((dataElement) =>
                toDataDTO({
                    dataId: dataElement.postId,
                    createdAt: dataElement.createdAt,
                })
            ),
        ]),
    ...
})

Maybe that breaks the logic of the app (e.g race condition with another Rx feed).


Since clock() controls Date, setTimeout() and setInterval(), I had a quick look to see if any of these underly the timing of auditTime(). There is TimestampProvider that uses Date.now() but can't tell how to mock that effectively.

Alternatively, TestScheduler may provide a way to accelerate the interval, but I can't see how to use it in an e2e test.

Upvotes: 2

Related Questions