# crypto.sha256 `sha256(utf8Encode("abc"))` is the 32 bytes `ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad` (print them with `hexEncode`). This is SHA-256 exactly as FIPS 180-4 defines it. Bytes in and out are lists of integers 0 to 255, as everywhere in the registry (see `encoding.hex`); hash text by encoding it with `encoding.utf8` first, so all three languages hash the same bytes. The TypeScript implementation is plain code with no `node:crypto` and no `crypto.subtle`, so it runs unchanged in a browser, in Node and in a worker, synchronously (`crypto.subtle.digest` is asynchronous and only exists in secure contexts). The Python implementation uses the standard library's `hashlib`, and the Rust one is written out with the standard library only. All three are checked against the same vectors. A hash is not a password hash: a single SHA-256 of a password can be guessed billions of times a second. Store passwords with `auth.password-hash`, which uses PBKDF2 with a salt and many iterations. A hash is not a MAC either: to prove a message came from someone holding a key, use `crypto.hmac-sha256` (prefixing the key and hashing is open to length extension). The digests in the vectors are the published ones: "abc" and the 448-bit message from the NIST example values for FIPS 180-4 (SHA256.pdf), the empty string, the pangram, and messages of 55, 56, 64 and 119 bytes, which sit on either side of the points where the padding needs a second block. Source: FIPS 180-4, Secure Hash Standard, section 6.2 (https://csrc.nist.gov/pubs/fips/180-4/upd1/final) and the NIST cryptographic standards example values (https://csrc.nist.gov/projects/cryptographic-standards-and-guidelines/example-values).