Lição: 047: Assert, Require e Revert em Solidity
Em Solidity, os contratos inteligentes frequentemente estão sujeitos a várias condições que precisam ser atendidas para que uma transação seja bem-sucedida. Para garantir que essas condições sejam respeitadas, Solidity fornece três funções principais: assert
, require
e revert
. Cada uma dessas funções tem um propósito distinto na manipulação de erros e na garantia da integridade dos seus contratos inteligentes.
1. Require
A função require
é utilizada para validar entradas e condições antes da execução de mais código. Se a condição especificada em require
avaliar como falsa, a função irá reverter e todas as mudanças feitas no estado serão desfeitas. Isso é especialmente útil para verificar entradas de usuários e garantir que as invariantes do contrato sejam mantidas.
Sintaxe:
require(condição, "Mensagem de erro se a condição for falsa");
Exemplo:
pragma solidity ^0.8.0;
contract ArmazenamentoSimples {
uint256 private dadoArmazenado;
function definir(uint256 x) public {
require(x > 0, "A entrada deve ser maior que 0.");
dadoArmazenado = x;
}
function obter() public view returns (uint256) {
return dadoArmazenado;
}
}
Neste exemplo, a função definir
inclui uma declaração require
para verificar se a entrada x
é maior que 0. Se um usuário tentar definir um valor não positivo, a transação será revertida com a mensagem "A entrada deve ser maior que 0."
2. Assert
A função assert
é utilizada para verificar condições que nunca deveriam ser falsas. Isso é normalmente empregado para verificações de erro internas e invariantes que se espera que sejam mantidas enquanto o contrato é executado. Se uma assert
falhar, isso indica um problema sério na lógica do contrato.
Sintaxe:
assert(condição);
Exemplo:
pragma solidity ^0.8.0;
contract Contador {
uint256 private contagem;
function incrementar() public {
contagem += 1;
assert(contagem > 0); // Deve sempre ser verdadeiro
}
function obterContagem() public view returns (uint256) {
return contagem;
}
}
Neste exemplo, a função incrementar
contém uma declaração assert
para garantir que a variável contagem
seja sempre maior que 0 após a incremento. Se contagem
sofresse um underflow (o que não pode acontecer no Solidity 0.8.0 e posteriores devido a verificações internas), a assert
falharia, indicando uma falha crítica na lógica.
3. Revert
A função revert
é outra forma de reverter o estado do contrato, semelhante a require
, mas geralmente é utilizada em operações mais complexas onde pode ser necessário reverter múltiplos estados ou onde se deseja retornar um erro personalizado.
Sintaxe:
revert("Mensagem de erro");
Exemplo:
pragma solidity ^0.8.0;
contract ControleAcesso {
address private proprietario;
constructor() {
proprietario = msg.sender;
}
modifier apenasProprietario() {
if (msg.sender != proprietario) {
revert("Apenas o proprietário pode chamar esta função.");
}
_;
}
function funcaoRestrita() public apenasProprietario {
// Lógica da função
}
}
Neste contrato ControleAcesso
, definimos um modificador apenasProprietario
que verifica se o chamador é o proprietário do contrato. Se o chamador não for o proprietário, ele chama revert
para interromper a execução e fornecer uma mensagem de erro.
Resumo
-
require
é utilizado para validar entradas e condições antes da execução das funções. Se a condição for falsa, reverte e fornece uma mensagem de erro. -
assert
é utilizado para verificar condições que nunca deveriam ser falsas. É usado principalmente para verificações de consistência interna e invariantes. -
revert
é utilizado para lógica mais complexa onde a função precisa reverter a execução e retornar uma mensagem de erro personalizada.
Compreender e utilizar efetivamente esses três mecanismos ajudará você a criar contratos inteligentes mais robustos e confiáveis em Solidity. Use require
para entradas de usuários, assert
para verificações de lógica interna e revert
para verificações de condições complexas.