Partition для сообщения выбирается на стороне продьюсера по алгоритму partitioner. Если у сообщения есть ключ, берётся хэш ключа и по модулю числа партиций вычисляется номер partition; это гарантирует, что сообщения с одинаковым ключом попадут в одну и ту же partition. Если ключ отсутствует, используется алгоритм равномерного распределения (round-robin/sticky) или логика из пользовательского partitioner-а.
Важно понимать, что выбор partition делает не брокер, а продьюсер, используя стратегию, заданную partitioner. Брокер лишь принимает уже «раскиданные» по партициям сообщения.
Алгоритм по умолчанию в Java-клиенте Kafka работает так:
1. Если в ProducerRecord явно указан номер partition, продьюсер использует именно его (предварительно проверив, что номер в допустимом диапазоне).
2. Если partition не указана, но задан ключ (key != null), рассчитывается хэш ключа (например, через key.hashCode()), берётся его абсолютное значение и по модулю количества партиций данного топика вычисляется номер partition. Так все сообщения с одинаковым ключом попадут в одну и ту же partition, что даёт упорядоченность по ключу.
3. Если и partition, и ключ не заданы, включается алгоритм равномерного распределения: в старых версиях это был простой round-robin, в новых клиентах используется sticky partitioner, который на короткое время «прилипает» к одной partition для эффективной пакетной отправки и затем переключается, сохраняя баланс нагрузки между партициями.
Такой подход позволяет управлять как балансировкой нагрузки (распределением сообщений между партициями), так и семантикой упорядоченности: все сообщения с одним и тем же ключом гарантированно обрабатываются в пределах одной partition в том порядке, в котором были записаны.
При необходимости разработчик может полностью переопределить эту логику, реализовав собственный класс Partitioner и указав его в конфигурации продьюсера. Тогда именно ваш код будет решать, в какую partition уйдёт каждое сообщение (например, по бизнес-правилам, по диапазонам значений ключа, по географии и т.п.).
Отметьте свой прогресс