Descubriendo la magia de las Guard Clauses
Altaskur
Posted on February 5, 2024
No me di cuenta de cómo el desarrollo Backend había cambiado mi forma de programar hasta el Jueves 1 de Febrero de 2024.
El momento de la revelación
No fue sino durante una conversación con mi profesor que me di cuenta de que no estaba utilizando la clásica estructura de if-else. Este episodio me desconcertó por completo e instigó una investigación sobre el tema. Nunca me había cuestionado el uso de esta estructura de manera consciente; simplemente la aplicaba de forma automática al verla en los ejemplos.
¿Qué estaba usando?
Descubrí que en una estructura básica de código, colocaba las negaciones al principio y cancelaba el flujo de la función con un return. A continuación, te muestro cómo lo estaba utilizando en una función para registrar a un usuario:
const singInUser = async (req, res) => {
try {
const { email, password } = req.body;
const user = await Users.findOne({ email });
if (!user) return res.status(404).json({ error: 'Usuario no encontrado' });
const isMatch = await user.comparePassword(password);
if (!isMatch) return res.status(401).json({ error: 'Contraseña incorrecta' });
const token = generateToken(user.email, user.name);
return res.status(200).json({ token });
} catch (error) {
console.log(error);
return res.status(500).json({ error: 'Ocurrió un error durante la solicitud' });
}
};
Transformar esto en un conjunto de if-else anidados crearía un laberinto de condiciones difícil de mantener. Al inicio de mi investigación no encontraba nada al respecto; sólo encontraba formas de devolver varios elementos dentro de una función, lo que se aleja completamente del objetivo.
Necesitaba un Rescate
No fue hasta que pude hablar sobre el tema con @programacon_es que me sugirió que buscara por las "Guard Clauses", y aquí comienza mi aventura.
¿Qué són las Guard clauses?
Las Guard Clauses, también conocidas como "early returns" o "return early", son estructuras de control de flujo en programación que se utilizan para mejorar la legibilidad y simplicidad del código al evitar anidaciones excesivas de condicionales. En concepto, estas estructuras se utilizan para evitar el uso de anidaciones excesivas y mejorar la simplicidad y legibilidad del código.
Pongamos un ejemplo teórico
Podemos escribir las cláusulas de error y negativas al principio, no solo mejorando la legibilidad sino también interrumpiendo el resto del código, lo que contribuye a una mejor optimización del mismo.
function validarContrasena(contrasena) {
if (!contrasena) {
return "La contraseña no puede estar vacía.";
}
if (contrasena.length < 8) {
return "La contraseña debe tener al menos 8 caracteres.";
}
if (!/\d/.test(contrasena)) {
return "La contraseña debe contener al menos un número.";
}
return "La contraseña es válida. ¡Bien hecho!";
}
Veamos una alternativa con if-else.
function validarContrasena(contrasena) {
if (!contrasena) {
return "La contraseña no puede estar vacía.";
} else {
if (contrasena.length < 8) {
return "La contraseña debe tener al menos 8 caracteres.";
} else {
if (!/\d/.test(contrasena)) {
return "La contraseña debe contener al menos un número.";
} else {
return "La contraseña es válida. ¡Bien hecho!";
}
}
}
}
Aunque observamos un cambio evidente, no siempre es lo más indicado. Como en todo en programación, el abuso de estas cláusulas puede ser contraproducente y generar fácilmente el efecto contrario, generando un código sucio. Veamos también un ejemplo.
function calculateScore(player) {
if (!player) {
console.error("Jugador no especificado");
return null;
} else {
if (!player.score) {
console.error("Puntuación del jugador no encontrada");
return null;
} else {
if (player.score < 0) {
console.error("Puntuación del jugador negativa");
return null;
} else {
return player.score * 100;
}
}
}
}
¿Entonces en que casos podemos usarlo?
Es importante darle un uso moderado, en casos simples y directos teniendo en cuenta siempre el uso de otras estructuras, recuerda el uso de los comentarios en caso de ser necesario.
¿Has experimentado con Guard Clauses en tus proyectos? ¡Comparte tu experiencia en los comentarios!
Referencias
- https://refactoring.guru/replace-nested-conditional-with-guard-clauses
- https://dev.to/homolibere/guard-clauses-in-c-30d0
- https://tech.jotform.com/making-code-more-robust-with-guard-clauses-tips-and-tricks-d8d3d1940bce
- https://www.codementor.io/@clintwinter/use-guard-clauses-for-cleaner-code-1rrsczgwxp
- https://www.linkedin.com/pulse/guard-clauses-vs-statements-j%C3%A1n-hor%C5%88%C3%A1k
- https://medium.com/@basuraratnayake/clean-code-guard-clauses-796225c83c3e
- https://refactoring.com/catalog/replaceNestedConditionalWithGuardClauses.html
Posted on February 5, 2024
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.