Closed
Description
Version
v22.14.0
Platform
Linux ### 6.15.2-arch1-1 #1 SMP PREEMPT_DYNAMIC Tue, 10 Jun 2025 21:32:33 +0000 x86_64 GNU/Linux
Subsystem
crypto
What steps will reproduce the bug?
Try to hash anything using a variable length hash function (e.g. shake128), without any options you get an empty buffer/string.
How often does it reproduce? Is there a required condition?
Reproducible, but I haven't dissected the exact version the default changed. I known it is somewhere between v14.21.3 and v22.14.0 and yes I realize this is a very large window 😕
What is the expected behavior? Why is that the expected behavior?
shake128 should default to outputLength = 16 as in earlier Node.JS versions. Other variable-length (XOF) hashes should also default to sensible non-zero length.
I believe it is sane to expect the following assertion:
const {getHashes, createHash } = require('crypto');
assert.equal( 0 , getHashes().filter( h => !createHash(h).digest().length ).length )
What do you see instead?
getHashes().filter( h => !createHash(h).digest().length ) == [ 'shake128', 'shake256' ]
Additional information
- Node 12.8.0 introduced the
outputLength
option tocrypto.createHash
- In Node 14.21.3 and earlier, when the option is omitted, shake128 defaults to 16 bytes output
- In Node 22.14.0 and later, the default is zero, which results in empty hashes:
> require('crypto').createHash('shake128').update('test').digest()
<Buffer >
There are two issues here:
- It is not backward compatible, and unless I missed something this breaking change is not documented, which resulted in breaking our app when upgrading node
- In general, defaulting to null length by default is very countrer-intuitive