# Manejo de errores

> La forma del resultado, el tipo de error y qué hacer con cada clase de fallo.


El SDK tiene un solo tipo de error y una sola forma de resultado. No hay jerarquía de excepciones que aprender.

## La forma

```ts
type Result<T> = { data: T; error: null } | { data: null; error: AndcoError };
```

Exactamente uno de los dos es nulo, siempre. Comprobar `error` estrecha el tipo de `data` sin aserciones.

## El error

```ts
class AndcoError extends Error {
  readonly code: string;
  readonly status: number | undefined;
  readonly details: Readonly<Record<string, unknown>> | undefined;
}
```

- **`code`** es lo que ramificas. Es estable; el mensaje no.
- **`status`** es el código HTTP cuando el error vino de una respuesta.
- **`details`** trae lo que Andco haya explicado del fallo: qué scope faltaba, qué campo era inválido.

Nunca ramifiques por `message`: está pensado para que lo lea una persona y puede cambiar.

## Las tres clases de fallo

**Falta un permiso.** La persona no aprobó lo que estás pidiendo. Se resuelve pidiendo una autorización nueva.

```ts
if (error.status === 403 && error.details?.["required_scope"]) {
  await andco.auth.signIn({ scopes: [...currentScopes, String(error.details["required_scope"])] });
}
```

**La sesión no sirve.** Venció y no se pudo renovar, o fue revocada.

```ts
if (error.status === 401) {
  await andco.auth.signOut();
  showSignIn();
}
```

**El entorno no coopera.** La ventana emergente fue bloqueada, no hay red, el servidor falló. Se reintenta o se explica; no se convierte en «la persona canceló».

```ts
if (error.code === "popup_blocked") {
  await andco.auth.signIn({ presentation: "redirect" });
}
```

## Cancelar no es fallar

Cuando alguien cierra la ventana de autorización, `signIn` devuelve `data: null` y `error: null`. No es un error, y tratarlo como tal produce mensajes de alarma por una decisión perfectamente normal.

```ts
const { data: session, error } = await andco.auth.signIn();
if (error) return showError(error);
if (!session) return; // closed the window, nothing happened
```

El SDK cuida la distinción de su lado: un tiempo de espera agotado, una navegación fallida o un error del servidor de autorización llegan como errores, nunca como cancelación.

## Errores al cargar la sesión

Una vuelta de callback puede fallar —transacción vencida, `state` que no correlaciona— y eso ocurre antes de que tu código llame a nada. El error queda en la carga del almacén:

```ts
const { error } = await andco.session.ready;
if (error) showError(error);
```

Sin esto, una integración rota se ve exactamente igual que una persona sin sesión.

## Códigos

La lista completa está en [Errores y códigos](/docs/reference/error-codes).
