Pool personalizado
WARNING
Esta es una API avanzada. Si solo estás ejecutando pruebas, probablemente no necesites esto. Su uso está principalmente destinado a autores de bibliotecas.
Vitest ejecuta las pruebas en pools (grupos de procesos). Por defecto, existen varios pools:
threads
: para ejecutar pruebas usandonode:worker_threads
(el aislamiento se logra mediante un nuevo contexto de worker).forks
: para ejecutar pruebas usandonode:child_process
(el aislamiento se logra mediante un nuevo procesochild_process.fork
).vmThreads
: para ejecutar pruebas usandonode:worker_threads
(pero el aislamiento se proporciona con el módulovm
en lugar de un nuevo contexto de worker).browser
: para ejecutar pruebas usando proveedores de navegadores.typescript
: para ejecutar la comprobación de tipos en las pruebas.
Puedes proporcionar tu propio pool especificando la ruta a un archivo:
import { defineConfig } from 'vitest/config';
// ---cut---
export default defineConfig({
test: {
// ejecutará cada archivo por defecto con un pool personalizado
pool: './my-custom-pool.ts',
// puedes proporcionar opciones mediante el objeto `poolOptions`
poolOptions: {
myCustomPool: {
customProperty: true,
},
},
// también puedes especificar el pool para un subconjunto de archivos
poolMatchGlobs: [['**/*.custom.test.ts', './my-custom-pool.ts']],
},
});
API
El archivo especificado mediante la opción pool
debe exportar una función (puede ser asíncrona) que acepte la interfaz Vitest
como su primer parámetro. Esta función debe devolver un objeto que coincida con la interfaz ProcessPool
:
import { ProcessPool, WorkspaceProject } from 'vitest/node';
export interface ProcessPool {
name: string;
runTests: (
files: [project: WorkspaceProject, testFile: string][],
invalidates?: string[]
) => Promise<void>;
close?: () => Promise<void>;
}
La función se llama solo una vez (a menos que se haya actualizado la configuración del servidor). Es recomendable inicializar todo lo necesario para las pruebas dentro de esta función y reutilizarlo en cada llamada a runTests
.
Vitest llama a runTest
cuando se programan nuevas pruebas para ejecutarse. No se llamará si files
está vacío. El primer argumento es un array de tuplas: el primer elemento es una referencia a un proyecto del espacio de trabajo y el segundo es una ruta absoluta a un archivo de prueba. Los archivos se ordenan mediante sequencer
antes de que se llame a runTests
. Es posible (aunque poco probable) tener el mismo archivo dos veces, pero siempre tendrá un proyecto diferente. Esto se implementa a través de la configuración vitest.workspace.ts
.
Vitest esperará a que runTests
termine su ejecución antes de finalizar una ejecución completa (es decir, emitirá onFinished
únicamente cuando la promesa de runTests
se resuelva).
Si utilizas un pool personalizado, deberás encargarte de procesar los archivos de prueba y sus resultados. Puedes consultar vitest.state
para obtener información relevante (las funciones más importantes son collectFiles
y updateTasks
). Vitest utiliza la función startTests
del paquete @vitest/runner
para realizar esta tarea.
Para la comunicación entre diferentes procesos, puedes crear un objeto con métodos utilizando createMethodsRPC
de vitest/node
y emplear el método de comunicación que prefieras. Por ejemplo, para usar WebSockets con birpc
podrías escribir algo como esto:
import { createBirpc } from 'birpc';
import { parse, stringify } from 'flatted';
import { WorkspaceProject, createMethodsRPC } from 'vitest/node';
function createRpc(project: WorkspaceProject, wss: WebSocketServer) {
return createBirpc(createMethodsRPC(project), {
post: msg => wss.send(msg),
on: fn => wss.on('message', fn),
serialize: stringify,
deserialize: parse,
});
}
Para asegurar que cada prueba se recopile, deberías llamar a ctx.state.collectFiles
y reportarlo a los reporteros de Vitest:
async function runTests(project: WorkspaceProject, tests: string[]) {
// ... ejecutando pruebas, poner en "files" y "tasks"
const methods = createMethodsRPC(project);
await methods.onCollected(files);
// la mayoría de los reporteros dependen de que los resultados se actualicen en "onTaskUpdate"
await methods.onTaskUpdate(tasks);
}
Puedes ver un ejemplo sencillo en pool/custom-pool.ts.