Сообщение об ошибке
TypeError: Cannot read properties of undefined (reading 'digest')
Также выводится как
- TypeError: Cannot read properties of undefined (reading 'importKey')
- TypeError: can't access property "digest", crypto.subtle is undefined
- TypeError: undefined is not an object (evaluating 'crypto.subtle.digest')
Это общая ошибка TypeError движка JavaScript. Chromium/V8: «Cannot read properties of undefined (reading 'digest')», Firefox: «can't access property \"digest\", crypto.subtle is undefined», Safari/WebKit: «undefined is not an object (evaluating 'crypto.subtle.digest')». Имя метода зависит от первого вызова (`importKey`, `sign`, `generateKey`…).
WebCrypto — window.crypto.subtle is undefined outside a secure context (Chromium / Firefox / WebKit)
Что это означает
На этой странице нет `crypto.subtle`, поэтому первый же вызов через него завершается общей ошибкой TypeError про «undefined». Браузеры предоставляют `SubtleCrypto` только в безопасных контекстах: на страницах, загруженных по HTTPS, с `http://localhost` / `127.0.0.1` или по URL `file:`. Один и тот же код работает на вашей машине через localhost и ломается, как только страницу открывают по обычному HTTP под другим именем хоста или по IP-адресу. `crypto.getRandomValues` при этом продолжает работать, поэтому сбой выглядит выборочным.
Почему это происходит
Страница загружается по обычному HTTP
частоStaging-хосты, инструменты в интрасети и превью-окружения без TLS не считаются безопасными контекстами. По спецификации все возможности WebCrypto там исчезают.
Сервер разработки открыт по адресу в локальной сети
часто`http://localhost:5173` считается безопасным, а `http://192.168.1.20:5173` (проверка на телефоне) — нет. Код, который работал при разработке, на устройстве даёт сбой.
Небезопасный фрейм или WebView
иногдаБезопасная страница, встроенная в родительский фрейм `http:`, или WebView, который загружает локальное содержимое по собственной небезопасной схеме, тоже не считаются безопасным контекстом.
Как исправить
- 1.
Проверяйте контекст и выводите понятное сообщение об ошибке
Перед использованием WebCrypto проверяйте `window.isSecureContext`. Не переключайтесь молча на криптографический полифил на JavaScript: без TLS целостность самой страницы всё равно не гарантирована.
js if (!window.isSecureContext || !globalThis.crypto?.subtle) { throw new Error("WebCrypto needs HTTPS (or http://localhost). Current origin: " + location.origin); } const digest = await crypto.subtle.digest("SHA-256", data); - 2.
Отдавайте страницу по HTTPS
Используйте TLS во всех окружениях, включая серверы разработки, которые вы открываете с других устройств; инструменты вроде mkcert создают локально доверенные сертификаты.
bash # Local HTTPS for a dev server reachable from other devices mkcert -install mkcert dev.example.test 192.168.1.20 localhost # Vite: server.https = { key: fs.readFileSync("dev.example.test+2-key.pem"), cert: fs.readFileSync("dev.example.test+2.pem") }
Связанные ошибки
DataError: Data provided to an operation does not meet requirementsWebCrypto crypto.subtle.importKeyTypeError: Failed to execute 'importKey' on 'SubtleCrypto': The provided value…WebCrypto SubtleCrypto.importKeySecurityError: The relying party ID is not a registrable domain suffix of, nor…WebAuthn navigator.credentials.create() / get()