> ## Documentation Index
> Fetch the complete documentation index at: https://docs.youka.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Erros

> Lide com YoukaRequestError, YoukaTaskError e falhas passíveis de retry

O SDK expõe duas classes de erro: `YoukaRequestError` para falhas de HTTP e validação, e `YoukaTaskError` para tarefas assíncronas que terminaram em um estado não bem-sucedido. Ambas estendem `Error` e carregam campos estruturados para que você possa ramificar por código, status e possibilidade de retry.

## `YoukaRequestError`

Lançado para erros HTTP, falhas de validação de requisição e respostas malformadas.

```ts theme={null}
import { YoukaRequestError } from "@youka/sdk";

try {
  await client.projects.create(body);
} catch (error) {
  if (error instanceof YoukaRequestError) {
    console.error({
      code: error.code,
      message: error.message,
      status: error.status,
      retryable: error.retryable,
      details: error.details,
    });
  } else {
    throw error;
  }
}
```

### Campos

<ParamField path="code" type="string">
  Código de erro legível por máquina, por exemplo `INVALID_REQUEST`, `UNAUTHORIZED`,
  `UPLOAD_FAILED`.
</ParamField>

<ParamField path="message" type="string">
  Descrição legível por humanos.
</ParamField>

<ParamField path="status" type="number">
  Código de status HTTP, se disponível.
</ParamField>

<ParamField path="retryable" type="boolean">
  `true` se o SDK considerar que vale a pena tentar novamente (limites de taxa, erros
  transitórios de servidor, repetição idempotente em andamento).
</ParamField>

<ParamField path="details" type="unknown">
  Detalhes fornecidos pelo servidor, normalmente uma lista de issues do Zod para erros de validação.
</ParamField>

### Códigos comuns

| Código                          | Causa                                                                                      | Retryable?        |
| ------------------------------- | ------------------------------------------------------------------------------------------ | ----------------- |
| `INVALID_REQUEST`               | O corpo da requisição falhou na validação do schema antes de ser enviado.                  | Não               |
| `UNAUTHORIZED`                  | Chave de API ausente ou inválida.                                                          | Não               |
| `NOT_FOUND`                     | O recurso não existe ou você não tem acesso.                                               | Não               |
| `CONFLICT`                      | Conflito de versão (HTTP 409).                                                             | Sim               |
| `TOO_MANY_REQUESTS`             | Limite de taxa atingido (HTTP 429).                                                        | Sim               |
| `INTERNAL_SERVER_ERROR`         | Falha transitória do servidor (HTTP 500).                                                  | Sim               |
| `IDEMPOTENT_REPLAY_IN_PROGRESS` | A requisição original ainda está em execução sob a mesma chave de idempotência (HTTP 202). | Sim               |
| `INVALID_RESPONSE`              | O servidor retornou um corpo que não correspondeu ao schema esperado.                      | Não               |
| `UPLOAD_FAILED`                 | O upload via URL assinada retornou um status diferente de 2xx.                             | Depende do status |

## `YoukaTaskError`

Lançado a partir de `client.tasks.wait(...)`, `client.projects.wait(...)` e `client.exports.wait(...)` quando a tarefa subjacente ou a exportação termina em `failed`, `cancelled` ou `timed-out`.

```ts theme={null}
import { YoukaTaskError } from "@youka/sdk";

try {
  await client.projects.wait(created);
} catch (error) {
  if (error instanceof YoukaTaskError) {
    console.error({
      code: error.code,
      message: error.message,
      status: error.status,
      task: error.task,
    });
  } else {
    throw error;
  }
}
```

### Campos

<ParamField path="code" type="'TASK_FAILED' | 'TASK_CANCELLED' | 'TASK_TIMED_OUT'">
  Mapeia diretamente para o status terminal da tarefa.
</ParamField>

<ParamField path="message" type="string">
  Ou a mensagem de erro da tarefa fornecida pelo servidor, ou um fallback gerado.
</ParamField>

<ParamField path="status" type="TaskStatus">
  O status terminal da tarefa.
</ParamField>

<ParamField path="task" type="RestTask">
  O payload completo da tarefa no momento da falha. Útil para logs e
  mensagens de erro voltadas ao usuário.
</ParamField>

## Padrão de retry

Combine `retryable` com uma chave de idempotência para construir um loop de retry seguro:

```ts theme={null}
import { YoukaRequestError } from "@youka/sdk";

async function createWithRetry<T>(fn: () => Promise<T>, maxAttempts = 3) {
  let lastError: unknown;

  for (let attempt = 1; attempt <= maxAttempts; attempt++) {
    try {
      return await fn();
    } catch (error) {
      lastError = error;
      if (
        error instanceof YoukaRequestError &&
        error.retryable &&
        attempt < maxAttempts
      ) {
        await new Promise((r) => setTimeout(r, 2 ** attempt * 1_000));
        continue;
      }
      throw error;
    }
  }

  throw lastError;
}

await createWithRetry(() =>
  client.projects.create(body, {
    idempotencyKey: "import-2026-04-08-song-001",
  }),
);
```

<Tip>
  Sempre reutilize a mesma chave de idempotência em todas as tentativas. Caso contrário, o servidor
  trata o retry como uma nova requisição e você pode acabar com duplicatas.
</Tip>

## Abort e cancelamento

Abortar uma requisição lança um `AbortError` padrão — não um `YoukaRequestError`. Verifique explicitamente:

```ts theme={null}
try {
  await client.projects.wait(created, { signal: controller.signal });
} catch (error) {
  if (error instanceof Error && error.name === "AbortError") {
    console.log("Cancelado pelo usuário");
    return;
  }
  throw error;
}
```

## Próximos passos

* [Tasks](/pt/sdk/tasks) — helpers de espera e polling avançado de tasks
* [Authentication](/pt/sdk/authentication) — opções do construtor e signals
* [API errors](/pt/api/errors) — os mesmos códigos em HTTP puro
