Por Ronny Cruz Alvarez, fundador de Open Feed Network (Candor Network). Fundador solo, una plataforma en producción, muchas opiniones sobre lo que un mensaje de rechazo tiene permitido decir.
El bug que me hizo pensar
Hace dos semanas, en medio de construir una herramienta de filtrado de registros durante la más reciente ola de spam en el Fediverso, encontré un bug en mi propio motor de detección que me enseñó algo que ya debí haber sabido: la salida de un sistema de seguridad es, en sí misma, una superficie de ataque.
El motor — Sentinel, el clasificador de defensa perimetral detrás de todo lo que construyo — marca texto de registro spam usando un banco de patrones. Ofertas de criptomonedas, aperturas genéricas tipo plantilla, ese tipo de cosas. Cuando un patrón coincidía, la razón de rechazo que regresaba a quien llamaba se veía así:
jsreason: spam phrase matched: /crypto|investment.{0,10}opportunity/i
Legible. Fácil de depurar. Y, si ese mensaje llegaba a la persona rechazada en vez de quedarse en un log privado de administrador — una especificación completa y legible por máquina de exactamente qué palabras evitar. No construí un filtro de spam. Construí un filtro de spam con sus propias instrucciones de cómo evadirlo impresas en la caja.
Nada se rompió. Nada se veía mal en las pruebas. El regex hacía su trabajo perfectamente, cada vez — mientras silenciosamente entregaba la respuesta correcta.
Este no es un error raro. Es el modo de fallo normal de construir sistemas de detección rápido: instrumentas para tu propia depuración, y olvidas que "útil para mí" y "útil para un atacante" muchas veces es el mismo texto.
El invariante
Lo arreglé el mismo día, pero el parche importó menos que la regla que escribí después, y esa regla es la que realmente gobierna Sentinel ahora:
La lógica de detección y la divulgación de la detección son sistemas distintos, y solo uno de los dos llega a quien hizo la solicitud.
Internamente, cada veredicto todavía lleva su razonamiento completo — qué capa se activó, qué patrón coincidió, el peso exacto. Ese detalle es esencial; un sistema de seguridad que no puedes auditar es un sistema que no puedes confiar, ni siquiera desde adentro. Pero nada interno es el mismo objeto que lo que ve un usuario rechazado o una respuesta pública de API. La razón pública se toma de un vocabulario fijo y genérico — "dominio de correo desechable," "frase de spam detectada," "patrón de registro marcado" — deliberadamente incapaz de nombrar un regex específico, un umbral específico, o una entrada específica de una lista. Un atacante que sondea la API puede aprender que algo se activó. No puede aprender qué cambiar para dejar de activarlo.
Esa distinción ahora sostiene todo lo que Sentinel hace, en los dos lugares donde corre.
Dos frentes, un solo motor
Sentinel empezó como defensa perimetral: puntuación a nivel de solicitud en el borde — reputación, velocidad, regularidad de tiempos — decidiendo qué se desafía o bloquea antes de que toque una aplicación. Sentinel Signup es el mismo motor de seis capas apuntando a un problema más específico: colas de registro del Fediverso, que la ola de spam de julio convirtió en una crisis real para instancias de Mastodon administradas por voluntarios. Correos desechables, IPs de centros de datos, texto tipo plantilla de "apruébame por favor," ráfagas de registro desde la misma subred, y — añadido esta semana, después de que un administrador de habla hispana describiera estar siendo golpeado por lo que parecía una ola coordinada en ruso — una señal de discordancia de escritura/idioma: texto de solicitud en una escritura que contradice el idioma declarado de la cuenta.
La misma regla de divulgación aplica a ambos. El guardia perimetral le dice a un cliente desafiado "solicitud marcada." No le dice cuál de las verificaciones de reputación, velocidad, o regularidad se activó, ni por cuánto. Sentinel Signup le dice a un administrador de instancia "bloqueado: dominio de correo desechable; IP de centro de datos; contenido tipo plantilla" — categorías, no la biblioteca de patrones subyacente. Un administrador recibe suficiente para confiar en el veredicto. Un operador de bots no recibe nada para evadirlo.
Falla-a-cola, no falla-abierto ni falla-cerrado
La otra regla que Sentinel Signup impone sin excepción: si el filtrado mismo falla — una dependencia se cae, una consulta falla, lo que sea — el veredicto es marcar para revisión, nunca aprobar y nunca bloquear.
Esa es una tercera opción deliberada que la mayoría de sistemas no construyen. Fallar-abierto en un filtro de spam significa que una caída se convierte en una puerta abierta. Fallar-cerrado significa que un percance de un martes por la tarde bloquea a los nuevos usuarios reales tan duro como a los bots — y cerrar los registros es exactamente la jugada perdedora que los administradores ya estaban haciendo antes de que esto existiera; automatizar esa pérdida no es una solución. Falla-a-cola significa que un error le cuesta a un moderador humano treinta segundos de juicio, y no le cuesta nada al solicitante. El fallo es visible, es barato, y nunca fabrica un veredicto falso en ninguna dirección.
La pieza complementaria es la misma disciplina de falla-ruidosa que uso en todas partes: una conexión de base de datos faltante al arrancar es una negativa a iniciar, no una caída silenciosa a memoria que pierde silenciosamente los datos de cada instancia en el próximo reinicio. Prefiero que el servicio no arranque a que arranque mintiendo sobre lo que puede garantizar.
Limitaciones honestas
Las partes de esto que todavía no están terminadas:
El límite de divulgación se impone hoy por convención a nivel de código — cada ruta de respuesta se revisa a mano para confirmar que toma del vocabulario genérico, no del conjunto de patrones interno. Todavía no se impone estructuralmente, de la forma en que la capa de almacenamiento del feed principal de Candor estructuralmente no puede aceptar contenido sin filtrar. Ese es el próximo paso de endurecimiento, y hasta que se construya, "solo genérico" es una disciplina que mantengo, no una garantía que la arquitectura me da.
El análisis de texto hoy es heurístico y basado en reglas, más la puntuación de contenido propia del motor. No hay un clasificador aprendido en el ciclo, y no hay ningún LLM en el ciclo para el filtrado de registros — lo cual es deliberado: esto necesita funcionar a un costo marginal efectivamente cero por evaluación, ya que las instancias que no pueden pagar por protección contra spam son exactamente las que están siendo golpeadas más duro. Un clasificador opcional, revelado por instancia, está diseñado pero no construido.
La señal de escritura/idioma es nueva — tiene días, un solo patrón de ataque real detrás de ella. Solo se activa cuando una cuenta declara un idioma y el texto del solicitante lo contradice de una forma específica, y una sola coincidencia gana revisión humana, nunca rechazo automático. Ese conservadurismo es intencional; prefiero que falle por defecto un tiempo a que aprenda una mala heurística con evidencia insuficiente.
Soy un fundador solo. Sentinel ha estado corriendo defensa perimetral en producción desde mayo. Sentinel Signup tiene una semana, está vivo, y actualmente es gratis mientras está en beta específicamente para que tráfico adversario real — no casos de prueba sintéticos — me diga dónde realmente está equivocado antes de que alguien pague por ello.
Por qué este orden importa
Todo sistema de detección eventualmente es sondeado por lo mismo que detecta. La pregunta no es si un atacante enviará tráfico de prueba y leerá tus respuestas — lo hará, inmediatamente, así es como descubrió que tu filtro existía. La pregunta es si tu respuesta le enseña algo. Un mensaje de rechazo no es un log privado de depuración. En el momento en que sale de tu proceso, es el reconocimiento gratuito más valioso que le puedes dar a la persona que construiste el sistema para detener.
Si administras una instancia de Mastodon, o cualquier cosa con una cola de registro que esté siendo golpeada ahora mismo, Sentinel Signup es gratis durante la beta en signup.candortheopenfeednetwork.com. Si quieres decirme dónde el límite de divulgación todavía tiene fugas — prefiero escucharlo de ti que de alguien usándolo. Estoy en tips@candortheopenfeednetwork.com, y respondo todo yo mismo.
Top comments (0)