Class Partitioning
This is a wire contract, not an implementation detail. A Java publisher and a Go consumer have to agree about where a key lands or ordering breaks silently across languages, so the hash is specified rather than borrowed: FNV-1a, 32-bit, over the key's UTF-8 bytes.
String.hashCode() was the obvious candidate and is the wrong one. It is stable
across Java versions but it is Java's, and reimplementing it in Go or Python to keep a fleet in
agreement is a strange thing to ask of anybody. FNV-1a is eight lines in any language and has
no library behind it.
The golden values in the test suite exist for exactly this reason: a port that produces different partitions is a port that reorders messages, and nothing else would catch it.
Changing the partition count is not free
Partition n for a key is a function of the count, so raising it moves most keys
somewhere new. During the change a key can have messages in two partitions at once, and their
relative order is not defined. There is no clever fix — consistent hashing reduces how many
keys move but does not stop it. Drain first, then change.
-
Method Summary
Modifier and TypeMethodDescriptionstatic intstatic intpartitionFor(String key, int partitions) static StringroutingKeyFor(int partition)
-
Method Details
-
hash
- Parameters:
key- the ordering key, such as a customer or account identifier- Returns:
- the FNV-1a 32-bit hash of its UTF-8 bytes
-
partitionFor
- Parameters:
key- the ordering keypartitions- how many partitions exist, at least 1- Returns:
- the partition this key belongs to, from 0 to
partitions - 1
-
routingKeyFor
- Parameters:
partition- partition number- Returns:
- the routing key it is bound with,
p0,p1and so on
-