Lección 44: Throw (Lanzar Errores)
🧠 Concepto
Section titled “🧠 Concepto”La instrucción throw permite lanzar errores personalizados en tu código. Puedes lanzar cualquier valor, pero por convención se usan objetos Error.
Sintaxis
Section titled “Sintaxis”throw new Error('Algo salió mal');Tipos de error nativos
Section titled “Tipos de error nativos”throw new Error('Error genérico');throw new TypeError('Se esperaba un número');throw new ReferenceError('Variable no definida');throw new SyntaxError('Sintaxis inválida');throw new RangeError('Valor fuera de rango');Crear errores personalizados
Section titled “Crear errores personalizados”class ValidacionError extends Error { constructor(mensaje, campo) { super(mensaje); this.name = 'ValidacionError'; this.campo = campo; }}
try { throw new ValidacionError('El email no es válido', 'email');} catch (error) { console.log(error.name); // "ValidacionError" console.log(error.message); // "El email no es válido" console.log(error.campo); // "email"}💻 Ejemplo
Section titled “💻 Ejemplo”// Validación con throwfunction dividir(a, b) { if (typeof a !== 'number' || typeof b !== 'number') { throw new TypeError('Ambos argumentos deben ser números'); } if (b === 0) { throw new Error('No se puede dividir por cero'); } return a / b;}
// Uso con try/catchtry { console.log(dividir(10, 2)); // 5 console.log(dividir(10, 0)); // Lanza error} catch (error) { if (error instanceof TypeError) { console.error('Error de tipo:', error.message); } else { console.error('Error:', error.message); }}
// Validación de rangosfunction configurarEdad(edad) { if (edad < 0) { throw new RangeError('La edad no puede ser negativa'); } if (edad > 150) { throw new RangeError(`Edad ${edad} excede el límite realista`); } if (!Number.isInteger(edad)) { throw new TypeError('La edad debe ser un número entero'); } return `Edad configurada: ${edad}`;}
try { console.log(configurarEdad(-5));} catch (error) { console.error(`${error.name}: ${error.message}`);}⚠️ Nota
Section titled “⚠️ Nota”Puedes lanzar cualquier tipo de valor, pero NO lo hagas. Lanzar strings, números u objetos genéricos dificulta el manejo de errores:
// ❌ Malthrow 'Error';throw 404;throw { codigo: 500 };
// ✅ Bienthrow new Error('Algo salió mal');throw new TypeError('Tipo incorrecto');La decisión de cuándo lanzar errores vs manejarlos localmente:
- Lanza errores cuando la función no puede continuar y el responsable es el llamante
- Maneja errores cuando puedes recuperarte localmente (valor por defecto, reintentar, etc.)
Buenas prácticas con throw:
- Usa tipos de error específicos (
TypeError,RangeError, etc.) - Crea clases de error personalizadas para tu dominio
- Siempre proporciona mensajes de error descriptivos
- Documenta qué errores lanza tu función (JSDoc)
/** * Valida un email * @param {string} email - Email a validar * @throws {TypeError} Si email no es string * @throws {Error} Si el formato del email es inválido */function validarEmail(email) { if (typeof email !== 'string') { throw new TypeError('Email debe ser string'); } if (!email.includes('@')) { throw new Error('Email debe contener @'); } return true;}📝 Ejercicio
Section titled “📝 Ejercicio”Crea una función transferirBancaria que reciba monto y saldo. Debe lanzar:
TypeErrorsi algún argumento no es númeroRangeErrorsi el monto es negativo o ceroErrorsi el monto supera el saldo
function transferirBancaria(monto, saldo) { // Tu código aquí}
try { transferirBancaria(100, 50); // Error: Saldo insuficiente} catch (error) { console.log(`${error.name}: ${error.message}`);}