El login se deja «para el final». Los roles se improvisan cuando el primer cliente pide un usuario que no pueda ver precios. A las tres semanas el backend tiene un isAdmin, un role: string y un if en cada controlador. El agujero no se ve en staging. Se ve el día que alguien lista facturas ajenas.
Autenticación y autorización no son un formulario bonito. Son el modelo de quién es quién y qué puede tocar. Si lo piensas después de dibujar pantallas, reescribes pantallas. Si lo piensas después de las tablas, reescribes tablas. En desarrollo web a medida es una de las partidas que más retrasan cuando se trata como detalle.
Este artículo enumera los errores que más caros salen al modelar roles de usuario web, cómo separar login de permisos, y qué tienes que tener escrito antes de la primera línea. Sin receta de framework: con el criterio que usamos en Truman cuando hay más de un tipo de usuario.
Por qué los roles de usuario web hay que modelarlos antes del código
Una pantalla es una vista de un permiso. Si no sabes el permiso, estás dibujando una hipótesis. En un sitio corporativo de una sola cara pública, el modelo cabe en una servilleta: anónimo y editor. En una plataforma, no. Hay quien crea, quien aprueba, quien solo lee, quien actúa en nombre de una empresa y quien no debería saber que esa empresa existe.
En Klapper no es lo mismo el que compra una entrada, el que organiza el evento y el que opera la plataforma. Mezclar esos mundos en un único «usuario logueado» produce fugas de datos y pantallas imposibles. En Weddle pasa igual con perfiles que no comparten objetivos: quien organiza no necesita las mismas herramientas que quien participa. El diseño UX/UI sale del modelo, no al revés.
Modelar antes no es escribir un tratado. Es una lista de actores, recursos (pedido, evento, factura, sede) y verbos (ver, crear, editar, publicar, cobrar, impersonar). Con eso ya puedes decir qué tabla, qué ruta y qué componente existen. Sin eso, cada historia de usuario inventa un flag.
Errores que retrasan el desarrollo (y abren agujeros)
is_admin empieza siendo útil y acaba siendo la
llave maestra. El día que necesitas un soporte que impersona
pero no borra, no tienes modelo: tienes un if peligroso.24%
de las brechas analizadas en 2024 empezaron por uso de credenciales robadas; a 10 años vista, el 31%
Verizon, 2024 Data Breach Investigations Report
El login flojo (sin MFA donde toca, sesiones eternas, recuperación de contraseña débil) y los permisos flojos son primos. OWASP lleva años poniendo el control de acceso roto en lo alto de su Top 10. No es paranoia de security theater: es el fallo más repetido en aplicaciones web. Diseñar roles mal es una forma elegante de fabricarlo.
Autenticación no es autorización
Autenticación responde «¿quién eres?». Autorización responde «¿qué puedes hacer con esto?». Mezclarlas es el origen del if (user) que abre el panel entero. Estar logueado no es un permiso. Es un prerrequisito.
| Concepto | Pregunta | Si lo mezclas |
|---|---|---|
| Autenticación | ¿Eres quien dices? | Sesiones y MFA mal puestos |
| Autorización | ¿Puedes hacer esta acción sobre este recurso? | IDOR y fugas entre clientes |
| Rol | Paquete de permisos reutilizable | Explosión de roles únicos |
| Permiso | Verbo + recurso (+ ámbito) | Se comprueba en API y UI |
| Ámbito (tenant) | ¿De qué organización son los datos? | El admin de A ve a B |
El ámbito se olvida más que el rol. En B2B, el usuario no es el borde del sistema: lo es la organización. Un admin de la empresa A no es admin del mundo. Si tu foreign key no lleva organization_id y cada query no lo filtra, el rol más bonito del mundo filtra mal. Eso no se arregla con un componente de menú.
Cómo modelarlos: actores, recursos, verbos, ámbitos
Una sesión de una hora con quien conoce el negocio. Pizarra. Actores a la izquierda, recursos arriba, cruces con verbos. Las celdas vacías son tan importantes como las llenas: documentan lo que no existe. «Dirección no edita pedidos» es una decisión, no un olvido.
¿Puede un usuario de la organización A adivinar un ID de B y verlo? Si no has escrito el test, la respuesta en producción suele ser sí.
Ese modelo cabe en una hoja y evita tres sprints de parches. También evita una discusión tardía de arquitectura: si el mapa de permisos es una madeja, a lo mejor no necesitas microservicios; necesitas un módulo de autorización decente dentro de un monolito bien cortado. Partir servicios antes de tener roles claros multiplica el problema: cada API reimplementa el if.
Tip técnico: RBAC primero, excepciones después
Role-Based Access Control (rol → permisos → comprobación) cubre el 90% de las plataformas que vemos. Attribute-Based (reglas sobre atributos: «puede editar si es el autor y el estado es borrador») se añade para las excepciones, no como primer diseño. Empieza por una tabla roles, permissions y role_permission. Comprueba siempre en servidor, con el mismo helper. El frontend solo decide qué mostrar. Si necesitas una regla rara, un policy object. Si todas las reglas son raras, no tienes producto: tienes un ERP disfrazado y hay que decirlo en el discovery.
Qué deja deuda (y cómo no arrastrarla)
Los flags sueltos, los roles que son personas, las comprobaciones solo en UI y las sesiones que no caducan son deuda técnica con cara de seguridad. Se paga en incidentes, no en un refactor elegante. Documenta el mapa de permisos en el repo, no en un hilo de Slack. Cada permiso nuevo entra en el mapa o no entra en el código.
Si tu única protección es que el menú no muestra el enlace, no tienes autorización. Tienes esperanza. La API no lee el menú.
Ojo también con el atajo headless: un WordPress desacoplado no te regala un modelo de roles de producto. Te regala los de WordPress (admin, editor, author…) que casi nunca coinciden con tu negocio. Si estás valorando WordPress headless, pregunta en el mismo brief quién es el usuario de la app, no solo quién edita la home. El CMS no es tu IAM.
Qué pedimos escrito antes de picar
En Truman no empezamos el módulo de usuarios con la pantalla de login. Empezamos con la matriz. Login, recuperación, MFA y proveedor (correo, Google, SSO de empresa) vienen después, cuando ya sabemos a qué espacio entra esa identidad. Invertir el orden es diseñar una puerta sin saber qué habitaciones hay.
Si el cliente no puede llenar la matriz, el proyecto no está listo para estimar bien. Se puede acompañar —de hecho es parte del discovery— pero no se puede fingir que «ya lo veremos». Verlo después es rehacer. Y rehacer autenticación en producción es de las pocas cosas que no se pueden maquillar con un sprint de diseño.
Antes de escribir el login, verifica esto
- ¿Tienes matriz de actores × recursos × verbos, con celdas vacías explícitas?
- ¿El ámbito (organización, sede, propio registro) está escrito, no supuesto?
- ¿Cada permiso se comprobará en API, no solo en el menú?
- ¿Hay un test de «cambiar el ID» previsto para cada recurso sensible?
- ¿Los roles son paquetes reutilizables, no nombres de personas?
- ¿Quién impersona, quién audita y cómo se registra esa acción?
- ¿Sesión, recuperación de acceso y MFA están decididos para el contexto real?
- ¿El mapa de permisos vivirá en el repo, no en un hilo?
Preguntas frecuentes sobre roles de usuario en una web
¿Cuál es la diferencia entre autenticación y roles de usuario?
Autenticación identifica. El rol agrupa permisos. Puedes estar autenticado y no poder borrar nada. Puedes tener un rol de «lector» en una organización y de «editor» en otra. Si usas «estar logueado» como único permiso, el modelo ya está roto.
¿Cuántos roles debería tener una plataforma?
Los mínimos que cubran responsabilidades distintas. Tres a seis suele bastar al inicio. Cuando cada persona pide un rol propio, lo que necesitas son permisos asignables o un rol base más excepciones, no veinte nombres. Más roles no es más control: es más superficie de error.
¿Se pueden añadir roles a mitad de proyecto?
Sí, si el modelo es de permisos y no de ifs. No, si cada pantalla asume dos tipos de usuario. Por eso se modela antes: añadir «supervisor de sede» en un sistema con ámbitos es una fila en la matriz. Añadirlo sobre booleanos es un mes.
¿Hace falta SSO o MFA desde el primer día?
Depende de quién entre y qué datos haya. Una herramienta interna de empresa casi siempre acaba en SSO (Google, Microsoft, Okta). Una plataforma con pagos o datos de terceros necesita MFA en cuentas privilegiadas desde el día uno. El login «solo email y contraseña» para un superadmin es una decisión, no un default.