// security

El modelo de seguridad.

Qué protege una nota, qué puede y qué no puede ver el servidor, y dónde están los límites, dicho con claridad — porque una seguridad que no puedes entender no es seguridad.

Criptografía

  • Cifrado: cada nota se sella en tu teléfono con AES-256-GCM (un nonce de 12 bytes y una etiqueta de autenticación de 16 bytes) antes de subir nada. El texto cifrado alterado falla la autenticación en lugar de descifrarse en basura.
  • Derivación de clave: la clave proviene de HKDF-SHA256 sobre 32 bytes aleatorios nuevos — la clave del fragmento — más una sal aleatoria de 16 bytes. Esos 32 bytes van al #fragmento del enlace y a nada más.
  • Frase de contraseña (opcional): si estableces una, se refuerza con PBKDF2-HMAC-SHA256 a 600.000 iteraciones y se mezcla en la derivación, de modo que el enlace por sí solo ya no basta. Los intentos fallidos fallan localmente en el navegador del destinatario y nunca consumen vistas.
  • Verificado por partida doble: las implementaciones en Swift y Kotlin de las apps y la implementación WebCrypto del visor se comprueban entre sí con vectores de prueba generados de forma independiente, de modo que una nota sellada por una siempre se abre en la otra.

El enlace con clave en el fragmento

Un enlace de nota se ve así: burnpony.app/n/<id>#<key>. Todo lo que sigue al # es un fragmento de URL, y los navegadores no envían los fragmentos en las peticiones HTTP — ni a este servidor ni a ningún otro. El servidor conoce el ID aleatorio de la nota; la clave existe solo en el propio enlace y en el navegador del destinatario mientras lee. Por eso «el servidor no puede leer tu nota» es una propiedad de cómo funciona la web, no una promesa.

Qué almacena el servidor — y no puede leer

Mientras una nota está viva, el servidor guarda: el ID aleatorio de la nota, el blob de texto cifrado sellado, marcas de tiempo de creación y caducidad, el límite y el recuento de vistas, si se pidió un acuse de lectura, y un hash del token de gestión que permite a tu app quemar la nota antes. Si los acuses están activos, se registran las marcas de hora de apertura. Ese es el inventario. Nunca tiene la clave, el texto de la nota, ni siquiera el ajuste de ocultar automáticamente — este viaja cifrado dentro de la nota. La limitación de tasa de creación usa hashes de IP con un secreto del servidor que caducan tras unas dos horas, no registros de direcciones sin procesar.

Quemar, y qué queda

Cuando se solicita la última vista permitida, el texto cifrado se elimina en la misma transacción de base de datos que lo sirvió. Las notas caducadas se eliminan mediante un barrido que se ejecuta cada cinco minutos. Y, crucialmente, una nota quemada, una nota caducada y una nota que nunca existió devuelven exactamente la misma respuesta — el servidor no puede usarse como oráculo para confirmar que un enlace dado fue real alguna vez.

El visor

Los destinatarios abren una única página autónoma: sin frameworks, sin cookies, sin analítica, sin peticiones a ningún sitio salvo a este servidor para la propia nota sellada. Lleva una Content-Security-Policy estricta (default-src 'none'), una directiva noindex y una política sin referer para que el enlace nunca se filtre por cabeceras de referencia. El descifrado ocurre en el WebCrypto integrado del navegador. La página es lo bastante corta para auditarla con Ver código fuente — es un objetivo de diseño, no un accidente.

Acuses de lectura, con honestidad

Los acuses son opcionales por nota. El destinatario ve «Se notificará al remitente cuando se abra esta nota» antes de revelarla. La notificación que recibes es deliberadamente genérica — «Se abrió una nota.» con solo el ID de la nota adjunto — así que nada del contenido de la nota pasa por los servidores del proveedor de notificaciones.

Modelo de amenazas

BurnPony protege la confidencialidad y la integridad de una nota frente al servidor, a observadores de red y a cualquiera que después encuentre la URL sin su fragmento — y limita cuánto tiempo y cuántas veces una nota es legible siquiera. Asume que tu teléfono y el navegador del destinatario se comportan como está documentado. No defiende contra malware en ninguno de los extremos, ni contra un destinatario que copia, captura o fotografía la nota mientras está visible — ninguna herramienta de leer y quemar puede. La autodestrucción limita el acceso futuro; no puede vigilar el momento de la lectura.

Límites honestos

  • El enlace es la clave. Cualquiera que obtenga el enlace completo (y la frase de contraseña, si está fijada) antes de que se queme puede leer la nota. Envíalo por un canal en el que confiarías con el propio secreto, o añade una frase y compártela por separado.
  • Las pantallas pueden capturarse. La cuenta atrás de ocultar automáticamente reduce el tiempo de mirar por encima del hombro; no es protección contra capturas.
  • Teléfono perdido, gestión perdida. Las notas que has enviado siguen quemándose y caducando según su propio calendario, pero sin la pestaña Enviados de la app pierdes la capacidad de quemarlas antes o comprobar su estado.
  • Existen metadatos a nivel de red. Como cualquier servidor web, este ve las direcciones IP que se conectan a nivel de red mientras atiende peticiones. El servidor web frente al relevo está configurado con el registro de accesos desactivado, y la aplicación conserva solo los hashes de IP salados de vida corta descritos arriba.

La especificación exacta

Cada afirmación de esta página está expresada con precisión, constante por constante, en la página del protocolo v1, escrita contra el código congelado en el repositorio público y comprobable con los vectores de prueba compartidos.

Abierto a inspección

El visor es auditable hoy en cada enlace de nota, y el núcleo criptográfico, el visor y el servidor de relevo están planeados para publicación — consulta la página de código abierto para ver cómo va.

Reportar una vulnerabilidad

¿Encontraste algo? Escribe a NorseHorse@norsehor.se — cifrado con la clave PGP si lo prefieres. Los informes van directo al desarrollador, y las correcciones salen rápido porque no hay ningún comité de por medio.