Skip to content
Vitest 2
Main Navigation ÚtmutatóAPIKonfigurációBöngésző módHaladó
2.1.9
1.6.1
0.34.6

magyar

English
简体中文
繁體中文
Español
Français
Русский
Português – Brasil
Deutsch
日本語
한국어
Italiano
Polski
Türkçe
čeština

magyar

English
简体中文
繁體中文
Español
Français
Русский
Português – Brasil
Deutsch
日本語
한국어
Italiano
Polski
Türkçe
čeština

Megjelenés

Sidebar Navigation

Teszt API Dokumentáció

Mock függvények

Vi

expect

expectTypeOf

assert

assertType

Ezen az oldalon

Vi ​

A Vitest a vi segédprogramján keresztül biztosít segédfunkciókat. Globálisan is elérheted (ha a globals konfiguráció engedélyezve van), vagy közvetlenül importálhatod a vitest-ből:

js
import { vi } from 'vitest';

Modulok Mockolása ​

Ez a szakasz az API-t írja le, amelyet a modulok mockolásához használhatsz. Fontos megjegyezni, hogy a Vitest nem támogatja a require() használatával importált modulok mockolását.

vi.mock ​

  • Típus: (path: string, factory?: MockOptions | ((importOriginal: () => unknown) => unknown)) => void
  • Típus: <T>(path: Promise<T>, factory?: MockOptions | ((importOriginal: () => T) => T | Promise<T>)) => void

Az összes importált modult a megadott path-ról egy másik modullal helyettesíti. Használhatod a konfigurált Vite aliasokat az útvonalon belül. A vi.mock hívás felemelésre kerül (hoisted), így nem számít, hogy hol hívod meg. Mindig az összes import előtt fog végrehajtódni. Ha hivatkoznod kell néhány változóra a hatókörén kívül, definiálhatod őket a vi.hoisted belsejében, és hivatkozhatsz rájuk a vi.mock belsejében.

WARNING

A vi.mock csak az import kulcsszóval importált moduloknál működik. Nem működik a require-rel.

A vi.mock hoistingolásához a Vitest statikusan elemzi a fájljaidat. Ez azt jelenti, hogy a vi, amelyet nem közvetlenül a vitest csomagból importáltál (például egy segédprogram fájlból), nem használható. Használd a vi.mock-ot a vitest-ből importált vi-vel, vagy engedélyezd a globals konfigurációs opciót.

A Vitest nem fogja mockolni azokat a modulokat, amelyeket egy setup fájlban importáltak, mert azok a tesztfájl futásakor már gyorsítótárazva vannak. Hívhatod a vi.resetModules() metódust a vi.hoisted belsejében, hogy törölje az összes modul gyorsítótárat a tesztfájl futtatása előtt.

Ha a factory függvény definiálva van, az összes importálás annak eredményét adja vissza. A Vitest csak egyszer hívja meg a factory-t, és gyorsítótárazza az eredményeket az összes későbbi importáláshoz, amíg a vi.unmock vagy a vi.doUnmock hívás meg nem történik.

A jest-tel ellentétben a factory lehet aszinkron. Használhatod a vi.importActual metódust vagy egy segédprogramot, amelynek a factory-t adják át első argumentumként, és így hozzáférhetsz az eredeti modulhoz.

A Vitest 2.1 óta a factory függvény helyett egy objektumot is megadhatsz spy tulajdonsággal. Ha a spy értéke true, akkor a Vitest a szokásos módon automockolja a modult, de nem írja felül az exportok implementációját. Ez akkor hasznos, ha csak azt szeretnéd ellenőrizni, hogy az exportált metódust egy másik metódus helyesen hívta-e meg.

ts
import { calculator } from './src/calculator.ts';

vi.mock('./src/calculator.ts', { spy: true });

// meghívja az eredeti implementációt,
// de lehetővé teszi a viselkedés későbbi ellenőrzését
const result = calculator(1, 2);

expect(result).toBe(3);
expect(calculator).toHaveBeenCalledWith(1, 2);
expect(calculator).toHaveReturned(3);

A Vitest támogatja a modul promise-t is a vi.mock és vi.doMock metódusokban string helyett a jobb IDE támogatás érdekében. Amikor a fájl áthelyezésre kerül, az útvonal frissül, és az importOriginal automatikusan örökli a típust. Ennek a szignatúrának a használata azt is kikényszeríti, hogy a factory visszatérési típusa kompatibilis legyen az eredeti modullal (az exportok opcionálisak maradnak).

ts
// @filename: ./path/to/module.js
export declare function total(...numbers: number[]): number;
// @filename: test.js
import { vi } from 'vitest';
// ---cut---
vi.mock(import('./path/to/module.js'), async importOriginal => {
  const mod = await importOriginal(); // a típus következtetett
  //    ^?
  return {
    ...mod,
    // néhány export felülírása
    total: vi.fn(),
  };
});

A háttérben a Vitest továbbra is stringgel dolgozik, nem modul objektummal.

Ha TypeScript-et használsz a tsconfig.json-ban konfigurált paths aliasokkal, a fordító nem fogja tudni helyesen feloldani az import típusokat. Ahhoz, hogy ez működjön, győződj meg róla, hogy az összes aliased importot lecseréled a megfelelő relatív útvonalakra. Pl. használd az import('./path/to/module.js') helyett az import('@/module')-t.

WARNING

A vi.mock hoistingolásra kerül (más szóval, áthelyezésre) a fájl tetejére. Ez azt jelenti, hogy bárhol is írod (legyen az beforeEach vagy test belsejében), valójában azelőtt fog meghívódni.

Ez azt is jelenti, hogy nem használhatsz semmilyen változót a factory belsejében, amelyek a factory-n kívül vannak definiálva.

Ha változókat kell használnod a factory belsejében, próbáld meg a vi.doMock metódust használni. Ugyanúgy működik, de nincs felemelve. Vigyázz, csak a későbbi importokat mockolja.

Hivatkozhatsz a vi.hoisted metódussal definiált változókra is, ha az a vi.mock előtt lett deklarálva:

ts
import { namedExport } from './path/to/module.js';

const mocks = vi.hoisted(() => {
  return {
    namedExport: vi.fn(),
  };
});

vi.mock('./path/to/module.js', () => {
  return {
    namedExport: mocks.namedExport,
  };
});

vi.mocked(namedExport).mockReturnValue(100);

expect(namedExport()).toBe(100);
expect(namedExport).toBe(mocks.namedExport);

WARNING

Ha egy modult mockolsz alapértelmezett exporttal, akkor a visszaadott factory függvény objektumon belül meg kell adnod egy default kulcsot. Ez egy ES modul-specifikus sajátosság; ezért a jest dokumentáció eltérhet, mivel a jest CommonJS modulokat használ. Például,

ts
vi.mock('./path/to/module.js', () => {
  return {
    default: { myDefaultKey: vi.fn() },
    namedExport: vi.fn(),
    // stb...
  };
});

Ha van egy __mocks__ mappa a mockolt fájl mellett, és a factory nincs megadva, a Vitest megpróbál egy azonos nevű fájlt találni a __mocks__ almappában, és azt használja tényleges modulként. Ha egy függőséget mockolsz, a Vitest megpróbál egy __mocks__ mappát találni a projekt gyökerében (alapértelmezett a process.cwd()). Megadhatod a Vitestnek, hol találhatók a függőségek a deps.moduleDirectories konfigurációs opcióval.

Például, van ez a fájlstruktúra:

- __mocks__
  - axios.js
- src
  __mocks__
    - increment.js
  - increment.js
- tests
  - increment.test.js

Ha a vi.mock metódust hívod egy tesztfájlban factory vagy opciók nélkül, akkor a __mocks__ mappában talál egy fájlt, amelyet modulként használhat:

ts
// increment.test.js
import { vi } from 'vitest';

// az axios egy alapértelmezett export a `__mocks__/axios.js`-ből
import axios from 'axios';

// az increment egy elnevezett export a `src/__mocks__/increment.js`-ből
import { increment } from '../increment.js';

vi.mock('axios');
vi.mock('../increment.js');

axios.get(`/apples/${increment(1)}`);

WARNING

Vigyázz, ha nem hívod a vi.mock metódust, a modulok nem lesznek automatikusan mockolva. A Jest automocking viselkedésének replikálásához hívhatod a vi.mock metódust minden szükséges modulhoz a setupFiles belsejében.

Ha nincs __mocks__ mappa vagy megadott factory, a Vitest importálja az eredeti modult, és automockolja az összes exportját. Az alkalmazott szabályokért lásd az algoritmust.

vi.doMock ​

  • Típus: (path: string, factory?: MockOptions | ((importOriginal: () => unknown) => unknown)) => void
  • Típus: <T>(path: Promise<T>, factory?: MockOptions | ((importOriginal: () => T) => T | Promise<T>)) => void

Ugyanaz, mint a vi.mock, de nincs felemelve a fájl tetejére, így hivatkozhatsz változókra a globális fájl hatókörében. A modul következő dinamikus importálása mockolva lesz.

WARNING

Ez nem fogja mockolni azokat a modulokat, amelyeket ez előtt hívtak meg. Ne felejtsd el, hogy az összes statikus import az ESM-ben mindig hoistingolásra kerül, így ennek a statikus import elé helyezése nem fogja kikényszeríteni, hogy az import előtt hívják meg:

ts
vi.doMock('./increment.js'); // ez az import utasítás _után_ lesz meghívva

import { increment } from './increment.js';
ts
// ./increment.js
export function increment(number) {
  return number + 1;
}
ts
import { beforeEach, test } from 'vitest';
import { increment } from './increment.js';

// a modul nincs mockolva, mert a vi.doMock még nincs meghívva
increment(1) === 2;

let mockedIncrement = 100;

beforeEach(() => {
  // hozzáférhetsz a változókhoz a factory belsejében
  vi.doMock('./increment.js', () => ({ increment: () => ++mockedIncrement }));
});

test('a következő modul importálása a mockoltat importálja', async () => {
  // az eredeti import NEM VOLT MOCKOLVA, mert a vi.doMock az importok UTÁN értékelődik ki
  expect(increment(1)).toBe(2);
  const { increment: mockedIncrement } = await import('./increment.js');
  // az új dinamikus import a mockolt modult adja vissza
  expect(mockedIncrement(1)).toBe(101);
  expect(mockedIncrement(1)).toBe(102);
  expect(mockedIncrement(1)).toBe(103);
});

vi.mocked ​

  • Típus: <T>(obj: T, deep?: boolean) => MaybeMockedDeep<T>
  • Típus: <T>(obj: T, options?: { partial?: boolean; deep?: boolean }) => MaybePartiallyMockedDeep<T>

Típus segéd TypeScript-hez. Csak visszaadja az átadott objektumot.

Ha a partial értéke true, akkor Partial<T>-t vár visszatérési értékként. Alapértelmezés szerint ez csak azt fogja elhitetni a TypeScript-tel, hogy az első szintű értékek mockolva vannak. Átadhatod a { deep: true }-t második argumentumként, hogy elmondd a TypeScript-nek, hogy az egész objektum mockolva van, ha tényleg az.

ts
// example.ts
export function add(x: number, y: number): number {
  return x + y;
}

export function fetchSomething(): Promise<Response> {
  return fetch('https://vitest.dev/');
}
ts
// example.test.ts
import * as example from './example';

vi.mock('./example');

test('1 + 1 egyenlő 10', async () => {
  vi.mocked(example.add).mockReturnValue(10);
  expect(example.add(1, 1)).toBe(10);
});

test('mock visszatérési érték csak részben helyes tipizálással', async () => {
  vi.mocked(example.fetchSomething).mockResolvedValue(new Response('hello'));
  vi.mocked(example.fetchSomething, { partial: true }).mockResolvedValue({
    ok: false,
  });
  // vi.mocked(example.someFn).mockResolvedValue({ ok: false }) // ez típus hiba
});

vi.importActual ​

  • Típus: <T>(path: string) => Promise<T>

Importálja a modult, megkerülve az összes ellenőrzést, hogy mockolni kell-e. Hasznos lehet, ha részben szeretnéd mockolni a modult.

ts
vi.mock('./example.js', async () => {
  const axios = await vi.importActual('./example.js');

  return { ...axios, get: vi.fn() };
});

vi.importMock ​

  • Típus: <T>(path: string) => Promise<MaybeMockedDeep<T>>

Importál egy modult az összes tulajdonságával (beleértve a beágyazott tulajdonságokat is) mockolva. Ugyanazokat a szabályokat követi, mint a vi.mock. Az alkalmazott szabályokért lásd az algoritmust.

vi.unmock ​

  • Típus: (path: string | Promise<Module>) => void

Eltávolítja a modult a mockolt regiszterből. Minden importálási hívás az eredeti modult adja vissza, még akkor is, ha korábban mockolva volt. Ez a hívás felemelésre kerül a fájl tetejére, így csak azokat a modulokat fogja unmockolni, amelyek például a setupFiles-ban voltak definiálva.

vi.doUnmock ​

  • Típus: (path: string | Promise<Module>) => void

Ugyanaz, mint a vi.unmock, de nincs felemelve a fájl tetejére. A modul következő importálása az eredeti modult fogja importálni a mock helyett. Ez nem fogja unmockolni a korábban importált modulokat.

ts
// ./increment.js
export function increment(number) {
  return number + 1;
}
ts
import { increment } from './increment.js';

// az increment már mockolva van, mert a vi.mock felemelésre került
increment(1) === 100;

// ez felemelésre került, és a factory az 1. sorban lévő import előtt hívódik meg
vi.mock('./increment.js', () => ({ increment: () => 100 }));

// minden hívás mockolva van, és az `increment` mindig 100-at ad vissza
increment(1) === 100;
increment(30) === 100;

// ez nincs felemelve, így a másik import unmockolt modult ad vissza
vi.doUnmock('./increment.js');

// ez MÉG MINDIG 100-at ad vissza, mert a `vi.doUnmock` nem értékeli újra a modult
increment(1) === 100;
increment(30) === 100;

// a következő import unmockolt, most az `increment` az eredeti függvény, amely count + 1-et ad vissza
const { increment: unmockedIncrement } = await import('./increment.js');

unmockedIncrement(1) === 2;
unmockedIncrement(30) === 31;

vi.resetModules ​

  • Típus: () => Vitest

Visszaállítja a modul regisztert az összes modul gyorsítótárának törlésével. Ez lehetővé teszi a modulok újraértékelését az újraimportáláskor. A felső szintű importok nem értékelhetők újra. Hasznos lehet a modulok izolálására, ahol a helyi állapot ütközik a tesztek között.

ts
import { vi } from 'vitest';

import { data } from './data.js'; // Nem lesz újraértékelve minden teszt előtt

beforeEach(() => {
  vi.resetModules();
});

test('állapot megváltoztatása', async () => {
  const mod = await import('./some/path.js'); // Újraértékelve lesz
  mod.changeLocalState('új érték');
  expect(mod.getLocalState()).toBe('új érték');
});

test('a modulnak régi állapota van', async () => {
  const mod = await import('./some/path.js'); // Újraértékelve lesz
  expect(mod.getLocalState()).toBe('régi érték');
});

WARNING

Nem állítja vissza a mock regisztert. A mock regiszter törléséhez használd a vi.unmock vagy a vi.doUnmock metódust.

vi.dynamicImportSettled ​

Várja meg az összes import betöltését. Hasznos, ha van egy szinkron hívásod, amely elindít egy modul importálását, amelyet egyébként nem tudsz megvárni.

ts
import { expect, test, vi } from 'vitest';

// nem tudja követni az importot, mert a Promise nem kerül visszaadásra
function renderComponent() {
  import('./component.js').then(({ render }) => {
    render();
  });
}

test('a műveletek feloldódtak', async () => {
  renderComponent();
  await vi.dynamicImportSettled();
  expect(document.querySelector('.component')).not.toBeNull();
});

TIP

Ha egy dinamikus import során egy másik dinamikus import indul el, ez a metódus megvárja, amíg mindegyik feloldódik.

Ez a metódus megvárja a következő setTimeout tick-et is az import feloldása után, így az összes szinkron műveletnek be kell fejeződnie, mire feloldódik.

Függvények és Objektumok Mockolása ​

Ez a szakasz leírja, hogyan dolgozhatsz a metódus mockokkal és hogyan cserélheted le a környezeti és globális változókat.

vi.fn ​

  • Típus: (fn?: Function) => Mock

Spy-t hoz létre egy függvényen, bár anélkül is inicializálható. Minden alkalommal, amikor egy függvényt meghívnak, tárolja a hívási argumentumait, visszatérési értékeit és példányait. Ezenkívül manipulálhatod a viselkedését a metódusokkal. Ha nincs megadva függvény, a mock undefined-t ad vissza, amikor meghívják.

ts
const getApples = vi.fn(() => 0);

getApples();

expect(getApples).toHaveBeenCalled();
expect(getApples).toHaveReturnedWith(0);

getApples.mockReturnValueOnce(5);

const res = getApples();
expect(res).toBe(5);
expect(getApples).toHaveNthReturnedWith(2, 5);

vi.isMockFunction ​

  • Típus: (fn: Function) => boolean

Ellenőrzi, hogy egy adott paraméter mock függvény-e. Ha TypeScript-et használsz, akkor a típusát is finomítja.

vi.clearAllMocks ​

Meghívja a .mockClear() metódust az összes spy-on. Ez törli a mock előzményeket, de nem állítja vissza az implementációját az alapértelmezettre.

vi.resetAllMocks ​

Meghívja a .mockReset() metódust az összes spy-on. Ez törli a mock előzményeket, és visszaállítja az implementációját egy üres függvényre (amely undefined-t ad vissza).

vi.restoreAllMocks ​

Meghívja a .mockRestore() metódust az összes spy-on. Ez törli a mock előzményeket, és visszaállítja az implementációját az eredetire.

vi.spyOn ​

  • Típus: <T, K extends keyof T>(object: T, method: K, accessType?: 'get' | 'set') => MockInstance

Spy-t hoz létre egy objektum metódusán vagy getter/setterén, hasonlóan a vi.fn() metódushoz. Egy mock függvényt ad vissza.

ts
let apples = 0;
const cart = {
  getApples: () => 42,
};

const spy = vi.spyOn(cart, 'getApples').mockImplementation(() => apples);
apples = 1;

expect(cart.getApples()).toBe(1);

expect(spy).toHaveBeenCalled();
expect(spy).toHaveReturnedWith(1);

TIP

Hívhatod a vi.restoreAllMocks metódust az afterEach belsejében (vagy engedélyezheted a test.restoreMocks opciót), hogy visszaállítsd az összes metódust az eredeti implementációjukra. Ez visszaállítja az objektum eredeti leíróját, így nem tudod megváltoztatni a metódus implementációját:

ts
const cart = {
  getApples: () => 42,
};

const spy = vi.spyOn(cart, 'getApples').mockReturnValue(10);

console.log(cart.getApples()); // 10
vi.restoreAllMocks();
console.log(cart.getApples()); // 42
spy.mockReturnValue(10);
console.log(cart.getApples()); // még mindig 42!

TIP

Nem lehetséges spy-t létrehozni az exportált metódusokon böngésző módban. Ehelyett kémkedhetsz minden exportált metóduson a vi.mock("./file-path.js", { spy: true }) hívásával. Ez minden exportot mockol, de az implementációját érintetlenül hagyja, lehetővé téve, hogy ellenőrizd, hogy a metódust helyesen hívták-e meg.

ts
import { calculator } from './src/calculator.ts';

vi.mock('./src/calculator.ts', { spy: true });

calculator(1, 2);

expect(calculator).toHaveBeenCalledWith(1, 2);
expect(calculator).toHaveReturned(3);

És bár lehetséges kémkedni az exportokon jsdom vagy más Node.js környezetekben, ez a jövőben megváltozhat.

vi.stubEnv ​

  • Típus: <T extends string>(name: T, value: T extends "PROD" | "DEV" | "SSR" ? boolean : string | undefined) => Vitest

Megváltoztatja a környezeti változó értékét a process.env és import.meta.env esetében. Az értékét visszaállíthatod a vi.unstubAllEnvs hívásával.

ts
import { vi } from 'vitest';

// `process.env.NODE_ENV` és `import.meta.env.NODE_ENV`
// "development" a "vi.stubEnv" hívása előtt

vi.stubEnv('NODE_ENV', 'production');

process.env.NODE_ENV === 'production';
import.meta.env.NODE_ENV === 'production';

vi.stubEnv('NODE_ENV', undefined);

process.env.NODE_ENV === undefined;
import.meta.env.NODE_ENV === undefined;

// nem változtatja meg a többi env-t
import.meta.env.MODE === 'development';

TIP

Az értéket egyszerűen hozzárendeléssel is megváltoztathatod, de nem fogod tudni használni a vi.unstubAllEnvs metódust az előző érték visszaállításához:

ts
import.meta.env.MODE = 'test';

vi.unstubAllEnvs ​

  • Típus: () => Vitest

Visszaállítja az összes import.meta.env és process.env értéket, amelyeket a vi.stubEnv metódus megváltoztatott. Amikor először hívják meg, a Vitest megjegyzi az eredeti értéket, és tárolja azt, amíg az unstubAllEnvs újra meg nem hívódik.

ts
import { vi } from 'vitest';

// `process.env.NODE_ENV` és `import.meta.env.NODE_ENV`
// "development" a stubEnv hívása előtt

vi.stubEnv('NODE_ENV', 'production');

process.env.NODE_ENV === 'production';
import.meta.env.NODE_ENV === 'production';

vi.stubEnv('NODE_ENV', 'staging');

process.env.NODE_ENV === 'staging';
import.meta.env.NODE_ENV === 'staging';

vi.unstubAllEnvs();

// visszaállítja az értéket, amely az első "stubEnv" hívás előtt volt tárolva
process.env.NODE_ENV === 'development';
import.meta.env.NODE_ENV === 'development';

vi.stubGlobal ​

  • Típus: (name: string | number | symbol, value: unknown) => Vitest

Globális változó értékét változtatja meg. Az eredeti értékét visszaállíthatod a vi.unstubAllGlobals hívásával.

ts
import { vi } from 'vitest';

// az `innerWidth` "0" a stubGlobal hívása előtt

vi.stubGlobal('innerWidth', 100);

innerWidth === 100;
globalThis.innerWidth === 100;
// ha jsdom-ot vagy happy-dom-ot használsz
window.innerWidth === 100;

TIP

Az értéket egyszerűen hozzárendeléssel is megváltoztathatod a globalThis vagy window objektumhoz (ha jsdom vagy happy-dom környezetet használsz), de nem fogod tudni használni a vi.unstubAllGlobals metódust az eredeti érték visszaállításához:

ts
globalThis.innerWidth = 100;
// ha jsdom-ot vagy happy-dom-ot használsz
window.innerWidth = 100;

vi.unstubAllGlobals ​

  • Típus: () => Vitest

Visszaállítja az összes globális értéket a globalThis/global (és window/top/self/parent, ha jsdom vagy happy-dom környezetet használsz) esetében, amelyeket a vi.stubGlobal metódus megváltoztatott. Amikor először hívják meg, a Vitest megjegyzi az eredeti értéket, és tárolja azt, amíg az unstubAllGlobals újra meg nem hívódik.

ts
import { vi } from 'vitest';

const Mock = vi.fn();

// az IntersectionObserver "undefined" a "stubGlobal" hívása előtt

vi.stubGlobal('IntersectionObserver', Mock);

IntersectionObserver === Mock;
global.IntersectionObserver === Mock;
globalThis.IntersectionObserver === Mock;
// ha jsdom-ot vagy happy-dom-ot használsz
window.IntersectionObserver === Mock;

vi.unstubAllGlobals();

globalThis.IntersectionObserver === undefined;
'IntersectionObserver' in globalThis === false;
// ReferenceError-t dob, mert nincs definiálva
IntersectionObserver === undefined;

Hamis időzítők ​

Ez a szakasz leírja, hogyan dolgozhatsz a hamis időzítőkkel.

vi.advanceTimersByTime ​

  • Típus: (ms: number) => Vitest

Ez a metódus minden elindított időzítőt meghív, amíg a megadott milliszekundum el nem telik, vagy a sor kiürül - attól függően, hogy melyik következik be előbb.

ts
let i = 0;
setInterval(() => console.log(++i), 50);

vi.advanceTimersByTime(150);

// log: 1
// log: 2
// log: 3

vi.advanceTimersByTimeAsync ​

  • Típus: (ms: number) => Promise<Vitest>

Ez a metódus minden elindított időzítőt meghív, amíg a megadott milliszekundum el nem telik, vagy a sor kiürül - attól függően, hogy melyik következik be előbb. Ez magában foglalja az aszinkron módon beállított időzítőket is.

ts
let i = 0;
setInterval(() => Promise.resolve().then(() => console.log(++i)), 50);

await vi.advanceTimersByTimeAsync(150);

// log: 1
// log: 2
// log: 3

vi.advanceTimersToNextTimer ​

  • Típus: () => Vitest

Meghívja a következő elérhető időzítőt. Hasznos az ellenőrzések elvégzéséhez minden időzítő hívás között. Láncolhatod a hívásokat, hogy saját magad kezeld az időzítőket.

ts
let i = 0;
setInterval(() => console.log(++i), 50);

vi.advanceTimersToNextTimer() // log: 1
  .advanceTimersToNextTimer() // log: 2
  .advanceTimersToNextTimer(); // log: 3

vi.advanceTimersToNextTimerAsync ​

  • Típus: () => Promise<Vitest>

Meghívja a következő elérhető időzítőt, és megvárja, amíg feloldódik, ha aszinkron módon lett beállítva. Hasznos az ellenőrzések elvégzéséhez minden időzítő hívás között.

ts
let i = 0;
setInterval(() => Promise.resolve().then(() => console.log(++i)), 50);

await vi.advanceTimersToNextTimerAsync(); // log: 1
expect(console.log).toHaveBeenCalledWith(1);

await vi.advanceTimersToNextTimerAsync(); // log: 2
await vi.advanceTimersToNextTimerAsync(); // log: 3

vi.advanceTimersToNextFrame 2.1.0+ ​

  • Típus: () => Vitest

Hasonló a vi.advanceTimersByTime metódushoz, de annyi milliszekundummal lépteti előre az időzítőket, amennyi a requestAnimationFrame segítségével jelenleg ütemezett visszahívások végrehajtásához szükséges.

ts
let frameRendered = false;

requestAnimationFrame(() => {
  frameRendered = true;
});

vi.advanceTimersToNextFrame();

expect(frameRendered).toBe(true);

vi.getTimerCount ​

  • Típus: () => number

Lekéri a várakozó időzítők számát.

vi.clearAllTimers ​

Eltávolítja az összes futásra ütemezett időzítőt. Ezek az időzítők soha nem fognak futni a jövőben.

vi.getMockedSystemTime ​

  • Típus: () => Date | null

Visszaadja a mockolt aktuális dátumot, amelyet a setSystemTime metódussal állítottak be. Ha a dátum nincs mockolva, a metódus null-t ad vissza.

vi.getRealSystemTime ​

  • Típus: () => number

Amikor a vi.useFakeTimers metódust használod, a Date.now hívások mockolva vannak. Ha valós időt szeretnél milliszekundumban lekérni, meghívhatod ezt a függvényt.

vi.runAllTicks ​

  • Típus: () => Vitest

Meghív minden mikrofeladatot, amelyet a process.nextTick sorba állított. Ez futtatja az összes önmaguk által ütemezett mikrofeladatot is.

vi.runAllTimers ​

  • Típus: () => Vitest

Ez a metódus minden elindított időzítőt meghív, amíg az időzítő sor kiürül. Ez azt jelenti, hogy minden időzítő, amelyet a runAllTimers hívás során hívtak meg, elindul. Ha végtelen intervallumod van, 10 000 próbálkozás után hibát dob (konfigurálható a fakeTimers.loopLimit opcióval).

ts
let i = 0;
setTimeout(() => console.log(++i));
const interval = setInterval(() => {
  console.log(++i);
  if (i === 3) {
    clearInterval(interval);
  }
}, 50);

vi.runAllTimers();

// log: 1
// log: 2
// log: 3

vi.runAllTimersAsync ​

  • Típus: () => Promise<Vitest>

Ez a metódus aszinkron módon meghív minden elindított időzítőt, amíg az időzítő sor kiürül. Ez azt jelenti, hogy minden időzítő, amelyet a runAllTimersAsync hívás során hívtak meg, elindul, még az aszinkron időzítők is. Ha végtelen intervallumod van, 10 000 próbálkozás után hibát dob (konfigurálható a fakeTimers.loopLimit opcióval).

ts
setTimeout(async () => {
  console.log(await Promise.resolve('eredmény'));
}, 100);

await vi.runAllTimersAsync();

// log: eredmény

vi.runOnlyPendingTimers ​

  • Típus: () => Vitest

Ez a metódus minden időzítőt meghív, amelyet a vi.useFakeTimers hívás után indítottak el. Nem fogja elindítani azokat az időzítőket, amelyeket a hívása során indítottak el.

ts
let i = 0;
setInterval(() => console.log(++i), 50);

vi.runOnlyPendingTimers();

// log: 1

vi.runOnlyPendingTimersAsync ​

  • Típus: () => Promise<Vitest>

Ez a metódus aszinkron módon meghív minden időzítőt, amelyet a vi.useFakeTimers hívás után indítottak el, még az aszinkronokat is. Nem fogja elindítani azokat az időzítőket, amelyeket a hívása során indítottak el.

ts
setTimeout(() => {
  console.log(1);
}, 100);
setTimeout(() => {
  Promise.resolve().then(() => {
    console.log(2);
    setInterval(() => {
      console.log(3);
    }, 40);
  });
}, 10);

await vi.runOnlyPendingTimersAsync();

// log: 2
// log: 3
// log: 3
// log: 1

vi.setSystemTime ​

  • Típus: (date: string | number | Date) => void

Ha a hamis időzítők engedélyezve vannak, ez a metódus szimulálja, hogy a felhasználó megváltoztatja a rendszerórát (ez hatással lesz a dátummal kapcsolatos API-kra, mint a hrtime, performance.now vagy new Date()) - azonban nem fog elindítani semmilyen időzítőt. Ha a hamis időzítők nincsenek engedélyezve, ez a metódus csak a Date.* hívásokat mockolja.

Hasznos, ha olyan dolgokat kell tesztelned, amelyek az aktuális dátumtól függenek - például a Luxon hívásokat a kódodban.

Ugyanazokat a string és number argumentumokat fogadja el, mint a Date.

ts
const date = new Date(1998, 11, 19);

vi.useFakeTimers();
vi.setSystemTime(date);

expect(Date.now()).toBe(date.valueOf());

vi.useRealTimers();

vi.useFakeTimers ​

  • Típus: (config?: FakeTimerInstallOpts) => Vitest

Az időzítők mockolásának engedélyezéséhez meg kell hívnod ezt a metódust. Ez felülírja az összes további hívást az időzítőkhöz (például setTimeout, setInterval, clearTimeout, clearInterval, setImmediate, clearImmediate, és Date), amíg a vi.useRealTimers() hívás meg nem történik.

A nextTick mockolása nem támogatott, ha a Vitest-et node:child_process belsejében futtatod a --pool=forks használatával. A NodeJS belsőleg használja a process.nextTick-et a node:child_process belsejében, és lefagy, ha mockolva van. A nextTick mockolása támogatott, ha a Vitest-et --pool=threads opcióval futtatod.

Az implementáció belsőleg a @sinonjs/fake-timers alapul.

TIP

A vi.useFakeTimers() nem mockolja automatikusan a process.nextTick-et. De engedélyezheted ezt az opciót a toFake argumentumban: vi.useFakeTimers({ toFake: ['nextTick'] }).

vi.isFakeTimers ​

  • Típus: () => boolean

true-t ad vissza, ha a hamis időzítők engedélyezve vannak.

vi.useRealTimers ​

  • Típus: () => Vitest

Amikor az időzítők lefutottak, meghívhatod ezt a metódust, hogy visszaállítsd a mockolt időzítőket az eredeti implementációjukra. Minden korábban ütemezett időzítő eldobásra kerül.

Egyéb ​

Egy sor hasznos segédprogram, amelyet a Vitest biztosít.

vi.waitFor ​

  • Típus: <T>(callback: WaitForCallback<T>, options?: number | WaitForOptions) => Promise<T>

Megvárja, amíg a visszahívás sikeresen végrehajtódik. Ha a visszahívás hibát dob, vagy elutasított promise-t ad vissza, tovább vár, amíg sikerül, vagy időtúllépés következik be.

Ez nagyon hasznos, ha meg kell várnod valamilyen aszinkron művelet befejezését, például amikor elindítasz egy szervert, és meg kell várnod, amíg elindul.

ts
import { expect, test, vi } from 'vitest';
import { createServer } from './server.js';

test('A szerver sikeresen elindult', async () => {
  const server = createServer();

  await vi.waitFor(
    () => {
      if (!server.isReady) {
        throw new Error('A szerver nem indult el');
      }

      console.log('A szerver elindult');
    },
    {
      timeout: 500, // alapértelmezett 1000
      interval: 20, // alapértelmezett 50
    }
  );
  expect(server.isReady).toBe(true);
});

Aszinkron visszahívásoknál is működik

ts
// @vitest-environment jsdom

import { expect, test, vi } from 'vitest';
import { getDOMElementAsync, populateDOMAsync } from './dom.js';

test('Az elem létezik a DOM-ban', async () => {
  // DOM feltöltésének indítása
  populateDOMAsync();

  const element = await vi.waitFor(
    async () => {
      // próbálja meg lekérni az elemet, amíg létezik
      const element = (await getDOMElementAsync()) as HTMLElement | null;
      expect(element).toBeTruthy();
      expect(element.dataset.initialized).toBeTruthy();
      return element;
    },
    {
      timeout: 500, // alapértelmezett 1000
      interval: 20, // alapértelmezett 50
    }
  );
  expect(element).toBeInstanceOf(HTMLElement);
});

Ha a vi.useFakeTimers metódust használod, a vi.waitFor automatikusan meghívja a vi.advanceTimersByTime(interval) metódust minden ellenőrző visszahívásban.

vi.waitUntil ​

  • Típus: <T>(callback: WaitUntilCallback<T>, options?: number | WaitUntilOptions) => Promise<T>

Ez hasonló a vi.waitFor metódushoz, de ha a visszahívás bármilyen hibát dob, a végrehajtás azonnal megszakad, és hibaüzenet érkezik. Ha a visszahívás hamis értéket ad vissza, a következő ellenőrzés folytatódik, amíg igaz érték nem kerül visszaadásra. Ez akkor hasznos, ha meg kell várnod, hogy valami létezzen, mielőtt megteszed a következő lépést.

Nézd meg az alábbi példát. Használhatjuk a vi.waitUntil metódust, hogy megvárjuk, amíg az elem megjelenik az oldalon, majd tehetünk valamit az elemmel.

ts
import { expect, test, vi } from 'vitest';

test('Az elem helyesen renderelődik', async () => {
  const element = await vi.waitUntil(() => document.querySelector('.element'), {
    timeout: 500, // alapértelmezett 1000
    interval: 20, // alapértelmezett 50
  });

  // tegyél valamit az elemmel
  expect(element.querySelector('.element-child')).toBeTruthy();
});

vi.hoisted ​

  • Típus: <T>(factory: () => T) => T

Az összes statikus import utasítás az ES modulokban hoistingolásra kerül a fájl tetejére, így minden kód, amely az importok előtt van definiálva, valójában az importok kiértékelése után fog végrehajtódni.

Azonban hasznos lehet néhány mellékhatás meghívása, például a dátumok mockolása egy modul importálása előtt.

Ennek a korlátozásnak a megkerüléséhez átírhatod a statikus importokat dinamikus importokra így:

diff
callFunctionWithSideEffect()
- import { value } from './some/module.js'
+ const { value } = await import('./some/module.js')

A vitest futtatásakor ezt automatikusan megteheted a vi.hoisted metódus használatával.

diff
- callFunctionWithSideEffect()
import { value } from './some/module.js'
+ vi.hoisted(() => callFunctionWithSideEffect())

Ez a metódus visszaadja a factory által szolgáltatott értéket. Ezt az értéket használhatod a vi.mock factory-jaidban, ha könnyen hozzáférsz a lokálisan definiált változókhoz:

ts
import { expect, vi } from 'vitest';
import { originalMethod } from './path/to/module.js';

const { mockedMethod } = vi.hoisted(() => {
  return { mockedMethod: vi.fn() };
});

vi.mock('./path/to/module.js', () => {
  return { originalMethod: mockedMethod };
});

mockedMethod.mockReturnValue(100);
expect(originalMethod()).toBe(100);

Megjegyzendő, hogy ez a metódus aszinkron módon is hívható, még akkor is, ha a környezeted nem támogatja a top-level await-et:

ts
const promised = await vi.hoisted(async () => {
  const response = await fetch('https://jsonplaceholder.typicode.com/posts');
  return response.json();
});

vi.setConfig ​

  • Típus: RuntimeConfig

Frissíti a konfigurációt az aktuális tesztfájlhoz. Ez a metódus csak azokat a konfigurációs opciókat támogatja, amelyek hatással lesznek az aktuális tesztfájlra:

ts
vi.setConfig({
  allowOnly: true,
  testTimeout: 10_000,
  hookTimeout: 10_000,
  clearMocks: true,
  restoreMocks: true,
  fakeTimers: {
    now: new Date(2021, 11, 19),
    // támogatja az egész objektumot
  },
  maxConcurrency: 10,
  sequence: {
    hooks: 'stack',
    // csak a "sequence.hooks"-ot támogatja
  },
});

vi.resetConfig ​

  • Típus: RuntimeConfig

Ha a vi.setConfig metódust korábban hívták, ez visszaállítja a konfigurációt az eredeti állapotba.

Pager
Előző oldalMock függvények
Következő oldalexpect

A MIT licenc alapján kiadva.

Copyright (c) 2024 Mithril Contributors

https://v2.vitest.dev/api/vi

A MIT licenc alapján kiadva.

Copyright (c) 2024 Mithril Contributors