Web Crypto API (window.crypto.subtle) функционирует в
рамках политики безопасности браузера, и одной из ключевых систем
контроля является Content Security Policy (CSP). CSP определяет, какие
источники данных, скриптов и операций разрешены в контексте страницы, и
напрямую влияет на доступность криптографических возможностей.
Web Crypto API относится к встроенным браузерным возможностям и не
загружает внешние скрипты для выполнения криптографических операций.
Поэтому сама по себе она не блокируется стандартными директивами вроде
script-src или worker-src в большинстве
сценариев.
Однако CSP влияет на окружение, в котором Web Crypto API может использоваться, особенно в следующих аспектах:
eval, new Function,
динамическим кодомWeb Crypto API доступен только в безопасных контекстах. Это означает, что страница должна быть загружена через:
CSP косвенно усиливает это требование через директиву:
Content-Security-Policy: upgrade-insecure-requests
Она автоматически переводит HTTP-запросы в HTTPS, что критично для
криптографических операций, так как браузер может полностью отключить
crypto.subtle в небезопасном окружении.
Хотя Web Crypto API не требует специальных CSP-директив, его использование часто пересекается с ограничениями политики безопасности.
Наиболее важная директива при работе с криптографией в браузере.
Пример строгой политики:
Content-Security-Policy: script-src 'self'
В этом случае запрещается:
Это напрямую влияет на криптографические библиотеки, если они используют динамическое создание функций.
Может блокировать старые плагины и встроенные объекты. Для Web Crypto API влияние косвенное, но важно для безопасности окружения:
Content-Security-Policy: object-src 'none'
Криптографические операции часто выносятся в Web Workers для предотвращения блокировки UI.
Content-Security-Policy: worker-src 'self'
Если эта директива отсутствует или настроена строго, создание воркеров с криптографическими задачами может быть заблокировано.
Используется при отправке зашифрованных данных на сервер.
Content-Security-Policy: connect-src 'self'
Если криптографический модуль выполняет fetch или
XHR для передачи зашифрованных данных, эта директива
становится критичной.
Многие примеры работы с Web Crypto API используют inline-код:
<script>
crypto.subtle.digest("SHA-256", new TextEncoder().encode("data"))
.then(hash => console.log(hash));
</script>
При CSP:
script-src 'self'
такой код будет заблокирован.
Правильная архитектура требует вынесения логики:
<script src="crypto.js"></script>
и в crypto.js:
async function hashData(data) {
const encoded = new TextEncoder().encode(data);
const hashBuffer = await crypto.subtle.digest('SHA-256', encoded);
const hashArray = Array.from(new Uint8Array(hashBuffer));
return hashArray.map(b => b.toString(16).padStart(2, '0')).join('');
}
hashData('message').then(console.log);
Использование Web Crypto API внутри воркеров — распространённая практика при обработке больших данных (например, хэширование файлов).
Создание воркера:
const worker = new Worker('crypto-worker.js');
CSP:
worker-src 'self'
В crypto-worker.js:
self.onmess age = async (e) => {
const data = e.data;
const hash = await crypto.subtle.digest(
'SHA-256',
new TextEncoder().encode(data)
);
self.postMessage(hash);
};
Если CSP не разрешает worker-src, криптографическая
нагрузка может быть вынуждена выполняться в основном потоке, что
ухудшает производительность и стабильность интерфейса.
Многие библиотеки используют Web Crypto API как fallback, но также включают JS-реализации алгоритмов.
Пример библиотек:
Если CSP запрещает загрузку внешних ресурсов:
script-src 'self'
то подключение CDN-версий библиотек становится невозможным:
<script src="https://cdn.example.com/crypto.js"></script>
Также может блокироваться WASM-версия криптографии при отсутствии:
Content-Security-Policy: script-src 'self' 'wasm-unsafe-eval'
WebAssembly часто используется для ускорения криптографических алгоритмов (например, Argon2, bcrypt, scrypt).
CSP ограничивает выполнение WASM через:
Content-Security-Policy: script-src 'self' 'wasm-unsafe-eval'
Без этой директивы загрузка и выполнение WASM-модулей может быть полностью заблокировано, даже если Web Crypto API доступен.
Безопасная конфигурация для приложений, активно использующих криптографию:
Content-Security-Policy:
default-src 'self';
script-src 'self';
worker-src 'self';
connect-src 'self';
object-src 'none';
base-uri 'none';
Такая политика:
При нарушении политики безопасности типичные ошибки выглядят так:
Refused to execute inline scriptRefused to create a workerBlocked a frame with originContent Security Policy directive violatedПри этом Web Crypto API может быть полностью исправен, но его использование невозможно из-за окружения.
При использовании nonce:
script-src 'self' 'nonce-random123'
скрипты криптографических операций должны быть явно помечены:
<script nonce="random123">
crypto.subtle.digest('SHA-256', new TextEncoder().encode('data'));
</script>
Hash-based CSP:
script-src 'self' 'sha256-abc...'
Используется редко в криптографических приложениях, так как любые изменения кода ломают политику и блокируют выполнение даже безопасных операций.
Типичная структура:
Пример распределения ответственности:
UI → отправка данных → Worker → crypto.subtle → результат → UI
CSP гарантирует, что в этот поток нельзя внедрить сторонний код, даже при наличии XSS уязвимости частичного уровня.
Web Crypto API не требует специальных разрешений CSP, но полностью зависит от:
CSP не управляет криптографией напрямую, но определяет среду, в которой она становится возможной или недоступной.