Python BLAKE2 Hash Code Example (Online Runner)

Python BLAKE2 hashing examples for BLAKE2b/BLAKE2s with keyed mode and digest length controls, matching the online tool.

Online calculator: use the site BLAKE2 text tool.

Calculation method

Use hashlib.blake2b (64-byte digest) or hashlib.blake2s (32-byte digest). Both accept:

  • digest_size: bytes of output (1–64 for BLAKE2b, 1–32 for BLAKE2s).
  • key: optional bytes for MAC mode (same max length as the digest size).

The code below mirrors the online tool: choose the variant, optional digest length, and optional key. It treats the key as UTF-8 text; if you need raw bytes, pass bytes directly. Keys longer than the max length will raise ValueError in hashlib.

Implementation notes

  • Package: built-in hashlib (no extra dependency).
  • Implementation: BLAKE2b defaults to 64-byte output, BLAKE2s to 32-byte output; digest_size lets you shorten them.
  • Notes: keyed BLAKE2 is a MAC (useful for authenticity) but the key length is limited to the digest size. For cryptographic verification of a secret key, prefer BLAKE2 with a key over raw hashes.
python
import hashlib
from typing import Literal, Optional


Variant = Literal["blake2b", "blake2s"]
DEFAULT_DIGEST_SIZE = {"blake2b": 64, "blake2s": 32}


def blake2_hasher(
    variant: Variant = "blake2b",
    digest_size: Optional[int] = None,
    key: Optional[str] = None,
    encoding: str = "utf-8",
):
    if variant not in ("blake2b", "blake2s"):
        raise ValueError("variant must be 'blake2b' or 'blake2s'")

    digest_size = digest_size or DEFAULT_DIGEST_SIZE[variant]
    key_bytes = key.encode(encoding) if key else None
    kwargs = {"digest_size": digest_size}
    if key_bytes is not None:
        kwargs["key"] = key_bytes

    factory = hashlib.blake2b if variant == "blake2b" else hashlib.blake2s
    return factory(**kwargs)


def blake2_text(
    text: str,
    variant: Variant = "blake2b",
    digest_size: Optional[int] = None,
    key: Optional[str] = None,
    encoding: str = "utf-8",
) -> str:
    hasher = blake2_hasher(variant, digest_size, key, encoding)
    hasher.update(text.encode(encoding))
    return hasher.hexdigest()

# Example usage
payload = "hello world"

print(blake2_text(payload))  # BLAKE2b with 64-byte digest
print(blake2_text(payload, variant="blake2s"))  # 32-byte digest
print(blake2_text(payload, variant="blake2b", digest_size=32))  # shorter digest
print(blake2_text(payload, key="secret-key"))  # keyed MAC mode

File hashing example

python
from pathlib import Path
from typing import Literal, Optional
import hashlib
import tempfile

Variant = Literal["blake2b", "blake2s"]
DEFAULT_DIGEST_SIZE = {"blake2b": 64, "blake2s": 32}


def blake2_hasher(
    variant: Variant = "blake2b",
    digest_size: Optional[int] = None,
    key: Optional[str] = None,
    encoding: str = "utf-8",
):
    digest_size = digest_size or DEFAULT_DIGEST_SIZE[variant]
    key_bytes = key.encode(encoding) if key else None
    kwargs = {"digest_size": digest_size}
    if key_bytes is not None:
        kwargs["key"] = key_bytes
    factory = hashlib.blake2b if variant == "blake2b" else hashlib.blake2s
    return factory(**kwargs)


def blake2_file(
    path: Path,
    variant: Variant = "blake2b",
    digest_size: Optional[int] = None,
    key: Optional[str] = None,
    chunk_size: int = 1024 * 1024,
) -> str:
    hasher = blake2_hasher(variant, digest_size, key)
    with path.open("rb") as handle:
        for chunk in iter(lambda: handle.read(chunk_size), b""):
            hasher.update(chunk)
    return hasher.hexdigest()


if __name__ == "__main__":
    with tempfile.TemporaryDirectory() as temp_dir:
        sample_path = Path(temp_dir) / "example.bin"
        sample_path.write_bytes(b"example payload\n")
        print(blake2_file(sample_path, variant="blake2b"))
        print(blake2_file(sample_path, variant="blake2s", key="secret-key"))

If you create files with echo, note it appends a newline by default. Use echo -n or include a \n byte to match this digest.

BLAKE2 file hashes are computed from the file bytes only. The filename or path is not included unless you explicitly hash it as part of the input.

When to use BLAKE2

BLAKE2 is fast and secure, and it supports keyed hashing for message authentication. Use BLAKE2b when you want a full-length 64-byte digest, or BLAKE2s for 32-byte outputs in constrained environments.

Test vectors

VariantInputExpected digest
BLAKE2b(empty string)786a02f742015903c6c6fd852552d272912f4740e15847618a86e217f71f5419d25e1031afee585313896444934eb04b903a685b1448b755d56f701afe9be2ce
BLAKE2babcba80a53f981c4d0d6a2797b69f12f6e94c212f14685ac4b74b12bb6fdbffa2d17d87c5392aab792dc252d5de4533cc9518d38aa8dbf1925ab92386edd4009923
BLAKE2s(empty string)69217a3079908094e11121d042354a7c1f55b6482ca1a51e1b250dfd1ed0eef9
BLAKE2sabc508c5e8c327c14e2e1a72ba34eeb452f37458b209ed63a294d999b4c86675982

Keyed vectors (key = secret):

VariantInputExpected digest
BLAKE2b(empty string)865aca2ba0b9b941352e4680e14f543d1af37f7a3479304262a5da8c97468d9fe22636bae941d9c7b83b93efc36e82177606c72a1c00af48bb182c69d1f1abc3
BLAKE2sabcd7d0d1441d31d042d6c1ef68ce5162e56f3b2a208de82b727b7c30c709b7bff2

Complete script (implementation + tests)

python
import hashlib
from typing import Literal, Optional

Variant = Literal["blake2b", "blake2s"]
DEFAULT_DIGEST_SIZE = {"blake2b": 64, "blake2s": 32}

TEST_VECTORS = [
    ("blake2b", "", None, "786a02f742015903c6c6fd852552d272912f4740e15847618a86e217f71f5419d25e1031afee585313896444934eb04b903a685b1448b755d56f701afe9be2ce"),
    ("blake2b", "abc", None, "ba80a53f981c4d0d6a2797b69f12f6e94c212f14685ac4b74b12bb6fdbffa2d17d87c5392aab792dc252d5de4533cc9518d38aa8dbf1925ab92386edd4009923"),
    ("blake2s", "", None, "69217a3079908094e11121d042354a7c1f55b6482ca1a51e1b250dfd1ed0eef9"),
    ("blake2s", "abc", None, "508c5e8c327c14e2e1a72ba34eeb452f37458b209ed63a294d999b4c86675982"),
    ("blake2b", "", "secret", "865aca2ba0b9b941352e4680e14f543d1af37f7a3479304262a5da8c97468d9fe22636bae941d9c7b83b93efc36e82177606c72a1c00af48bb182c69d1f1abc3"),
    ("blake2s", "abc", "secret", "d7d0d1441d31d042d6c1ef68ce5162e56f3b2a208de82b727b7c30c709b7bff2"),
]


def blake2_text(
    text: str,
    variant: Variant = "blake2b",
    digest_size: Optional[int] = None,
    key: Optional[str] = None,
    encoding: str = "utf-8",
) -> str:
    digest_size = digest_size or DEFAULT_DIGEST_SIZE[variant]
    key_bytes = key.encode(encoding) if key else None
    kwargs = {"digest_size": digest_size}
    if key_bytes is not None:
        kwargs["key"] = key_bytes
    factory = hashlib.blake2b if variant == "blake2b" else hashlib.blake2s
    hasher = factory(**kwargs)
    hasher.update(text.encode(encoding))
    return hasher.hexdigest()


def run_tests() -> None:
    for variant, text, key, expected in TEST_VECTORS:
        actual = blake2_text(text, variant=variant, key=key)
        assert actual == expected, f"{variant} mismatch for {text!r}: {actual} != {expected}"
    print("All BLAKE2 test vectors passed.")


if __name__ == "__main__":
    run_tests()