Custom Errors en Solidity: Guía Completa


En Solidity, los custom errors son una característica que se añadió en la versión 0.8.4 que permite a los desarrolladores definir y lanzar errores personalizados dentro de sus contratos inteligentes. Esta funcionalidad mejora la eficiencia del uso de gas y proporciona mensajes de error más claros y específicos.

En este artículo, te explicaremos qué son, cómo funcionan, y cómo puedes utilizarlos para optimizar tus contratos inteligentes en Solidity.

¿Qué son los Custom Errors?

Los custom errors en Solidity son definiciones de errores personalizados que puedes crear y utilizar en lugar de las tradicionales funciones require, assert, y revert.

A diferencia de estos métodos, los custom errors permiten proporcionar información más específica cuando algo sale mal en tu contrato, lo que puede ayudar a los usuarios y desarrolladores a entender mejor la causa del error.

📰

A partir de Solidity v0.8.26, la función require también soporta custom errors, permitiendo revertir con un error personalizado en lugar de un string.

Ventajas de usar Custom Errors

Algunas de las principales ventajas de usar custom errors son:

  1. Eficiencia en el uso de gas: Los custom errors son más eficientes en términos de gas en comparación con los mensajes de error estándar. Esto se debe a que solo se almacenan las variables necesarias en lugar de una cadena de texto completa.
  2. Mensajes de error claros y detallados: Puedes proporcionar más contexto en los errores, lo que facilita la depuración y el manejo de errores.
  3. Organización del código: Los custom errors permiten un manejo de errores más organizado y estructurado dentro de los contratos inteligentes.

Cómo definir y usar Custom Errors

Para definir un custom error en Solidity, utilizamos la palabra clave error, seguida por el nombre del error y, opcionalmente, los parámetros que deseas incluir en el mensaje de error.

error FondosInsuficientes(uint256 saldoDisponible, uint256 cantidadRequerida );

error ZeroAddress()

A continuación, te mostramos un ejemplo de cómo definir y utilizar un custom error en un contrato inteligente.

pragma solidity ^0.8.18;

contract EjemploCustomError {
 // Definición del custom error
 error FondosInsuficientes(
  uint256 saldoDisponible, 
  uint256 cantidadRequerida
 );
 
 function retirarFondos(uint256 cantidad) public {
  uint256 saldo = obtenerSaldo();
 
  // Lanza el custom error si el saldo es insuficiente
  if (cantidad > saldo) {
   revert FondosInsuficientes(saldo,cantidad);
  }
 
  // Resto del código...
 }
 
 function obtenerSaldo() private view returns (uint256) {
  // Retorna un saldo ficticio
  return 100;
 }
}

En este ejemplo, el custom error FondosInsuficientes se lanza cuando un usuario intenta retirar más fondos de los que tiene disponibles. Este error incluye dos parámetros: el saldo disponible y la cantidad requerida, lo que proporciona información detallada sobre la causa del fallo.

Consideraciones y Buenas Prácticas

Al implementar custom errors en tus contratos, es importante tener en cuenta lo siguiente:

  1. Usa custom errors en lugar de mensajes de error string: Aprovecha la eficiencia de los custom errors para reducir los costos de gas, especialmente en contratos que se ejecutan con frecuencia.
  2. Definición clara de errores: Define errores que sean claros y específicos para los casos que deseas manejar. Esto facilitará la depuración y el mantenimiento del contrato.
  3. No se propagan automáticamente: Es importante tener en cuenta que los custom errors no se propagan automáticamente a través de llamadas de contrato anidadas. Esto significa que si un contrato A llama a un contrato B y este último lanza un custom error, el contrato A solo recibirá una señal de error genérica, a menos que se implemente lógica específica para decodificar y manejar ese error. Por ejemplo:
pragma solidity ^0.8.18;

error ErrorPersonalizado();

contract B {
 function lanzarError() external pure {
  revert ErrorPersonalizado();
 }
}

contract A {
 B contratoB;
 
 constructor(address _direccionB) {
  contratoB = B(_direccionB);
 }

 function llamarContratoB() external {
  try contratoB.lanzarError() {
   // Código si no hay error. Todo ha ido correctamente
  } catch (bytes memory) {
   // Aqui me llega un error genérico. Solo sé que ha habido un fallo
  }
 }
}

En este ejemplo, cuando el contrato A llama a la función lanzarError en el contrato B, el error ErrorPersonalizado no se decodifica automáticamente en el contrato A.

Esto significa que, aunque el código entra en el bloque catch a causa de que ha habido un fallo, la transacción no fallará por sí sola a menos que el error se maneje explícitamente dentro del contrato A.

Conclusión

Los custom errors son una poderosa herramienta en Solidity que no solo mejora la claridad y la especificidad de los mensajes de error, sino que también optimiza el uso de gas en tus contratos inteligentes. Al implementar esta funcionalidad, podrás construir contratos más eficientes y fáciles de mantener. Aprovecha esta característica para mejorar la calidad de tu código en Solidity.