Часть 1. Архитектура ClickHouse и что меняется в Kubernetes

MergeTree, куски и слияния, шарды против реплик, роль Keeper. Где stateful-природа ClickHouse конфликтует с моделью Kubernetes и почему вертикальное масштабирование стоит исчерпать до шардирования.
Опубликовано:

Прежде чем писать манифесты, нужно понимать, что именно вы разворачиваете. ClickHouse устроен иначе, чем привычные OLTP-базы, и половина проблем в Kubernetes растёт из попытки эксплуатировать его «как обычный stateless-деплоймент».

MergeTree: куски, гранулы, слияния

Основное семейство движков — MergeTree. Модель простая и жёсткая:

Отсюда сразу следуют два практических вывода, к которым мы вернёмся в частях про схему и вставку:

  1. Много мелких вставок — это яд. Каждая создаёт кусок, слияния не успевают, вы получаете ошибку too many parts и деградацию.
  2. ORDER BY определяет производительность сильнее, чем что-либо ещё: он же порядок хранения, он же индекс, он же фактор сжатия.

Шард или реплика

Два принципиально разных способа «добавить узлов»:

Их комбинируют: например, 3 шарда × 2 реплики = 6 узлов.

  flowchart TD
    C["Клиент"] --> D["Distributed-таблица<br/>(объединяет шарды)"]
    subgraph S1["Шард 1"]
        R11[("Реплика A")] <--> R12[("Реплика B")]
    end
    subgraph S2["Шард 2"]
        R21[("Реплика A")] <--> R22[("Реплика B")]
    end
    D --> S1
    D --> S2
    S1 -.координация.-> K["ClickHouse Keeper<br/>(кворум из 3 узлов)"]
    S2 -.координация.-> K

Реплики договариваются между собой не напрямую, а через ClickHouse Keeper — он хранит метаданные репликации, очередь задач и обеспечивает консенсус (Raft). Keeper — это встроенная замена ZooKeeper, менее прожорливая и рекомендуемая по умолчанию. Без Keeper ReplicatedMergeTree не работает вовсе.

Идентичность узла в топологии задаётся макросами {shard} и {replica} — они видны в system.macros и подставляются в путь реплики при создании таблицы. Оператор проставляет их за вас.

Сначала вертикаль, потом шардирование

Главная ошибка при переезде в Kubernetes — сразу нарезать много маленьких подов, по аналогии со stateless-сервисами. ClickHouse так не любит: он рассчитан на большие машины и хорошо утилизирует много ядер и памяти в одном процессе. Один узел на 32 ядра и 128 ГиБ памяти на аналитической нагрузке обычно обгоняет четыре узла по 8 ядер и 32 ГиБ — при этом он проще в эксплуатации.

Шардирование добавляет постоянную сложность: распределённые запросы, ключ шардирования, перекосы, ребалансировка при добавлении шарда (её придётся делать руками — автоматического решардинга нет). Поэтому сначала выжимайте вертикаль.

Разумные сигналы, что реплик уже мало и пора в шарды:

До этих порогов — добавляйте ядра, память и реплики для чтения.

Что меняется именно в Kubernetes

ClickHouse — stateful, и это меняет правила:

Именно поэтому в проде почти всегда используют оператор: он умеет генерировать конфиги, StatefulSet’ы, сервисы, PDB и связывать кластер с Keeper. К операторам переходим в следующей части.

Чего ClickHouse не делает

Чтобы не строить ожиданий, которые он не оправдает:

Если нагрузка — это аналитика по большим потокам событий, ClickHouse блестящ. Если это «обычная база для приложения» — вы берёте не тот инструмент.


Дальше: Часть 2. Операторы: официальный от ClickHouse Inc. и Altinity.

Начать поиск

Введите ключевые слова для поиска статей

↑↓
ESC
⌘K Горячая клавиша