Upload a file
  1. base64hub
  2. Other bases
  3. Z85

Z85 Encoder and Decoder (ZeroMQ)

Paste bytes as hex to get Z85, the Base85 variant ZeroMQ uses for CurveZMQ keys. Input must be a multiple of 4 bytes, as the spec requires, unless you allow a partial last block.

Free no sign-up, no limits Local nothing uploaded Spec-exact ZeroMQ RFC 32 test vectors pass Updated Oct 27, 2026
Input 0Bytes 0 BOutput 0

Processed in your browser. This page cannot send your data anywhere – how we know

How to encode and decode Z85

  1. Paste the bytes as hex into Input · Hex. Spaces, colons and 0x prefixes are accepted, so a hex dump pastes as is.
  2. Read the Z85 in Output · Z85 (ZeroMQ).
  3. If the byte count is not a multiple of 4, you get an error that names the count. Tick Allow partial last block (non-standard) only if both sides agree on that extension.
  4. To decode, click Z85 (ZeroMQ) → Hex in the direction toggle and paste the Z85 string. Set To to Base64 or Text for other views, or Save bytes for a binary file.

The spec test vectors

ZeroMQ’s Z85 specification (RFC 32 in the ZeroMQ RFC series) gives two test values. This tool reproduces both:

HexZ85
86 4F D2 6F B5 59 F7 5BHelloWorld
8E 0B DD 69 76 28 B9 1D 8F 24 55 87 EE 95 C5 B0 4D 48 96 3F 79 25 98 77 B4 9C D9 06 3A EA D3 B7JTKVSB%%)wK0E.X)V>+}o?pNmC{O&4W4b!Ni{Lh6

The first shows the block structure: 8 bytes, two blocks, ten characters. The second is a 32-byte key and its 40-character encoding, the size you see in CurveZMQ configuration.

Some edge values: four zero bytes are 00000, and four ff bytes are %nSc0. Z85 has no shortcut for zero blocks, so a run of zeros stays five characters per block.

Why ZeroMQ uses Z85

CurveZMQ keys are 32 random bytes. ZeroMQ needed a way to put them in configuration files, command lines and source code as plain strings. Z85 was designed for that:

  • It is 25% larger than the raw bytes, against 33% for Base64, so a 32-byte key is 40 characters instead of 44.
  • Its alphabet has no ", ', \ or backtick, so a key can go into a C, Python or shell string literal without escaping. It also avoids , and ;.
  • Digits and letters come first (0-9 a-z A-Z), followed by 23 punctuation characters: .-:+=^!/*?&<>()[]{}@%$#.

It still contains <, > and &, so Z85 inside XML or HTML needs escaping. In JSON it needs none.

Z85 in Python

Z85 and Python’s b85encode share the arithmetic and differ only in the alphabet, so a character translation converts one into the other:

import base64

B85 = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz!#$%&()*+-;<=>?@^_`{|}~"
Z85 = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ.-:+=^!/*?&<>()[]{}@%$#"
TO_Z85 = str.maketrans(B85, Z85)
FROM_Z85 = str.maketrans(Z85, B85)

def z85encode(data: bytes) -> str:
    if len(data) % 4:
        raise ValueError("Z85 needs a multiple of 4 bytes")
    return base64.b85encode(data).decode().translate(TO_Z85)

def z85decode(text: str) -> bytes:
    return base64.b85decode(text.translate(FROM_Z85))

z85encode(bytes.fromhex("864FD26FB559F75B"))   # 'HelloWorld'

If you already depend on PyZMQ, zmq.utils.z85.encode and decode do the same. In C, libzmq has zmq_z85_encode and zmq_z85_decode. More Python byte handling is on the Python page.

Common problems

  • “Z85 encodes 4-byte blocks and the data has N bytes”. The input is not block-aligned. Check that you copied the whole key; a 32-byte key that shows 31 bytes lost a pair of hex digits.
  • “Z85 needs groups of 5 characters; N are left over”. The Z85 string was cut short or has extra characters. A CurveZMQ key must be exactly 40 characters.
  • The string decodes but the key does not work. It may be Ascii85 or Git Base85, which share the length rules but not the alphabet, so the same characters decode to different bytes. Try it on the Base85 page with From set to another variant.

FAQ

Why does Z85 require a multiple of 4 bytes?

The spec defines Z85 only for whole 4-byte blocks, so a decoder can rely on every 5 characters being 4 bytes. Data of another length has to be padded or framed by the application. Tick Allow partial last block (non-standard) to encode the tail Ascii85-style anyway.

How long is a Z85 CurveZMQ key?

40 characters. CurveZMQ public and secret keys are 32 bytes, and 32 / 4 × 5 = 40. That is the length zmq_curve_keypair() returns, plus a terminating null in C.

Is Z85 the same as Ascii85?

Same arithmetic, different alphabet. Both write 4 bytes as 5 base-85 digits, but Z85 orders digits and letters first and avoids quotes and backslashes, and it has no z shortcut or <~ ~> delimiters.

How do I encode Z85 in Python?

The standard library has no Z85, but base64.b85encode uses the same arithmetic, so translating its output alphabet gives Z85. The snippet on this page does that. PyZMQ also ships zmq.utils.z85.