Почему Kafka такая быстрая
Что проверяют
Знаете ли вы конкретные механизмы, а не лозунги про высокую пропускную способность. И понимаете ли, где скорость теряется на практике: в сервисе на Go настройки клиента решают больше, чем настройки брокера.
Как отвечать
Назвать четыре опоры:
- последовательная запись в лог. Данные дописываются в конец сегмента, без поиска места и без правки на месте, поэтому дисковая головка или контроллер работают в самом выгодном режиме;
- страничный кэш вместо своего. Брокер пишет в файл и полагается на кэш операционной системы: потребитель, идущий у хвоста лога, читает из памяти, не касаясь диска. Своей огромной кучи брокеру не нужно, значит нет и пауз сборщика на данных;
- отдача без лишних копирований. Сегмент уходит в сокет системным вызовом
sendfile, минуя пользовательское пространство. Оговорка, которая ценится: с TLS этот путь пропадает, шифровать приходится в юзерспейсе; - батчи на всех уровнях. Продюсер копит записи (
linger.ms,batch.size), сжимает пачку целиком, брокер кладёт её на диск как есть и отдаёт потребителю тоже пачкой. Плюс брокер почти не хранит состояния о потребителях: позиции лежат в служебном топике, доставка идёт по запросу самого клиента.
Про Go добавить своё: пропускная способность franz-go, sarama или обёртки над librdkafka упирается в те же батчи. Отправка по одному сообщению с ожиданием подтверждения даёт скорость сетевого round trip, а не скорость Kafka.
Где спотыкаются
Говорят, что Kafka быстрая, потому что держит данные в памяти. Она пишет на диск всегда, а выигрыш даёт последовательный доступ и страничный кэш поверх него.
Называют главным лекарством переход на SSD. Архитектура как раз терпима к обычным дискам, а упирается обычно в сеть, число партиций, подтверждение всеми репликами или в отсутствие батчинга у клиента.
Забывают про плату. Накопление батча увеличивает задержку, отставший потребитель читает с диска и вымывает страничный кэш у остальных, а лишние партиции удлиняют восстановление после падения брокера.