What We Learned
blake3-wasm has exactly two published versions: 2.1.5 and 3.0.0. Version 3.0.0 introduced a mandatoryawait load() call before any hashing — the WASM module loads asynchronously. Version 2.1.5 loads the WASM module synchronously at import time.
This seemingly minor API difference has cascading consequences:
-
2.1.5 (sync):
fingerprint()andverify()are synchronous functions. Callers use them inline:const fp = fingerprint(unit). Batch fingerprinting is a simple loop. The SPUH header can be computed in the same synchronous pipeline as encoding. -
3.0.0 (async): Every function that touches Blake3 becomes async. Callers need
await. Batch fingerprinting requiresPromise.all()or sequentialawaitin a loop. The entirestratt publishpipeline becomes async. Test setup needsbeforeAll(async () => { await load(); }).
The Decision
Pin toblake3-wasm@2.1.5 (exact version, no caret, no tilde) per DR-05. The sync API is the right default for a hashing library — the operation is CPU-bound, not I/O-bound. The async ceremony in 3.0.0 is an artefact of the WASM loading mechanism, not a performance benefit.
The FALLBACK.md documents the SHA-256 migration path if blake3-wasm is abandoned. Web Crypto’s crypto.subtle.digest() IS async, so the fallback path would require the API to become async — but that’s a bridge to cross only if needed, and it would be a major version bump.