C.W.K.
Stream
Lesson 06 of 07 · published

Binary Protocols

~13 min · protocol, binary, msgpack, protobuf

Level 0Poller
0 XP0/60 lessons0/10 achievements
0/120 XP to next level120 XP to go0% complete

When JSON is too expensive

JSON is verbose, slow to parse, and unable to represent floats compactly. For high-frequency numerical data — game state at 60fps, market ticks at 100Hz, sensor streams — the JSON tax shows up as bandwidth costs and dropped frames. Two binary formats dominate: MessagePack (drop-in, schema-less) and Protocol Buffers (compact, schema-required).

MessagePack: JSON-shaped, smaller, faster

MessagePack encodes the same JSON-ish structures (objects, arrays, numbers, strings, booleans, null) into ~30% smaller binary frames with much faster parse. No schema definition needed. Reach for it first when JSON costs too much.

Protocol Buffers: schema-driven, smallest

Protobuf requires a .proto schema and code generation, but produces 60% smaller payloads with the fastest parse. Schemas double as documentation and version control. Worth the setup when your protocol stabilizes and the data volume justifies it.

Code

MessagePack on browser + Python·javascript
// Browser side, with msgpack-lite or msgpackr
import { encode, decode } from 'msgpackr';

ws.binaryType = 'arraybuffer';
ws.send(encode({ x: 150.5, y: 300.2, id: 42, flags: 0b0001 }));

ws.onmessage = (e) => {
  if (e.data instanceof ArrayBuffer) {
    const data = decode(new Uint8Array(e.data));
    applyState(data);
  }
};
Server side with msgpack·python
import msgpack
from fastapi import WebSocket

@app.websocket('/ws/binary')
async def binary(websocket: WebSocket):
    await websocket.accept()
    while True:
        raw = await websocket.receive_bytes()
        data = msgpack.unpackb(raw)
        result = process(data)
        await websocket.send_bytes(msgpack.packb(result))
Format comparison·text
| Format     | Size (typical) | Parse speed | Schema required |
| ---------- | -------------- | ----------- | --------------- |
| JSON       | baseline       | slowest     | no              |
| MessagePack| ~30% smaller   | fast        | no              |
| Protobuf   | ~60% smaller   | fastest     | yes (.proto)    |

External links

Exercise

Take a 50-field game-state dict and serialize it as JSON, MessagePack, and Protobuf. Measure: byte size, encode time, decode time, in JS and Python. Build a table; which one would you pick for 60fps multiplayer? Which for a once-per-minute notification?

Progress

Progress is local-only — sign in to sync across devices.
Spotted a bug or have feedback on this page?Report an Issue

Comments 0

🔔 Reply notifications (sign in)
Sign inPlease sign in to comment.

No comments yet — be the first.