denoland/deno · error · ERR_CRYPTO_INVALID_DIGEST
ERR_CRYPTO_INVALID_DIGEST
ERR_CRYPTO_INVALID_DIGEST
Error message
Invalid digest: ${e} What it means
In hkdfSync (ext/node/polyfills/internal/crypto/hkdf.ts:186-190) the native op op_node_hkdf is wrapped in try/catch, and any failure is re-thrown as ERR_CRYPTO_INVALID_DIGEST with the original error embedded in the message. Note the asymmetry: the JS-side validateAlgorithm already filtered names not in crypto.getHashes(), so this site fires when a name passes that check but the native HKDF op still rejects it, or when the op fails for another reason (e.g. an unusable key handle). The async hkdf() wraps the same op failure into its callback as the error argument.
Source
Thrown at ext/node/polyfills/internal/crypto/hkdf.ts:189
salt: any,
info: any,
length: number,
) {
({ hash, key, salt, info, length } = validateParameters(
hash,
key,
salt,
info,
length,
));
hash = StringPrototypeToLowerCase(hash);
const okm = new Uint8Array(length);
try {
op_node_hkdf(hash, key[kHandle], salt, info, okm);
} catch (e) {
throw new ERR_CRYPTO_INVALID_DIGEST(e);
}
return TypedArrayPrototypeGetBuffer(okm);
}
let hashes: Set<string> | null = null;
function validateAlgorithm(algorithm: string) {
if (hashes === null) {
hashes = new SafeSet(getHashes());
}
if (!SetPrototypeHas(hashes, algorithm)) {
throw new ERR_CRYPTO_INVALID_DIGEST(algorithm);
}
}
return {
hkdf,View on GitHub (pinned to 9ad36f7a2c)
Solutions
- Use a mainstream HMAC digest for HKDF: sha256, sha384, or sha512.
- Catch by code and surface the embedded cause: if (e.code === 'ERR_CRYPTO_INVALID_DIGEST') inspect e.message for the wrapped op error.
- For the async crypto.hkdf(...), check the callback's err argument rather than expecting a throw.
- Verify the digest against a small known-answer vector at startup so unsupported digests fail early.
Example fix
// before
crypto.hkdfSync(digestFromConfig, ikm, salt, info, 32); // op rejects -> ERR_CRYPTO_INVALID_DIGEST(e)
// after
const digest = String(digestFromConfig).toLowerCase();
if (!['sha256', 'sha384', 'sha512'].includes(digest)) {
throw new Error(`unsupported HKDF digest: ${digestFromConfig}`);
}
crypto.hkdfSync(digest, ikm, salt, info, 32); Defensive patterns
Strategy: try-catch
Validate before calling
const SAFE = new Set(['sha256', 'sha384', 'sha512']);
if (!SAFE.has(String(digest).toLowerCase())) {
throw new Error(`hkdf digest '${digest}' is not in the supported set`);
}
crypto.hkdfSync(String(digest).toLowerCase(), ikm, salt, info, 32); Type guard
function isSafeHkdfDigest(name) {
return ['sha256', 'sha384', 'sha512'].includes(String(name).toLowerCase());
} Try / catch
try {
okm = crypto.hkdfSync(digest, ikm, salt, info, 32);
} catch (e) {
if (e.code === 'ERR_CRYPTO_INVALID_DIGEST') {
// e.message embeds the native op failure; fall back or surface clearly
return fallbackDerivation(digest, ikm, salt, info, 32);
}
throw e;
}
// async form: check the callback's err argument, same code Prevention
- Pin HKDF digests to sha256/sha384/sha512.
- For async crypto.hkdf, always handle the callback error - it never throws this directly.
- Run a known-answer HKDF test at startup to catch runtime digest mismatches early.
When it happens
Trigger: hkdfSync with a hash name that exists in getHashes() but is not usable for HKDF by the native implementation; passing a key whose [kHandle] is not a usable secret-key handle (a KeyObject of the wrong kind); runtime/version differences where the JS allowlist and the native op disagree on supported digests.
Common situations: Switching digest configurations from config files (e.g. 'blake2b-512', XOF names like 'shake256') that hash fine but fail inside the HKDF op; code that ran on one Node/Deno version and hits a native-op mismatch on another; feeding an unexpected KeyObject type through an abstraction layer.
Related errors
- ERR_OUT_OF_RANGE
- ERR_CRYPTO_INVALID_KEYLEN
- ERR_INVALID_ARG_TYPE
- ERR_CRYPTO_INVALID_DIGEST
- HKDF keys are not extractable
AI-assisted analysis of denoland/deno@9ad36f7a2c (2026-08-20).
Data as JSON: /api/errors/e8b2fe17f5c93dc0.
Report an issue: GitHub.