Tutorial para la programación segura en React que cubriría las principales vulnerabilidades existentes

La aparición de de vulnerabilidades de seguridad es una constante en el desarrollo de software, por lo que es importante que los especialistas en ciberseguridad aprenden a identificar los potenciales riesgos de seguridad y algunos mecanismos de prevención de incidentes.

En esta ocasión, los expertos del Instituto Internacional de Seguridad Cibernética (IICS) le mostrarán cómo utilizar la biblioteca JavaScript de código abierto React para abordar los principales riesgos de seguridad existentes actualmente. Como recordará, React es una biblioteca mantenida por Facebook y creada para crear interfaces de usuario con el objetivo de facilitar el desarrollo de aplicaciones en una sola página. Actualmente hay más de mil investigadores de ciberseguridad colaborando con este proyecto.

SCRIPTS ENTRE SITIOS (XSS)

El script entre sitios (XSS) es un tipo de vulnerabilidad del lado del cliente que puede generar problemas graves, señalan los expertos en ciberseguridad. Los ataques XSS ocurren cuando un actor de amenazas puede engañar a un sitio web para que ejecute JavaScript arbitrario en el navegador web objetivo, además de que existen variantes como el XSS reflejado o el XSS almacenado

El ataque XSS reflejado se lleva a cabo en un enlace que contiene datos en texto que el navegador procesa como código. Por ejemplo, un campo de formulario en el que se ingresa un texto de solicitud especial en el lado del cliente.

Por otra parte, el XSS almacenado es un escenario en el que un atacante tiene acceso a un servidor y cuando el código ejecutado en el servidor genera lo que llega a la página web del cliente. Los vectores típicos de estos ataques son la carga de comentarios e imágenes en los servidores.

En el pasado, los hackers usaron el gusano Samy para explotar una vulnerabilidad XSS en MySpace, con lo que se convirtió en uno de los virus de mayor propagación en la historia. Los scripts maliciosos se utilizan con mayor frecuencia para enviar spam y redirigir a los usuarios a sitios fraudulentos, señalan expertos en ciberseguridad.

VULNERABILIDAD NO. 1: TOMAR CONTROL SOBRE EL ESTADO DE LA PÁGINA ORIGINAL DURANTE LA RENDERIZACIÓN DEL SERVIDOR

A veces, cuando formamos el estado inicial de la página, lo que es peligroso, creamos un documento basado en una cadena JSON. Esta vulnerabilidad se ve así en el código:

<script>window.__STATE__ = ${JSON.stringify({ data })}</script>

Esto es peligroso porque este método convertirá los datos que se le proporcionen en una forma de cadena que se mostrará en la página. Si contiene campos que un usuario no autorizado puede editar, como el nombre de usuario o la información del usuario, puede incluir lo siguiente en esos campos: JSON.stringify (){data}

{ username: "pwned", bio: "</script><script>alert('XSS Vulnerability!')</script>" }

Este patrón se usa a menudo al renderizar aplicaciones React del lado del servidor usando Redux. Se introdujo en la documentación oficial de Redux, con el resultado de que muchos de los tutoriales y plantillas de aplicaciones de muestra que se encuentran en GitHub todavía lo usan.

¿Cómo identificar una vulnerabilidad durante una revisión de código?

Los expertos en ciberseguridad recomiendan buscar llamadas a métodos que acepten variables que puedan contener datos no autorizados en la etiqueta. Aquí hay un ejemplo que solía estar en la documentación de Redux: script JSON.stringify ()

function renderFullPage(html, preloadedState) {
    return `
        <!doctype html>
        <html>
            <head>
                <title>Redux Universal Example</title>
            </head>
            <body>
                <div id="root">${html}</div>
                <script>
                    window.__PRELOADED_STATE__ = ${JSON.stringify(preloadedState)}
                </script>
                <script src="/static/bundle.js"></script>
            </body>
        </html>
        `
}

Y aquí hay un fragmento de código de la aplicación de muestra que se encontró en GitHub:

function htmlTemplate( reactDom, reduxState, helmetData ) {
    return `
    <!DOCTYPE html>
    <html>
    <head>
        <meta charset="utf-8">
        ${ helmetData.title.toString( ) }
        ${ helmetData.meta.toString( ) }
        <title>React SSR</title>
        <link rel="stylesheet" type="text/css" href="./styles.css" />
    </head>
    
    <body>
        <div id="app">${ reactDom }</div>
        <script>
            window.REDUX_DATA = ${ JSON.stringify( reduxState ) }
        </script>
        <script src="./app.bundle.js"></script>
    </body>
    </html>
    `;
    
}

A veces, esta vulnerabilidad es un poco más difícil de detectar. El siguiente código también resultará inseguro si no se realiza el escape de sandbox adecuado: context.data

const RenderedApp = htmlData.replace('{{SSR}}', markup)
    .replace('<meta-head/>', headMarkup)
    .replace('{{data}}', new ArrayBuffer(JSON.stringify(context.data)).toString('base64'))

Al renderizar el servidor, preste atención a lo que se está renderizando. Si lo que ingresa el usuario no se escapa y se envía al DOM, puede ser peligroso.

¿Cómo protegerse contra este ataque?

Uno de los principales métodos de protección es usar el módulo npm serialize-javascript, diseñado para eliminar la salida JSON. Si ​está renderizando en un servidor fuera de Node.js, deberá seleccionar el paquete apropiado para el idioma que está utilizando.

A continuación se muestra el comando de instalación del módulo mencionado:

$ npm install --save serialize-javascript

Después de eso, debe importarlo a un archivo y reescribir el código previamente vulnerable:

<script>window.__STATE__ = ${ serialize( data, { isJSON: true } ) }</script>

Puede consultar más detalles en otros tutoriales.

VULNERABILIDAD NO. 2: ENLACES MALICIOSOS

Una etiqueta <a> puede contener un atributo hrefthat para conducir a los usuarios de un sitio web a otra página completamente distinta. Estos enlaces también pueden contener scripts maliciosos que podrían desencadenar severos daños en el sistema objetivo. Puede probar estas funciones copiando el siguiente código en la cadena de su navegador: javascript: stuff ().

data:text/html, <a href="javascript: alert('hello from javascript!')" >click me</a>

Los expertos en ciberseguridad mencionan que esto quiere decir que si el contenido de los enlaces se instala según la entrada del usuario, un atacante puede agregar código malicioso a los sistemas comprometidos. Luego, si el usuario sigue el enlace incorrecto, la secuencia de comandos del atacante se iniciará en el navegador.

Esta no es una falla que solo afecte a las aplicaciones basadas en React, pero es uno de los problemas más comunes para los desarrolladores de React cuando esperan que el valor correspondiente se escape automáticamente de manera adecuada. Cabe señalar que las próximas versiones de React incluirán mitigaciones para esta clase de fallas.

¿Cómo detectar una vulnerabilidad?

¿Pueden los usuarios del proyecto agregar enlaces a páginas por las que otros usuarios pueden navegar? Si es así, intente agregar un “enlace” a la página de la siguiente manera:

javascript: alert("You are vulnerable to XSS!")

Si se muestra el cuadro de mensaje correspondiente al hacer clic en el enlace, significa que el proyecto es vulnerable a los ataques XSS. Pruébelo cada vez que pueda agregar enlaces. Probablemente no todas estas ubicaciones sean vulnerables.

Mecanismos de protección

Los expertos en ciberseguridad mencionan que eliminar el prefijo javascript: data puede solucionar este problema. Este es un ejemplo de política de lista negra que no funciona correctamente.

Los hackers han ideado toda clase de métodos para esquivar estos mecanismos de seguridad, por lo que es necesario utilizar protocolos avanzados de lista blanca.

Otra estrategia de ciberseguridad es agregar una capa adicional de protección a su proyecto es utilizar un mecanismo de apertura de enlace personalizado en las nuevas pestañas del navegador. Sin embargo, los expertos no recomiendan utilizar esta estrategia como única línea de defensa para el proyecto.

VULNERABILIDAD NO. 3: ERRORES EN LA CONSTRUCCIÓN DANGEROUSLYSETINNERHTML

DangerouslySetInnerHTML es el nombre por el que se conoce a una configuración de React que puede resultar muy peligrosa para los desarrolladores. Considere el siguiente ejemplo, encontrado en un sitio desde la primera página de los resultados en la búsqueda de Google:

<script dangerouslySetInnerHTML={{ __html: `window.__PRELOADED_STATE__ = ${JSON.stringify(initialState)};`}}></script>

Este es un ejemplo de la primera vulnerabilidad descrita en este artículo, pero con una peculiaridad que debería llamar la atención de los expertos en ciberseguridad. En este ejemplo se usa dangerouslySetInnerHTML como un método para borrar datos y prevenir ataques XSS, lo que es poco recomendable; puede encontrar más información sobre esta configuración en los archivos de React.

Otro ejemplo de que esto sucede todo el tiempo es el hallazgo de una vulnerabilidad al agregar el marco Markdown a un sitio usando dangerousSetInnerHTML. Para protegernos de esta condición, podemos usar una regla especial.

Cómo identificar una vulnerabilidad durante una revisión de código

Antes de enviar solicitudes de extracción, puede buscar en el código las cadenas de evaluación y de HTML dangerouslySetInnerHTML (así es como también busco los comandos de console.log) o usar la regla de linter apropiada.

Asegúrese de que cada vez que utilice la configuración dangerouslySetInnerHTML, solo se carguen en la página datos de confianza. Puede consultar más información en otros tutoriales.

CONCLUSIONES

React está construido sobre JavaScript, por lo que aquellos interesados en aprender React deben comprender qué tan bien conocen JavaScript. Frecuentemente los desarrolladores cometen errores que demuestran su poco conocimiento de JavaScript, por lo que son propensos a los errores de configuración en React.

Los expertos en ciberseguridad recomiendan a los desarrolladores profundizar en el uso de JavaScript antes de usar React. Para conocer más sobre riesgos de seguridad informática, malware, vulnerabilidades y tecnologías de la información, no dude en ingresar al sitio web del Instituto Internacional de Seguridad Cibernética (IICS).