0

In my Angular project, I have decided to remove jasmine and karma and use jest and testing-library. I have decided to apply my test policy under the "case of use" concept. It means: My tests are made on the component and I only will mock the infrastructure layer (in this case, the requests of the API --> HttpClient.

For this reason, I have decided to use Testbed to prepare my component and use HttpClientTestingModule for mocking the requests.

Everything goes well except if I try to use the mocks of HttpClientTestingModule, asynchrony of @angular/core/testing (fakeAsync() and tick() ) and testing-library at the same test.

So, I have this tests that work:

function mockGet(url: string, response: object): void {
  const httpMock = TestBed.inject(HttpTestingController)

  const mockRequest = httpMock.expectOne(url)
  mockRequest.flush(response)
}

describe('MY COMPONENT', () => {
  beforeEach(async () => {
    TestBed.configureTestingModule({
      declarations: [],
      imports: [HttpClientTestingModule, MyModule],
    }).compileComponents()

    await TestBed.compileComponents()
  })

  describe('when render component', () => {
    it('call to endpoint to get data', fakeAsync(async () => {
      await render(OrdersComponent, {})
      mockGet('/status', {
        detail: 'not recalculating',
      })
      tick()
      mockGet('/data', [])
    }))
  })

  describe('When is recaltulating', () => {
    it('show recalcualting loader', async () => {
      await render(OrdersComponent, {})
      mockGet('/status', {
        detail: 'recalculating',
      })

      expect(await screen.findByText('Recalculating')).toBeInTheDocument()
    })
  })
})

As you can see, I have one test using a fakeAsync() and tick() and other test with testing-library.

But, if I try to add one test with fakeAsync and tick and testing-library:

[...]
describe('When is not recalculating', () => {
  it('show data', fakeAsync(async () => {
    const { detectChanges } = await render(OrdersComponent, {})
    mockGet('/status', {
      detail: 'not recalculating',
    })
    tick()
    mockGet('/data', 'some_text_from_data')
    
    expect(await screen.findByText('some_text_from_data)).toBeInTheDocument()

    //discardPeriodicTasks()
    //detectChanges()
    //flush()
  }))
})
[...]

This is giving me an error: "1 periodic timer(s) still in the queue."

I have tried to use discardPeriodicTasks() (and flush()), but nothing fix this. Even, I have tried some changes using detectChanges or waitFor from testing-library, but I can't get the test to turn green.

Also, I don't know if this is relevant, but I show it for your information:
Within the hours I've been trying to fix this, I've done many variations, and on more than one occasion I get this error:

 TypeError: Converting circular structure to JSON
        --> starting at object with constructor 'Zone'
        |     property '_zoneDelegate' -> object with constructor '_ZoneDelegate'
        --- property 'zone' closes the circle
        at stringify (<anonymous>)

      at messageParent (node_modules/jest-worker/build/workers/messageParent.js:33:19)

PD: it's my first post on Stackoverflow, I hope I have made myself clear in my explication.
PD': sorry for my level of english xD

David
  • 1
  • 1

0 Answers0