Tratamento de erros
Todos os erros do SDK derivam de Nfe::Error, então você pode capturar a
família inteira com um único rescue Nfe::Error. Esta página descreve a
hierarquia, os códigos HTTP mapeados, padrões de rescue por tipo, a validação
client-side e os erros de rede.
A hierarquia de erros
| Classe | Código HTTP | Quando ocorre |
|---|---|---|
Nfe::Error | — | Base de toda a família. |
Nfe::AuthenticationError | 401 | Chave de API ausente ou inválida. |
Nfe::AuthorizationError | 403 | Chave válida, mas sem permissão para o recurso. |
Nfe::InvalidRequestError | 400 / 422 | Requisição malformada ou reprovada na validação. |
Nfe::NotFoundError | 404 | Recurso não existe. |
Nfe::ConflictError | 409 | Conflito com o estado atual do recurso. |
Nfe::RateLimitError | 429 | Excesso de requisições; expõe #retry_after. |
Nfe::ServerError | 5xx | Falha no servidor da API. |
Nfe::ApiConnectionError | — | Falha de rede (DNS, conexão recusada, TLS, reset). |
Nfe::TimeoutError | — | Timeout de conexão/leitura (< ApiConnectionError). |
Nfe::SignatureVerificationError | — | Assinatura de webhook reprovada. |
Nfe::ConfigurationError | — | SDK mal configurado (chave ausente, environment inválido). |
Nfe::InvoiceProcessingError | — | Resposta 202 viola o protocolo (ex.: sem header Location). |
TimeoutError é subclasse de ApiConnectionErrorUm rescue Nfe::ApiConnectionError também captura Nfe::TimeoutError. Trate o
timeout antes, se quiser distingui-lo.
Contexto carregado pelos erros HTTP
Erros derivados de uma resposta HTTP carregam contexto para diagnóstico:
#status_code, #request_id, #error_code, #response_body e
#response_headers.
begin
client.service_invoices.retrieve(company_id: "...", invoice_id: "...")
rescue Nfe::Error => e
e.status_code # ex.: 404
e.request_id # id de correlação do servidor
e.error_code # código de erro legível por máquina
end
#to_h é seguro para logsNfe::Error#to_h devolve um Hash com type, message, status_code,
request_id e error_code — e omite deliberadamente o corpo e os headers
brutos, que podem conter a chave de API ou PII. Prefira-o ao logar erros.
Padrões de rescue por tipo
Capture do mais específico para o mais genérico:
begin
client.service_invoices.create(company_id: company_id, data: payload)
rescue Nfe::AuthenticationError
# 401 — revise a chave de API.
raise
rescue Nfe::AuthorizationError
# 403 — a chave não tem permissão para este recurso.
raise
rescue Nfe::InvalidRequestError => e
# 400/422 — corrija o payload; e.message traz o detalhe do servidor.
warn "Requisição inválida: #{e.message}"
rescue Nfe::RateLimitError => e
# 429 — respeite o retry_after antes de tentar de novo.
sleep(e.retry_after || 5)
retry
rescue Nfe::ServerError
# 5xx — falha do lado do servidor; reportar/retentar com backoff.
raise
rescue Nfe::TimeoutError
# Timeout de conexão/leitura.
raise
rescue Nfe::ApiConnectionError
# Outras falhas de rede.
raise
rescue Nfe::Error => e
# Rede de segurança para qualquer erro do SDK.
warn e.to_h.inspect
raise
end
Validação client-side (fail-fast)
Validações client-side (id de empresa vazio, chave de acesso com tamanho
errado, CNPJ/CPF/CEP/UF inválidos) levantam Nfe::InvalidRequestError com uma
mensagem em pt-BR antes de qualquer requisição HTTP:
begin
client.service_invoices.retrieve(company_id: "", invoice_id: "abc")
rescue Nfe::InvalidRequestError => e
# Levantado de forma síncrona, sem rede. e.status_code é nil aqui.
warn e.message # mensagem em português identificando o argumento inválido
end
status_code na validação localPor não vir de uma resposta HTTP, um InvalidRequestError client-side tem
status_code igual a nil — diferente do mesmo erro vindo de um 400/422.
RateLimitError#retry_after
No HTTP 429, o SDK lê o header Retry-After (quando presente) e o expõe como um
inteiro de segundos em #retry_after. Pode ser nil se o servidor não anunciar.
begin
client.addresses.retrieve(postal_code: "01310100")
rescue Nfe::RateLimitError => e
wait = e.retry_after || 5
sleep wait
retry
end
Erros de rede
Quando nenhuma troca HTTP se completa, o SDK levanta um erro de rede em vez de devolver uma resposta:
Nfe::ApiConnectionError— DNS, conexão recusada, TLS, reset de conexão.Nfe::TimeoutError— timeout de conexão ou de leitura; subclasse deApiConnectionError. A exceção original fica preservada emcause.
begin
client.companies.list
rescue Nfe::TimeoutError => e
warn "Timeout: #{e.message}; causa original: #{e.cause&.class}"
rescue Nfe::ApiConnectionError => e
warn "Falha de conexão: #{e.message}"
end
Próximos passos
- Emissão assíncrona e polling — trate falhas no loop.
- Configuração —
timeout,max_retriese TLS. - Primeiros passos — visão geral do SDK.