Testując funkcję, która jest obietnica i setTimeout, dlaczego jest ona wyłączona na czas?

0

Pytanie

Próbuję przetestować funkcję, która ma setTimeout wewnątrz jest obietnica. Jednak on nadal odliczać czas.

To jest funkcja:

export const sleep = async (duration: number): Promise<void> => {
  await new Promise<void>((resolve) => {
    setTimeout(resolve, duration);
  });

  if (process.env.NODE_ENV === "test") {
    console.log("sleep end");
  }
};

I to jest mój test:

import { sleep } from "../../helpers/utils";

console.log = jest.fn();
jest.useFakeTimers();

test("calls sleep with correct argument and calls console.log", async () => {
  const NODE_ENV = "test";
  const SLEEP_DURATION = "100";

  process.env = { ...process.env, NODE_ENV, SLEEP_DURATION };

  const timeoutSpy = jest.spyOn(global, "setTimeout");

  await sleep(+SLEEP_DURATION);

  jest.runAllTimers();

  expect(sleep).toHaveBeenCalledWith(+SLEEP_DURATION);
  expect(timeoutSpy).toHaveBeenCalledWith(+SLEEP_DURATION);
  expect(console.log).toHaveBeenCalledWith("sleep end");
});

Problem w tym, że gdy próbuję uruchomić to, test kończy się niepowodzeniem i wyświetlany następujący komunikat:

thrown: "Exceeded timeout of 5000 ms for a test.
    Use jest.setTimeout(newTimeout) to increase the timeout value, if this is a long-running test."

Próbowałem jest.setTimeout(10000) co po prostu prowadzi do błędu Exceeded timeout of 10000ms ...

Jakieś pomysły co do tego, dlaczego tak się dzieje? Lub jak to naprawić?

Dziękuję!

javascript jestjs settimeout timeout
2021-11-24 01:41:50
1

Najlepsza odpowiedź

1

Oto rozwiązanie, które zbliża się do tego, do czego dążycie. Ważne jest, aby pamiętać, że nie można await rozdzielczość obietnice z użyciem fałszywych timerów, inaczej nigdy nie zostanie rozwiązana. Zamiast tego możesz zadzwonić, aby przypisać wartość zwracana sleep funkcja zmiennej, a następnie uruchom zegary, a następnie poczekaj na zmiennej.

Ja również zmienił swój expect operator limit czasu, tak jak przyjmuje dwa argumenty. W końcu usunąłem twoje oczekiwanie, że sleep jest wywoływana z podaniem czasu trwania, bo dosłownie robi się to w teście, więc chyba nie warto robić to stwierdzenie.

console.log = jest.fn();
jest.useFakeTimers();

test("calls sleep with correct argument and calls console.log", async () => {
  const NODE_ENV = "test";
  const SLEEP_DURATION = "100";

  process.env = { ...process.env, NODE_ENV, SLEEP_DURATION };

  const timeoutSpy = jest.spyOn(global, "setTimeout");

  const sleepFn = sleep(+SLEEP_DURATION);

  jest.runAllTimers();

  // Now that we ran timers we can await the promise resolving 
  await sleepFn;

  // timeout takes two arguments
  expect(timeoutSpy).toHaveBeenCalledWith(
    expect.any(Function),
    +SLEEP_DURATION
  );
  expect(console.log).toHaveBeenCalledWith("sleep end");
});
2021-11-24 02:03:50

Dziękuję za pouczające odpowiedź, pierwszy raz używam te humoru liczniki, więc mi na pewno trzeba się trochę uczyć!
ffx292

W innych językach

Ta strona jest w innych językach

Русский
..................................................................................................................
Italiano
..................................................................................................................
Română
..................................................................................................................
한국어
..................................................................................................................
हिन्दी
..................................................................................................................
Français
..................................................................................................................
Türk
..................................................................................................................
Česk
..................................................................................................................
Português
..................................................................................................................
ไทย
..................................................................................................................
中文
..................................................................................................................
Español
..................................................................................................................
Slovenský
..................................................................................................................