React XSS

XSS-атаки или межсайтовый скриптинг — это тип атаки, при которой вредоносный код внедряется на веб-страницу и затем выполняется.

Этот вредоносный код может украсть ваши cookies, изменить содержимое или взять под контроль всю веб-страницу.

Содержание этой статьи:

  • Атаки
  • XSS-атаки на основе DOM
    • eval
    • href
    • dangerouslySetHTML
  • Простая защита от XSS-атак
  • React XSS защита

Атаки

Примерно с середины 2012 года исследовательское сообщество начало использовать два новых термина, чтобы помочь упорядочить типы XSS.
Типы XSS-атак с середины 2012 года:

XSS-атаки на основе DOM в React

Эти атаки относятся к подмножеству клиентского межсайтового скриптинга, поскольку источник данных находится только на стороне клиента.


В этой статье я покажу вам три примера XSS-атак на основе DOM.
Мы рассмотрим уязвимости eval, href и dangerouslySetHTML.

eval

Функция eval() оценивает строку и возвращает значение завершения.
Проблема функции eval заключается в том, что вы можете вставить внутрь вредоносный код javascript и выполнить его.
Приведем пример, вот фрагмент кода в JSX-коде

import React, { useState } from 'react';

const Eval = () => {
    const [data, setData] = useState();

    const handleType = (e) => {
        setData(e.target.value);
    };

    const handleSubmit = () => {
        eval(data);
    };

    return (
        <div>
            <p>Place this code inside input: <code>alert('Hacked')</code></p>
            <input
                type='text'
                name='firstName'
                value={data}
                onChange={(e) => handleType(e)}
            />
            <button onClick={() => handleSubmit()} className="button">Submit</button>{' '}
        </div>
    );
};

export default Eval;
Войти в полноэкранный режим Выйти из полноэкранного режима

И ниже результат выполнения фрагмента кода.

Мы используем браузер пользователя и его ввод для выполнения простой функции оповещения, а в реальной жизни злоумышленник может использовать другой вредоносный код javascript, чтобы сделать что-то ужасное с вашей веб-страницей, cookies.

href

href — это атрибут элемента. Элемент <a> определяет гиперссылку, которая используется для ссылки с одной страницы на другую.
В качестве примера, мы можем внедрить пользовательский ввод внутри href, и это является проблемой. Как видно из приведенного ниже фрагмента кода, мы используем переменную data для заполнения атрибута href, а данные заполняют элемент input.

import React, { useState } from 'react';

const Href = () => {
    const [data, setData] = useState();
    const handleType = (e) => {
        setData(e.target.value);
    };

    return (
        <div>
            <p>Place this code inside input: <code>javascript: alert('Hacked');</code></p>
            <input
                type='text'
                name='text'
                value={data}
                onChange={(e) => handleType(e)}
            />
            <a href={data} className="button">Click Here</a>
        </div>
    );
};

export default Href;
Вход в полноэкранный режим Выход из полноэкранного режима

Выполнение кода:

dangerouslySetHTML

Это свойство HTML-кода, благодаря которому вы можете использовать HTML-элементы в коде react вместо функции innerHTML. Содержимое dangerouslySetHTML является динамическим и пропускает сравнение с виртуальным DOM. Как вы можете понять, это уже третья XSS-уязвимость. Ниже приведен код и результат выполнения

import React from 'react';

const DangerouslySetInnerHTML = () => {

    const placeHtml = () => {

        return {

            __html: "<img onerror='alert("Hacked!");' src='invalid-image' />",

        };

    };

    return (

        <div>

            <p>We inserted img inside div using dangerouslySetInnerHTML property and add js code in onerror attribute</p>

            <div dangerouslySetInnerHTML={placeHtml()} />

        </div>

    );

};

export default DangerouslySetInnerHTML;
Вход в полноэкранный режим Выйти из полноэкранного режима

Результат рендеринга:

Простая защита от XSS-атак

Вы можете заменить зарезервированные символы (такие как < и >) на соответствующие им символьные сущности (&lt; и &gt;).
В результате код будет отрисован, код JavaScript не сможет быть выполнен, а символьные сущности будут преобразованы в соответствующие им резервные символы.
Также можно использовать «санацию» пользовательского ввода с помощью библиотеки под названием dompurify.

Защита от XSS в React

Как вы видите, наиболее уязвимым местом является ввод, и у нас есть статья о контролируемых и неконтролируемых компонентах в документации React.
Ниже вы можете прочитать блок-цитату из официальной документации React:

В форме элементы являются либо вводимыми, как textarea. input, либо выбираемыми, как радиокнопки или чекбоксы, при каждом изменении они обновляются соответствующим образом через некоторые функции, которые также обновляют состояние.
Для реализации форм мы рекомендуем использовать управляемые компоненты. В управляемом компоненте данные формы обрабатываются компонентом React.
В HTML элементы формы, такие как , , , и , обычно поддерживают свое собственное состояние и обновляют его на основе пользовательского ввода. В React изменяемое состояние обычно хранится в свойстве state компонентов и обновляется только с помощью функции setState().
Альтернативой являются неконтролируемые компоненты, в которых данные формы обрабатываются самим DOM.
Чтобы написать неконтролируемый компонент, вместо того чтобы писать обработчик событий для каждого обновления состояния, вы можете использовать ссылку (createRef) для получения значений формы из DOM.

Резюме

Защита вашего React-приложения от межсайтового скриптинга не является одношаговым процессом. Лучший способ защитить React-приложения от XSS-атак — это предотвратить их на ранних этапах кодовой базы. Вы можете составить список рекомендаций для своих коллег.

Вот мой список:

  1. Используйте dangerousSetHTML и createRef в очень специфических случаях.
  2. Не мутируйте DOM напрямую, как мы можем сделать это с помощью React.
  3. Используйте функциональность React вместо написания личных приемов. Читайте документацию.
  4. Проверяйте все данные, которые у вас есть, и данные о доходах (от пользователя и от API).
  5. Не создавайте свои личные библиотеки санации, выбирайте лучшие среди других библиотек от проверенных разработчиков.

Оцените статью
devanswers.ru
Добавить комментарий