DEV Community

Ronny Cruz
Ronny Cruz

Posted on

El Formulario de Registro Que No Tiene Nada Que Filtrar

El Formulario de Registro Que No Tiene Nada Que Filtrar

Por Ronny Cruz Alvarez, fundador de Open Feed Network (Candor Network). Fundador solo, una plataforma en producción, y un flujo de registro que deliberadamente no sabe casi nada de ti.

El problema que me creé yo mismo

El registro de Candor no recoge correo electrónico. Ni teléfono. Ni cuenta de CAPTCHA, ni identidad de OAuth, nada que verificar porque no hay nada contra qué verificar. Instalas la app, eliges un nombre de usuario, pones un PIN, y el navegador genera un par de llaves ECDSA P-256 en tu dispositivo. El servidor recibe exactamente dos cosas: el nombre de usuario y la llave pública. Las doce palabras semilla y el archivo de recuperación se quedan contigo. Ese es el registro completo.

Lo construí así a propósito. Registro sin datos personales significa que no hay base de datos de correos que filtrar, ni lista de teléfonos que citar judicialmente, ni grafo de identidad que vender. Para una plataforma cuya tesis completa es que tu voz no debería depender de confiar en mí, es el diseño correcto.

También es, desde la perspectiva de la defensa contra spam, una pesadilla que me entregué a mí mismo. Cada señal en la que la industria se apoya para filtrar registros —dominios de correo desechable, reputación de correo, verificación de ida y vuelta— asume que existe un correo. El mío no. Y el flujo es rápido por diseño, lo cual significa que un script también puede serlo. El viernes pasado, una revisión de código con IA lo dijo sin rodeos: nada impedía que un bot hiciera un bucle sobre el endpoint de registro y creara cincuenta mil cuentas, inundando el feed con identidades que no cuestan nada crear.

La revisión tenía razón. Nada lo impedía.

La ironía era que yo vendo la solución

La semana anterior había lanzado Sentinel Signup — un servicio de filtrado de registros para instancias del Fediverso golpeadas por exactamente ese tipo de ola. Seis capas: reputación de IP y de dominio, velocidad por subred, patrones de tiempo, análisis de contenido, todo.

Mi propia plataforma no lo estaba usando. Los hijos del zapatero, descalzos como siempre.

Peor: no podía usarlo. La API de filtrado exigía un correo en cada petición, porque todos los clientes que había imaginado tenían uno. Mi propio flujo de registro —el más respetuoso con la privacidad que conozco— estaba estructuralmente excluido de mi propio producto de seguridad. Y el motor iba más lejos que solo exigirlo: un correo ausente sumaba una penalización de +30 por "correo inválido". Pasa a mis propios usuarios honestos por mi propio filtro, y todos empiezan pareciendo sospechosos. Una función de privacidad leída como señal de fraude.

Vale la pena detenerse ahí, porque no es una peculiaridad de mi código. Es lo que pasa en toda esta industria cuando los sistemas anti-abuso asumen señales de identidad que las plataformas respetuosas con la privacidad deliberadamente no recogen. La postura por defecto de la defensa contra spam es que saber menos de un usuario lo hace más sospechoso. Si queremos que existan plataformas que preserven la privacidad, las herramientas de seguridad tienen que dejar de castigarlas por ello.

La solución: ausencia no es malformación

El cambio fue pequeño y filosóficamente importante. El motor ahora distingue dos cosas que antes confundía:

Correo presente pero mal formado — se sigue penalizando. Alguien mandó basura en un campo de correo; eso es una señal real.
Correo no proporcionado en absoluto — se registra como un hecho neutral, peso cero. Una plataforma sin datos personales no tiene nada que enviar, y ser honesta sobre eso no debería costarle nada a sus usuarios.
Cada verificación que se activa cuando el correo sí está presente —listas de dominios desechables, patrones de correos temporales— se activa exactamente igual que antes. La batería de pruebas comprueba ambas direcciones: ninguna penalización por ausencia, ninguna suavización ante la basura.

Con eso, mi registro por fin pudo ser filtrado por mi propio producto, usando solo lo que realmente existe: nombre de usuario, IP real del cliente (desde la cabecera reenviada por el CDN — el servicio nunca ve conexiones directas), agente de usuario y tiempo. Sin correo, sin marcador de posición sintético contaminando el análisis. Lo que es real se analiza; lo que no existe no se inventa.

La pregunta de postura que nadie hace hasta que hay una caída

Conectar el filtro al manejador de registro obligó a una decisión que la mayoría de las integraciones se saltan: ¿qué pasa cuando el filtrado mismo falla?

Para mis clientes administradores de Mastodon, la respuesta es falla-a-cola — un error de filtrado envía al solicitante a la cola de aprobación humana, donde decide un moderador. Nunca admitido en silencio, nunca rechazado en silencio.

Mi flujo de registro no tiene cola. No hay moderador entre una persona y su cuenta, por diseño. Así que falla-a-cola no significa nada aquí, y las dos opciones de manual están mal: fallar-cerrado significa que un tropiezo de dos segundos deja fuera a personas reales; fallar-abierto en silencio significa que los bots pasan y nadie se entera.

La postura que desplegué: bloquear solo ante un veredicto duro de bloqueo; ante una marca o cualquier error, permitir — pero en voz alta. Cada registro marcado y cada fallo de filtrado queda en los logs con su razón. Una ráfaga que se cuele durante una caída es visible y atribuible en minutos. Una persona real bloqueada por un fallo de dependencia sería invisible para siempre — simplemente se iría. Entre esos dos costos, la decisión no está reñida.

Qué le hizo la barrera al escenario del bot

Después de desplegar, corrí el ataque contra mi propio servidor de producción. Primero, un registro legítimo — pasó limpio, token emitido, indistinguible de antes. Luego la versión en miniatura del escenario de las cincuenta mil cuentas: registros a toda velocidad desde una sola IP, par de llaves nuevo cada vez.

La escalera de escalado, directo de los logs:

Registros 1–2: pasaron.
Registro 3: marcado — múltiples cuentas desde una IP, alta velocidad de subred — permitido, registrado.
Registro 4: bloqueado — umbral de velocidad superado.
Registros 5 al 15: bloqueados al instante — "IP previamente bloqueada". La barrera recordó. Cada intento posterior murió sin siquiera ser evaluado de nuevo.
Un bot que quería cincuenta mil cuentas consiguió cuatro. Y la persona que se registró primero nunca notó que pasara nada.

Limitaciones honestas

Mi prueba fue desde una sola IP. Un adversario real rota por proxies residenciales, y la velocidad desde la misma IP se debilita frente a eso. La velocidad por subred atrapa la versión perezosa; una botnet bien distribuida es un problema más difícil, y no pretendo haberlo cerrado.
Las señales que quedan son delgadas por diseño. Nombre de usuario, IP, agente de usuario, tiempo — ese es todo el conjunto cuando te niegas a recoger identidad. Considero que el intercambio vale la pena, pero es un intercambio, y quien te diga que puede reemplazar por completo la reputación de correo con cuatro campos te está vendiendo algo.
Los umbrales se quedan privados. Ya escribí antes sobre por qué los mensajes de rechazo nunca deben enseñarle al atacante qué lo delató; la misma regla aplica aquí. Un registro bloqueado ve "temporalmente no disponible", no qué capa se activó ni con qué conteo.
Esto es una plataforma, con días en producción. La evidencia son mis propios logs, fechados, de mi propio servidor. No es un estudio a escala de flota.
Por qué el punto era comernos nuestra propia comida

La propuesta de Sentinel Signup a los administradores de Mastodon siempre ha sido "construido para nosotros, disponible para ti" — los módulos se extrajeron de las defensas de la propia plataforma. Desde esta semana eso es cierto en el sentido más pleno: el mismo motor de filtrado, la misma API, el mismo sistema de inquilinos que recibe cualquier cliente es lo que está entre mi propio endpoint de registro y la próxima ola de creación masiva. El cliente cero soy yo. Cuando se rompa, se me rompe a mí primero — que es exactamente el arreglo que mantiene honesto a un producto de seguridad.

Si administras una plataforma con un flujo de registro —especialmente una que recoge menos de lo que la industria asume que deberías— Sentinel Signup es gratis durante la beta en signup.candortheopenfeednetwork.com, y el soporte sin datos personales descrito aquí está activo para todos los inquilinos. Si crees que mi postura ante fallos está equivocada, quiero escucharlo especialmente: tips@candortheopenfeednetwork.com. Respondo todo yo mismo.

Top comments (0)