Как сэкономить место на диске, управляя временем: проблемы администрирования Apache Kafka на примере Booking.com

Big Data, Большие данные, обработка данных, Kafka, администрирование, архитектура

В продолжении серии статей по докладу Александра Миронова из Booking.com, который был представлен 23 января 2020 года на зимнем Kafka-митапе Avito.Tech, сегодня мы рассмотрим некоторые проблемы администрирования Apache Kafka, с которыми можно столкнуться на практике. Читайте в этом материале, как не допустить разрастание топика, правильно задав параметр CreateTime.

Что делать, если Apache Kafka вдруг стала поглощать слишком много места на диске

Как мы уже рассказывали, производительность Apache Kafka напрямую связана с hardware-ресурсами. В частности, эта Big Data система активно использует жесткий диск, сохраняя сообщения в долговременную ROM-память и считывая их оттуда. Поэтому администраторы Кафка-кластера постоянно наблюдают за объемом потребляемого места на жестком диске. Внезапное увеличение этого показателя сигнализирует о проблеме, которую нужно срочно решать. Именно с такой ситуацией столкнулись администраторы Big Data инфраструктуры в компании Booking.com, когда заметили, что один из Кафка-топиков, который обычно пишет не более пары десятков байт в секунду, вдруг стал занимать около 12 ТБ. Проверив конфигурационные настройки этого топика, инженеры запустили системную утилиту /kafka-run-class.sh kafka.tools.DumpLogSegments [1], чтобы распечатать сообщения прямо из лог-файлов и проверить правильность индексов для журналов [2].

В результате было выявлено, что у самой первой записи (сегмента) этого злосчастного топика задано некорректное значение временного штампа (timestamp): параметр CreateTime установлен в будущую дату (10 ноября 2021 года). Это означает, что данный лог не будет очищен до тех пор, пока не наступит указанная дата. За установку этого параметра отвечает свойство message.timestamp.difference.max.ms – максимально допустимая разница между отметкой времени, когда брокер получает сообщение, и отметкой времени, указанной в сообщении. Если message.timestamp.type=CreateTime, сообщение будет отклонено, если разница во времени превышает этот порог. Эта конфигурация игнорируется, если message.timestamp.type=LogAppendTime [3].

CreateTime и message.timestamp.difference.max.ms: конфигурирование топиков Кафка

Проясним подробнее важность параметра CreateTime для свойства message.timestamp.type – если он задан, то справедливы следующие выводы по его использованию [4]:

  • timestamp во временном индексе возьмется из времени запроса клиента Kafka;
  • при следующей записи индекса необходимо убедиться, что ее временная метка больше предыдущей, в противном случае ее следует игнорировать;
  • новая запись временного индекса будет сгенерирована на основе предыдущей временной метки и планировщика, поэтому весь файл временного индекса будет полностью испорчен, даже если там присутствует всего 1 некорректная будущая дата;
  • политика хранения на основе временных меток (timestamp-basedretention policy) не удаляет остальные сегменты, если не удаляется самый первый, поэтому сохраняемый объем топика продолжает увеличиваться.

Таким образом, CreateTime влияет на брокера Kafka следующим образом [4]:

  • невозможно освободить память, поскольку условие удаления сегмента всегда ложно;
  • нет показателей для отслеживания некорректной метки времени, до тех пор, пока администратор Big Data не получит предупреждение о нехватке места в хранилище;
  • в Kafka нет конфигурации для отклонения данных с некорректной меткой времени;
  • не так-то просто остановить запрос Kafka, включая некорректный timestamp, если нет возможности идентифицировать клиента;
  • даже если некорректный timestamp составляет всего лишь пару часов будущего времени, политика хранения на основе времени по-прежнему будет работать после этой задержки, но любая функция поиска, основанная на метке времени, пропустит нужные данные за эти часы.

Параметр CreateTime также отражается и на клиенте Kafka [4]:

  • в случае последовательного получения сообщений по порядку согласно метке времени, механизм потоковой передачи Kafka приведет к отсутствию некоторых данных;
  • аналогичным образом, ожидаемые данные будут отсутствовать, если клиент Kafka запрашивает их по метке времени.
CreateTime в Apache Kafka
Как работает параметр CreateTime в Apache Kafka

В Booking.com решить эту проблему помогла настройка message.timestamp.difference.max.ms, которая определяет максимальную разницу между локальным временем брокера и временем, который был передан pruducer’ом в параметре CreateTime. Если разница между этими значениями больше, чем заданный интервал (message.timestamp.difference.max.ms), то Kafka отклонит поступившее сообщение. Администраторы Big Data в Booking.com задали message.timestamp.difference.max.ms равным 24 часа и с тех пор не сталкивались с подобными проблемами [1]. Однако, по мере эксплуатации системы возникли другие баги, о которых мы расскажем завтра.

Как обеспечить эффективное использование Apache Kafka за счет грамотного администрирования для потоковой обработки больших данных в проектах цифровизации своего бизнеса, а также государственных и муниципальных предприятий, вы узнаете на специализированных курсах в нашем лицензированном учебном центре обучения и повышения квалификации для разработчиков, менеджеров, архитекторов, инженеров, администраторов, Data Scientist’ов и аналитиков Big Data в Москве:

 

Источники

  1. https://habr.com/ru/company/avito/blog/486278/
  2. https://cwiki.apache.org/confluence/display/KAFKA/System+Tools
  3. https://docs.confluent.io/current/installation/configuration/topic-configs.html
  4. https://medium.com/@jiangtaoliu/a-kafka-pitfall-when-to-set-log-message-timestamp-type-to-createtime-c17846813ca3