Saltar al contenido

Los seis puntos donde puede morir

Cada tramo del recorrido tiene su forma de fallar, su mensaje característico y su arreglo. El catálogo completo, con lo que el frontend debe hacer en cada caso y lo que nunca debe hacer.

Las seis

La distinción que ordena todo

Mira la columna del medio: cinco de los seis son errores de programación y uno es un estado legítimo del mundo. Esa asimetría es la lección del nivel.

Los cinco primeros son deterministas: si el permiso falta, falta siempre; si el nombre está mal escrito, está mal siempre. No dependen de nada que el usuario haga, así que una interfaz que los trate con delicadeza está gastando trabajo en algo que debería haberse arreglado antes de publicar.

El quinto es distinto: el fichero puede existir o no, el disco puede estar lleno o no, la red puede fallar hoy y no mañana. Ese es el único que merece una pantalla.

El antipatrón

Es este, y está en casi todos los proyectos:

JS
// MAL: los seis casos acaban en el mismo sitio, con el mismo mensaje.try {  const p = await invoke('cargar_proyecto', { proyectoId: id });  pintar(p);} catch (e) {  mostrarError('Algo ha salido mal');}

Tiene tres problemas, en orden de gravedad:

Esconde los errores de programación. Un permiso que falta y un nombre mal escrito se ven en desarrollo exactamente igual que un fichero que no existe: como «algo ha salido mal». Ese mensaje es una alfombra, y debajo hay bugs.

No ayuda al usuario. «Algo ha salido mal» no le dice si tiene que reintentar, cambiar de fichero, liberar disco o llamar a soporte.

No deja rastro. Cuando alguien informe del problema, no vas a tener nada.

La forma que funciona

JS
try {  const p = await invoke('cargar_proyecto', { proyectoId: id });  pintar(p);} catch (e) {  // 5 · un estado legítimo: el core lo dijo con un código. Nivel 18.  if (e && typeof e === 'object' && 'code' in e) {    switch (e.code) {      case 'NO_EXISTE':   return avisar('Ese proyecto ya no está.');      case 'SIN_PERMISO': return avisar('No tengo acceso a esa carpeta.');      default:            return avisar('No se pudo abrir. ' + e.message);    }  }  // 1 a 4 y 6 · no es un estado del mundo: es un fallo nuestro.  registrar('invoke cargar_proyecto falló fuera de contrato', e);  throw e;   // que se vea en desarrollo; en producción lo recoge el registro}

La clave es la última línea: relanzar lo que no es un error de contrato. En desarrollo eso hace ruido, que es lo que quieres. En producción, con el plugin de registro del nivel 10.4, queda escrito en el fichero que un usuario te puede mandar.