bytedance/deer-flow · error · ValueError

bad bech32 checksum in {value!r}

Error message

bad bech32 checksum in {value!r}

What it means

Bech32 strings end with a 6-character checksum derived from the hrp and data via the polymod function. The decoder recomputes it and requires the result to be exactly 1; otherwise the string is corrupt or mistyped and this ValueError is raised. This catches single-character typos and truncation that survived the charset check.

Source

Thrown at backend/app/channels/buzz_nostr.py:57

        chk = (chk & 0x1FFFFFF) << 5 ^ v
        for i in range(5):
            chk ^= gen[i] if ((b >> i) & 1) else 0
    return chk


def _bech32_decode(expected_hrp: str, value: str) -> bytes:
    if "1" not in value:
        raise ValueError(f"not bech32: {value!r}")
    hrp, data_part = value.rsplit("1", 1)
    if hrp != expected_hrp:
        raise ValueError(f"expected {expected_hrp!r} bech32, got {hrp!r}")
    try:
        data = [_BECH32_CHARSET.index(c) for c in data_part]
    except ValueError as exc:
        raise ValueError(f"invalid bech32 character in {value!r}") from exc
    hrp_expanded = [ord(c) >> 5 for c in hrp] + [0] + [ord(c) & 31 for c in hrp]
    if _bech32_polymod(hrp_expanded + data) != 1:
        raise ValueError(f"bad bech32 checksum in {value!r}")
    acc = bits = 0
    out = bytearray()
    for v in data[:-6]:
        acc = (acc << 5) | v
        bits += 5
        if bits >= 8:
            bits -= 8
            out.append((acc >> bits) & 0xFF)
    if len(out) != 32:
        raise ValueError(f"expected 32-byte payload in {value!r}")
    return bytes(out)


def _parse_32_bytes(value: str, bech_hrp: str) -> bytes:
    value = value.strip()
    if value.lower().startswith(f"{bech_hrp}1"):
        return _bech32_decode(bech_hrp, value.lower())
    try:

View on GitHub (pinned to 1dd6ba1acb)

Solutions

  1. Re-copy the complete key from its original source — checksum failures almost always mean transcription corruption.
  2. Paste as 64-char hex instead, which has no checksum to fail.
  3. Verify in an external Nostr tool (e.g. a key converter) that the key is valid before configuring it.
Defensive patterns

Strategy: validation

Validate before calling

def _polymod_ok(hrp: str, data_part: str) -> bool:
    # reuse the module's own decoder in a dry-run
    try:
        _bech32_decode(hrp, f'{hrp}1{data_part}')
        return True
    except ValueError:
        return False

Try / catch

try:
    parse_pubkey(user_value)
except ValueError as e:
    if 'checksum' in str(e):
        reject_with_hint('key corrupted in transit — re-copy it')
    raise

Prevention

When it happens

Trigger: A key whose data part was altered — one character changed, characters dropped or added, or the string truncated/extended — so the recomputed polymod checksum no longer equals 1. Common with manual transcription or partial clipboard copies.

Common situations: User retyped the key and made one typo; clipboard copied only the first N characters; a YAML editor 'smart-quoted' or trimmed part of the value; key from an incompatible bech32 variant (bech32m) where the checksum constant differs.

Related errors


AI-assisted analysis of bytedance/deer-flow@1dd6ba1acb (2026-08-14). Data as JSON: /api/errors/4ea8ae9a0f2efa3d. Report an issue: GitHub.