Implementar o tratamento de exceção estruturado

Concluído

Agora que você tem uma compreensão da natureza dos erros e do tratamento de erros básicos no T-SQL, é hora de examinar uma forma mais avançada de tratamento de erros. O tratamento de exceção estruturado foi introduzido no SQL Server 2005.

Aqui, você verá como usá-lo e avaliar seus benefícios e limitações, incluindo o bloco TRY CATCH, o papel das funções de tratamento de erros e entender a diferença entre erros capturáveis e não capturáveis. Por fim, você verá como os erros podem ser gerenciados e revelados quando necessário.

O que é o bloco de programação TRY/CATCH

O tratamento de exceções estruturados é mais eficiente do que o tratamento de erros com base na variável do sistema @@ERROR. Ele permite que você impeça que o código seja repleto de código de tratamento de erros e centralize esse código de tratamento de erros. Centralização do código de tratamento de erros também significa que você pode se concentrar mais na finalidade do código do que no tratamento de erros presente nele.

Bloco TRY e bloco CATCH

Ao usar o tratamento de exceção estruturado, o código que pode gerar um erro é colocado em um bloco TRY. Os blocos TRY são colocados entre as instruções BEGIN TRY e END TRY .

Caso ocorra um erro capturável - a maioria dos erros pode ser capturada - o controle de execução é movido para o bloco CATCH. O bloco CATCH é uma série de instruções T-SQL entre as instruções BEGIN CATCH e END CATCH .

Observação

Embora BEGIN CATCH e END TRY sejam instruções separadas, BEGIN CATCH deve seguir imediatamente o END TRY.

Limitações atuais

Idiomas de alto nível geralmente oferecem um constructo try/catch/finally e geralmente são usados para liberar recursos implicitamente. Não há nenhum bloco FINALLY equivalente no T-SQL.

Entender a diferença entre erros capturáveis e não capturáveis

É importante perceber que, embora os blocos TRY/CATCH permitam capturar uma gama muito maior de erros do que você poderia com @@ERROR, você não pode capturar todos os tipos.

Erros capturáveis ​​vs. erros não capturáveis

Nem todos os erros podem ser capturados pelos blocos TRY/CATCH dentro do mesmo escopo onde o bloco TRY/CATCH existe. Muitas vezes, erros que não podem ser detectados no mesmo escopo podem ser detectados em um escopo adjacente. Por exemplo, talvez você não consiga detectar um erro dentro do procedimento armazenado que contém o bloco TRY/CATCH. No entanto, é provável que você encontre esse erro em um bloco TRY/CATCH no código que chamou o procedimento armazenado onde o erro ocorreu.

Erros comuns não detectáveis

Exemplos comuns de erros não capturáveis são:

  • Erros de compilação, como erros de sintaxe, que impedem a compilação de um lote.
  • Problemas de recompilação no nível de declaração que geralmente estão relacionados à resolução de nomes adiada. Por exemplo, você pode criar um procedimento armazenado que se refere a uma tabela desconhecida. Um erro só é gerado quando o procedimento tenta resolver o nome da tabela para um objectid.

Como relançar erros usando THROW

Se a instrução THROW for usada em um bloco CATCH sem parâmetros, ela irá relançar o erro que causou a inserção do código no bloco CATCH. Você pode usar essa técnica para implementar o log de erros no banco de dados capturando erros e registrando seus detalhes e, em seguida, lançando o erro original para o aplicativo cliente, para que ele possa ser tratado lá.

Aqui está um exemplo de como relançar um erro.

BEGIN TRY
    -- code to be executed
END TRY
BEGIN CATCH
    PRINT ERROR_MESSAGE();
    THROW
END CATCH

Em algumas versões anteriores do SQL Server, não havia nenhum método para gerar um erro do sistema. Embora THROW não possa especificar um erro de sistema a ser gerado, quando THROW é usado sem parâmetros em um bloco CATCH, ele gerará novamente erros de sistema e de usuário.

O que são funções de tratamento de erros

Os blocos CATCH disponibilizam as informações relacionadas a erros durante toda a duração do bloco CATCH. Isso inclui subescopos, como procedimentos armazenados, executados dentro do bloco CATCH.

Funções de tratamento de erros

Lembre-se de que, ao programar com @@ERROR, o valor mantido pela variável do sistema @@ERROR foi redefinido assim que a próxima instrução foi executada.

Outra vantagem fundamental do tratamento estruturado de exceções no T-SQL é que uma série de funções de tratamento de erros foram fornecidas e mantêm seus valores em todo o bloco CATCH. Funções separadas fornecem cada propriedade de um erro que foi gerado.

Isso significa que você pode escrever procedimentos armazenados de tratamento de erros genéricos que ainda podem acessar as informações relacionadas a erros.

  • Os blocos CATCH disponibilizam as informações relacionadas a erros durante toda a duração do bloco CATCH.
  • @@Error é redefinido quando a próxima instrução é executada.

Gerenciar erros no código

A integração do SQL CLR permite a execução do código gerenciado no SQL Server. Linguagens .NET de alto nível, como C# e VB, têm tratamento detalhado de exceções disponível para eles. Erros podem ser detectados usando blocos try/catch/finally padrão do .NET.

Erros no código gerenciado

Em geral, talvez você queira capturar erros dentro do código gerenciado o máximo possível. No entanto, é importante perceber que todos os erros não tratados no código gerenciado são passados de volta para o código T-SQL de chamada. Sempre que qualquer erro ocorrido no código gerenciado for retornado ao SQL Server, ele será exibido como um erro 6522. Erros podem ser aninhados e aquele erro específico envolverá a causa real do erro.

Outra causa rara, mas possível, de erros no código gerenciado seria que o código poderia executar uma instrução T-SQL RAISERROR por meio de um objeto SqlCommand.