---
title: "Error Not Handled — Como Resolver em Zig"
url: "https://ziglang.com.br/erros/error-not-handled-como-resolver-em-zig/"
markdown_url: "https://ziglang.com.br/erros/error-not-handled-como-resolver-em-zig.MD"
description: "Entenda o erro 'error not handled' em Zig, que ocorre quando um error union não é tratado adequadamente. Veja como usar try, catch e switch para resolver."
date: "2026-02-21"
author: "Zig Brasil"
---

# Error Not Handled — Como Resolver em Zig

Entenda o erro 'error not handled' em Zig, que ocorre quando um error union não é tratado adequadamente. Veja como usar try, catch e switch para resolver.


# Error Not Handled — Como Resolver em Zig

## O Que Este Erro Significa

O erro de compilação `error is not handled` ocorre quando uma função retorna um error union (`!T`) e o código que a chama ignora o possível erro. Zig exige que todos os erros sejam tratados explicitamente — não é possível simplesmente ignorá-los como em C, onde valores de retorno de erro podem ser descartados silenciosamente.

A mensagem de erro típica do compilador:

```
error: error is ignored
```

Ou:

```
error: error union is not handled
```

Esse design é intencional: Zig acredita que erros ignorados são a causa de muitos bugs em produção, e força o programador a tomar uma decisão consciente sobre cada erro possível.

## Causas Comuns

### 1. Ignorar Retorno de Função que Pode Falhar

```zig
const std = @import("std");

pub fn main() void {
    const file = std.fs.cwd().openFile("dados.txt", .{});
    // ERRO DE COMPILAÇÃO: error union is not handled
    _ = file;
}
```

### 2. Chamar Função Falhável sem try ou catch

```zig
const std = @import("std");

fn lerDados(allocator: std.mem.Allocator) ![]u8 {
    return allocator.alloc(u8, 1024);
}

pub fn main() void {
    var gpa = std.heap.GeneralPurposeAllocator(.{}){};
    const allocator = gpa.allocator();

    const dados = lerDados(allocator);
    // ERRO: error union de lerDados não é tratado
    _ = dados;
}
```

### 3. Usar Resultado de Error Union Diretamente

```zig
const std = @import("std");

fn dividir(a: u32, b: u32) !u32 {
    if (b == 0) return error.DivisaoPorZero;
    return a / b;
}

pub fn main() void {
    const resultado = dividir(10, 2);
    // ERRO: resultado é !u32, não u32
    std.debug.print("{}\n", .{resultado});
}
```

### 4. Ignorar Erro em Expressão de Atribuição

```zig
const std = @import("std");

pub fn main() void {
    var buf: [100]u8 = undefined;
    const n = std.fmt.bufPrint(&buf, "Olá {}", .{"mundo"});
    // ERRO: bufPrint retorna ![]u8
    _ = n;
}
```

## Como Corrigir

### Solucao 1: Usar try para Propagar o Erro

A forma mais comum — propaga o erro para quem chamou a função:

```zig
const std = @import("std");

pub fn main() !void {  // Note o !void
    const file = try std.fs.cwd().openFile("dados.txt", .{});
    defer file.close();

    // Usa file normalmente
    var buf: [1024]u8 = undefined;
    const bytes = try file.read(&buf);
    _ = bytes;
}
```

### Solucao 2: Usar catch com Valor Padrão

```zig
const std = @import("std");

fn dividir(a: u32, b: u32) !u32 {
    if (b == 0) return error.DivisaoPorZero;
    return a / b;
}

pub fn main() void {
    const resultado = dividir(10, 0) catch 0; // Se falhar, usa 0
    std.debug.print("resultado: {}\n", .{resultado});
}
```

### Solucao 3: Usar catch com Bloco de Tratamento

```zig
const std = @import("std");

pub fn main() void {
    const file = std.fs.cwd().openFile("dados.txt", .{}) catch |err| {
        std.debug.print("Não foi possível abrir arquivo: {}\n", .{err});
        return;
    };
    defer file.close();

    // Usa file...
    _ = file;
}
```

### Solucao 4: Usar catch com switch para Erros Específicos

```zig
const std = @import("std");

pub fn main() void {
    const file = std.fs.cwd().openFile("config.txt", .{}) catch |err| switch (err) {
        error.FileNotFound => {
            std.debug.print("Arquivo não encontrado, usando padrões\n", .{});
            return;
        },
        error.AccessDenied => {
            std.debug.print("Permissão negada\n", .{});
            return;
        },
        else => {
            std.debug.print("Erro inesperado: {}\n", .{err});
            return;
        },
    };
    defer file.close();
    _ = file;
}
```

### Solucao 5: Usar if com Error Union

```zig
const std = @import("std");

fn dividir(a: u32, b: u32) !u32 {
    if (b == 0) return error.DivisaoPorZero;
    return a / b;
}

pub fn main() void {
    if (dividir(10, 2)) |resultado| {
        std.debug.print("Sucesso: {}\n", .{resultado});
    } else |err| {
        std.debug.print("Erro: {}\n", .{err});
    }
}
```

### Solucao 6: Descartar Erro Explicitamente (Quando Apropriado)

Em casos raros onde você sabe que o erro não vai acontecer:

```zig
const std = @import("std");

pub fn main() void {
    // Só use catch unreachable quando tiver CERTEZA de que não falhará
    var buf: [100]u8 = undefined;
    const resultado = std.fmt.bufPrint(&buf, "valor: {d}", .{@as(u32, 42)}) catch unreachable;
    std.debug.print("{s}\n", .{resultado});
}
```

## Padrões de Tratamento de Erro

### Propagação com try

```zig
fn lerConfig(caminho: []const u8) !Config {
    const file = try std.fs.cwd().openFile(caminho, .{});
    defer file.close();
    // try propaga qualquer erro para cima
    const dados = try file.readToEndAlloc(allocator, max_size);
    defer allocator.free(dados);
    return try parseConfig(dados);
}
```

### Fallback com catch

```zig
fn obterPorta() u16 {
    const env_porta = std.process.getEnvVarOwned(allocator, "PORT") catch return 8080;
    defer allocator.free(env_porta);
    return std.fmt.parseInt(u16, env_porta, 10) catch 8080;
}
```

### Conversão de Erro

```zig
const AppError = error{ConfigInvalida};

fn carregarApp() AppError!void {
    lerConfig("app.conf") catch {
        return AppError.ConfigInvalida;
    };
}
```

## Por Que Zig Exige Tratamento de Erros

Em muitas linguagens, erros são facilmente ignorados:

```c
// C — erro ignorado silenciosamente
FILE *f = fopen("dados.txt", "r");
// Se f é NULL, o programa continua e crashará depois
```

Zig elimina essa classe de bugs ao tornar o tratamento de erros obrigatório. O compilador garante que toda possibilidade de falha é endereçada pelo programador, mesmo que a decisão seja "propagar para cima com try". Outras linguagens de sistemas adotam abordagens similares: <a href="https://golang.com.br/artigos/go-error-handling/" target="_blank" rel="noopener" onclick="umami.track('portfolio-site-click', { destination: 'golang.com.br' })">Go exige verificação explícita de error</a> e <a href="https://rustlang.com.br/artigos/rust-error-handling/" target="_blank" rel="noopener" onclick="umami.track('portfolio-site-click', { destination: 'rustlang.com.br' })">Rust usa Result&lt;T, E&gt; com o operador ?</a> para garantir que erros nunca sejam ignorados.

## Erros Relacionados

- [Try in non-error function](/erros/erro-try-in-non-error-fn/) — Usar try em função que não retorna erro
- [Catch reached unreachable](/erros/erro-catch-unreachable/) — Catch atingiu unreachable
- [Attempt to unwrap error](/erros/erro-unwrap-error/) — Tentar desempacotar error union
- [Error payload not used](/erros/erro-payload-not-used/) — Payload de erro não utilizado

## Links Úteis

- [Documentação oficial do Zig — Errors](https://ziglang.org/documentation/master/#Errors)
- [Receitas de tratamento de erros](/receitas/)
- [Tutorial sobre error unions](/tutoriais/)
