Estoy trabajando con un código en el que necesito probar el tipo de una excepción lanzada por una función (¿es TypeError, ReferenceError, etc.?).
Mi marco de prueba actual es AVA y puedo probarlo como un método de segundo argumento t.throws , como aquí:
it('should throw Error with message \'UNKNOWN ERROR\' when no params were passed', (t) => { const error = t.throws(() => { throwError(); }, TypeError); t.is(error.message, 'UNKNOWN ERROR'); });Empecé a reescribir mis pruebas en Jest y no pude encontrar cómo hacerlo fácilmente. ¿Es posible?
En Jest, debe pasar una función a expect(function).toThrow(<blank or type of error>) .
Ejemplo:
test("Test description", () => { const t = () => { throw new TypeError(); }; expect(t).toThrow(TypeError); });O si también desea verificar el mensaje de error:
test("Test description", () => { const t = () => { throw new TypeError("UNKNOWN ERROR"); }; expect(t).toThrow(TypeError); expect(t).toThrow("UNKNOWN ERROR"); }); Si necesita probar una función existente si arroja un conjunto de argumentos, debe envolverla dentro de una función anónima en expect() .
Ejemplo:
test("Test description", () => { expect(() => {http.get(yourUrl, yourCallbackFn)}).toThrow(TypeError); });Es un poco raro, pero funciona y en mi humilde opinión es bien legible:
it('should throw Error with message \'UNKNOWN ERROR\' when no parameters were passed', () => { try { throwError(); // Fail test if above expression doesn't throw anything. expect(true).toBe(false); } catch (e) { expect(e.message).toBe("UNKNOWN ERROR"); } }); El bloque Catch detecta su excepción, y luego puede probar su Error generado. Extraño expect(true).toBe(false); es necesario para reprobar la prueba si no se arroja el Error esperado. De lo contrario, nunca se podrá acceder a esta línea (se debe generar un Error antes que ellos).
@Kenny Body sugirió una mejor solución que mejora la calidad del código si usa expect.assertions() :
it('should throw Error with message \'UNKNOWN ERROR\' when no parameters were passed', () => { expect.assertions(1); try { throwError(); } catch (e) { expect(e.message).toBe("UNKNOWN ERROR"); } });Vea la respuesta original con más explicaciones: Cómo probar el tipo de una excepción lanzada en Jest
Para usar este enfoque y no activar la regla no-conditional-expect (si está usando eslint-plugin-jest ), la documentación de esta regla sugiere usar el envoltorio de error:
class NoErrorThrownError extends Error {} const getError = async <TError>(call: () => unknown): Promise<TError> => { try { await call(); throw new NoErrorThrownError(); } catch (error: unknown) { return error as TError; } }; describe('when the http request fails', () => { it('includes the status code in the error', async () => { const error = await getError(async () => makeRequest(url)); // check that the returned error wasn't that no error was thrown expect(error).not.toBeInstanceOf(NoErrorThrownError); expect(error).toHaveProperty('statusCode', 404); }); });Yo uso una versión un poco más concisa:
expect(() => { // Code block that should throw error }).toThrow(TypeError) // Or .toThrow('expectedErrorMessage')