Безопасное хранение конфигураций

Конфигурация Kepler.gl представляет собой сериализованный JSON-объект, описывающий состояние карты: слои, датасеты, стили визуализации, фильтры, взаимодействия и параметры камеры. В типичном приложении этот объект включает разделы visState, mapState, uiState и interactionConfig. Именно эта структура чаще всего сохраняется, передаётся между клиентом и сервером и восстанавливается при загрузке карты.

Любая система, работающая с пользовательскими конфигурациями визуализации, должна рассматривать JSON Kepler.gl как потенциально недоверенный вход. Даже если конфигурация генерируется внутри собственного фронтенда, она может быть изменена через DevTools, подменена в запросе или восстановлена из внешнего источника.

Основные угрозы:

  • внедрение вредоносных данных через конфигурацию слоя;
  • подмена API-ключей и URL источников данных;
  • XSS через поля, интерпретируемые UI-рендерером;
  • утечка приватных параметров фильтрации;
  • инъекции через пользовательские описания и tooltip-поля;
  • компрометация серверного хранилища конфигураций.

Структура конфигурации Kepler.gl как поверхность атаки

visState

Раздел visState содержит ключевую визуальную логику:

  • layers — описание слоёв (ScatterplotLayer, LineLayer, HexagonLayer и др.)
  • filters — фильтры по атрибутам данных
  • interactionConfig — настройки всплывающих окон и интерактивности

Наиболее чувствительные поля:

  • dataId — связывает слой с датасетом
  • column / field — определяют доступ к данным
  • color / strokeColor — могут включать выражения или вычисляемые значения
  • textLabel — потенциальный источник XSS при небезопасном рендеринге

Даже если Kepler.gl сам по себе экранирует часть данных, внешние обёртки или кастомные компоненты могут нарушить эту защиту.


mapState

mapState описывает положение и поведение карты:

  • координаты центра (latitude, longitude)
  • масштаб (zoom)
  • наклон и вращение (bearing, pitch)

С точки зрения безопасности этот раздел кажется нейтральным, но он может быть использован для:

  • fingerprinting пользователей через сохранённые геоданные;
  • передачи координат, содержащих чувствительную информацию (например, домашние адреса);
  • восстановления пользовательских маршрутов.

datasets

datasets содержат исходные данные или ссылки на них:

  • inline data (JSON/CSV)
  • URL источников
  • метаданные колонок

Наиболее критичный риск — внешние источники данных:

  • подмена URL на вредоносный endpoint;
  • утечка токенов через query-параметры;
  • загрузка данных с непроверенных доменов.

Принципы безопасного хранения конфигураций

Разделение конфигурации и секретов

Конфигурация Kepler.gl никогда не должна содержать:

  • API keys;
  • OAuth токены;
  • приватные URL с доступом по подписи;
  • серверные credentials.

Правильная модель:

  • конфигурация хранит только ссылки-идентификаторы;
  • секреты хранятся на сервере;
  • клиент получает данные через защищённый API-слой.

Нормализация и валидация JSON

Перед сохранением конфигурации необходимо выполнять строгую проверку структуры:

  • проверка типов (number, string, array);
  • ограничение глубины вложенности;
  • whitelist допустимых слоёв и фильтров;
  • удаление неизвестных полей.

Пример подхода:

  • разрешены только layers, filters, interactionConfig, mapState;
  • любые дополнительные ключи игнорируются или отклоняются;
  • строки проверяются на допустимые символы.

Особое внимание уделяется полям, которые могут интерпретироваться UI-слоем.


Санитизация пользовательских полей

Потенциально опасные поля:

  • label
  • tooltip
  • description
  • text
  • name

Даже если Kepler.gl не исполняет HTML напрямую, кастомные расширения могут это делать.

Стратегии защиты:

  • удаление HTML-тегов;
  • запрет <script>, jav * ascript:;
  • экранирование специальных символов;
  • ограничение длины строк.

Безопасное хранение на клиенте

localStorage и sessionStorage

Хранение полной конфигурации в localStorage удобно, но небезопасно:

  • доступно любому скрипту на странице;
  • уязвимо к XSS;
  • не имеет шифрования.

Допустимо использовать только для:

  • временных черновиков;
  • некритичных визуальных настроек.

Нельзя хранить:

  • токены доступа;
  • приватные датасеты;
  • пользовательские идентификаторы.

Шифрование на клиенте

Если требуется локальное хранение чувствительных конфигураций, применяется:

  • симметричное шифрование (например, AES-GCM через WebCrypto API);
  • ключ, производный от пароля пользователя;
  • хранение только зашифрованного blob.

Важно учитывать:

  • потеря ключа делает данные недоступными;
  • слабые пароли делают шифрование бессмысленным;
  • защита не спасает от XSS в момент расшифровки.

Безопасное серверное хранение

База данных конфигураций

При хранении Kepler.gl конфигураций на сервере применяются:

  • строгая JSON Schema валидация;
  • версионирование формата;
  • хранение метаданных отдельно от payload;
  • ограничение размера документа.

Рекомендуемая структура:

  • config_id
  • user_id
  • config_json
  • created_at, updated_at
  • schema_version

Подпись конфигурации

Для предотвращения подмены:

  • конфигурация подписывается HMAC;
  • сервер проверяет подпись при загрузке;
  • любые изменения инвалидируют подпись.

Это защищает от:

  • модификации URL датасетов;
  • изменения параметров слоёв;
  • внедрения дополнительных полей.

Контроль источников данных

Белый список источников

Все внешние датасеты должны проходить через allowlist:

  • разрешённые домены;
  • разрешённые API endpoints;
  • ограничение протоколов (только HTTPS).

Любая попытка загрузки данных с неизвестного источника должна блокироваться.


Проксирование данных

Безопасная архитектура:

  • клиент не обращается к внешним данным напрямую;
  • сервер проксирует запросы;
  • выполняет фильтрацию и очистку;
  • возвращает уже нормализованный dataset.

Это исключает:

  • утечку токенов;
  • подмену данных;
  • SSRF-риски через клиент.

Защита от XSS через конфигурацию Kepler.gl

Несмотря на то, что Kepler.gl ориентирован на визуализацию, риски XSS возникают в интеграциях:

Опасные сценарии:

  • кастомные tooltip-компоненты;
  • рендер HTML в описаниях слоёв;
  • использование сторонних библиотек для UI поверх Kepler.gl.

Меры защиты:

  • полный запрет innerHTML с пользовательскими данными;
  • использование React-рендеринга вместо HTML строк;
  • Content Security Policy с запретом inline script;
  • строгая фильтрация строковых полей.

Версионирование конфигураций

Kepler.gl активно развивается, и структура конфигурации меняется. Без версионирования возникают риски:

  • несовместимость слоёв;
  • ошибки при восстановлении состояния;
  • уязвимости старых форматов.

Рекомендуется:

  • хранить schemaVersion в каждом конфиге;
  • выполнять миграции на сервере;
  • отклонять неизвестные версии или переводить в safe-mode.

Ограничение возможностей конфигурации

Безопасная система должна ограничивать:

  • количество слоёв;
  • количество фильтров;
  • размер датасета;
  • глубину вложенности выражений.

Причины:

  • защита от DoS через сложные визуализации;
  • предотвращение утечки памяти;
  • контроль производительности клиента.

Принципы доверенной загрузки конфигурации

При восстановлении состояния карты:

  • JSON должен проходить валидацию до передачи в Kepler.gl reducer;
  • неизвестные поля удаляются;
  • данные нормализуются;
  • ошибки логируются без раскрытия чувствительной информации.

Reducer Kepler.gl должен рассматриваться как конечная точка, а не как вход без проверки.


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

В multi-tenant системах важно:

  • жёсткая привязка конфигурации к user_id;
  • проверка прав доступа при загрузке;
  • запрет доступа к чужим конфигурациям через прямые ссылки;
  • защита от IDOR (Insecure Direct Object Reference).

Логирование и аудит изменений

Для отслеживания безопасности:

  • фиксируются все изменения конфигураций;
  • сохраняются diff-версии JSON;
  • логируются источники загрузки;
  • отслеживаются подозрительные паттерны (массовые изменения, аномальные слои).

Это позволяет выявлять:

  • попытки инъекций;
  • автоматизированные атаки;
  • утечку данных через конфигурации.