Atlasingeniería

Code review en la prácticaRobustez donde el usuario es impredecibleTema 2

Cuando el navegador bloquea el almacenamiento local

Leer una preferencia guardada puede lanzar una excepción, devolver algo de una versión anterior de la aplicación o volver vacío sin aviso. Tres casos que rompen la pantalla entera si el acceso no está encapsulado.

Guardar una preferencia en el navegador parece la operación más inofensiva que existe. En una pestaña de incógnito, con cookies de terceros bloqueadas, con el disco lleno o con la configuración del navegador endurecida, esa misma línea lanza una excepción.

Y si está en el camino de inicialización, la excepción no rompe la preferencia: rompe la pantalla.

Las tres formas de fallar

SituaciónQué pasaQué se ve si no está contemplado
Almacenamiento deshabilitado o sin cuotaEl acceso lanza excepciónLa aplicación no arranca
Valor de una versión anteriorSe lee algo con otra formaErrores al usar campos que ya no existen
Valor corrupto o editado a manoEl parseo falla o devuelve cualquier cosaEstado inconsistente difícil de reproducir
Los tres tienen la misma solución de fondo: que nada dependa de que el almacenamiento funcione.

El segundo es el más subestimado. El almacenamiento del navegador es persistente de verdad: lo que guardó una versión de hace dos años sigue ahí, y lo va a leer el código de hoy.

Encapsular el acceso

El comentario de review que resuelve la familia entera es el mismo: el acceso directo no va repartido por la aplicación, va detrás de una capa chica.

Qué hace esa capa

  1. Captura. Toda lectura y escritura, en un try. Si falla, la aplicación sigue con el valor por defecto en memoria.
  2. Valida la forma. Lo leído se verifica contra un esquema antes de usarse; lo que no cumple se descarta como si no estuviera.
  3. Tolera lo viejo. Descartar entradas inválidas y conservar las válidas, en vez de tirar todo o confiar en todo.
  4. Centraliza las claves. Una constante por clave, para que no haya dos formas de escribir el mismo nombre —el bug silencioso de siempre—.

Qué conviene guardar ahí y qué no

La otra mitad del comentario es sobre el contenido. El almacenamiento del navegador es visible y editable por el usuario, no viaja entre dispositivos y puede desaparecer en cualquier momento.

Antes de seguir, predecí

¿Cuál de estos datos NO debería vivir en el almacenamiento local?

La regla es la misma que con la validación: conveniencia sí, verdad no. Y hay una consideración de privacidad: datos personales guardados en el dispositivo son datos que sobreviven al cierre de sesión, salvo que alguien se ocupe de limpiarlos.

Cuando cambia la forma de lo guardado

Si la estructura cambia entre versiones, hace falta una decisión explícita, porque los dos extremos son malos: confiar en lo viejo rompe, y borrar todo hace que el usuario pierda sus preferencias sin motivo.

Lo que funciona

  1. Versionar lo guardado, con un número dentro del valor o en el nombre de la clave.
  2. Migrar lo que se pueda al leer, una sola vez, y descartar lo que no.
  3. Tratar lo desconocido como ausente. Es lo que convierte un error en un valor por defecto.
Más a fondo · nivel seniorEsto mismo vale para cualquier estado que sobrevive al despliegue

El patrón excede al navegador: es el mismo problema de un archivo de configuración escrito por una versión anterior, de un mensaje en una cola con el formato viejo o de una fila en la base guardada por el código del año pasado. Todo dato que persiste más que el código que lo escribió necesita versión, validación al leer y una política explícita para lo que no se entiende.

Una línea que puede tirar la pantalla

src/theme/use-theme.ts+7−1

Hay 3 problemas en este cambio. Tocá la línea donde creas que está.

@@ -1,8 +1,18 @@
11
22
3
4
35
4
6
7
8
9
10
511
612
713

Dos accesos al almacenamiento, tres formas de fallar, y la aplicación andaba perfecto en la máquina de quien lo escribió.

La regla general de la frontera

Cierre

Autoevaluación

¿Lo entendiste?

¿Por qué es riesgoso leer del almacenamiento local durante el render inicial?
¿Qué tipo de dato NO corresponde guardar en el navegador?