Шардирование и зачем оно нужно при росте данных

6 апреля 2026 г.
Евгений Левашов2.png
Евгений Левашов
Автор статьи
6.jpg

Когда таблица вырастает до сотен миллионов строк, привычные методы оптимизации — индексы, кэширование, партиционирование — перестают справляться. Запросы замедляются, запись начинает конкурировать с чтением за ресурсы дисковой подсистемы, а наращивать мощность одного сервера становится всё дороже. В какой-то момент приходит мысль о горизонтальном масштабировании: разделить данные между несколькими независимыми узлами так, чтобы каждый обрабатывал только свою часть.

Именно этим занимается шардирование. В этой статье разберём, как оно устроено, чем отличается от репликации и партиционирования, какие стратегии распределения данных существуют и как шардирование реализовано в Tarantool.

кленов2.jpeg

Статья подготовлена вместе с экспертом

Александр Кленов, руководитель команды

Что такое шардирование

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

Ключ шардирования (shard key) — это столбец или группа столбцов, которые определяют, на какой шард попадёт запись. Для таблицы заказов таким ключом может быть user_id. Неудачный выбор ключа приводит к неравномерному распределению данных: один шард оказывается перегружен, остальные простаивают.

Шардирование становится необходимым, когда один сервер достигает предела производительности. Признаки этого хорошо узнаваемы: индексы таблиц перестают помещаться в оперативную память и СУБД переходит к дисковым операциям, параллельные запросы на чтение и запись конкурируют за I/O, а резервное копирование создаёт заметную нагрузку на production.

Вертикальное масштабирование — наращивание CPU, RAM, дисков — имеет физический потолок и растущую стоимость: сервер с 512 Гб RAM обходится не в два, а в 3–4 раза дороже сервера с 256 Гб. Горизонтальное масштабирование через шардирование снимает привязку к одному узлу, и каждый новый шард увеличивает одновременно и ёмкость, и пропускную способность кластера.

Партиционирование vs шардирование: в чём разница

Партиционирование и шардирование часто путают, хотя это разные механизмы. Партиционирование — разбиение таблицы на логические секции внутри одного сервера: данные по-прежнему хранятся в одной СУБД, но физически разнесены по отдельным файлам или табличным пространствам. Это ускоряет запросы за счёт сканирования только нужной секции, но не решает проблему предела мощности одной машины.

Шардирование идёт дальше и распределяет данные между физически разными серверами. Каждый шард представляет собой самостоятельный экземпляр СУБД со своей оперативной памятью, процессорами и дисками. Партиционирование масштабирует работу с данными внутри одного узла, шардирование — между узлами.

На практике эти подходы часто комбинируют: внутри каждого шарда таблицы могут быть дополнительно партиционированы. Например, шард хранит заказы пользователей с ID от 1 до 1 000 000, а внутри шарда те же заказы партиционированы по месяцам. Такой двухуровневый подход даёт и горизонтальную масштабируемость, и быструю работу с временными срезами данных.

Репликация vs шардирование

Репликация и шардирование решают разные задачи масштабирования, хотя на практике их часто применяют совместно.

  • Репликация создаёт полные копии базы данных на нескольких серверах. Шардирование разделяет данные на фрагменты, каждый из которых хранится на отдельном узле.
  • Репликация масштабирует чтение: запросы распределяются между копиями, но каждая копия содержит весь объём данных. Если база занимает 2 Тб, каждая реплика тоже требует 2 Тб хранилища. Шардирование масштабирует и чтение, и запись, потому что каждый узел обрабатывает только свою часть данных, а суммарная пропускная способность растёт с добавлением новых узлов.

В продакшн-системах подходы комбинируют: каждый шард реплицируется для отказоустойчивости. Кластер с тремя шардами и двумя репликами на каждый шард состоит из девяти узлов — три набора данных, каждый в трёх копиях. В Tarantool такую комбинацию реализует связка vshard, который распределяет виртуальные бакеты по реплика-сетам, со встроенным механизмом репликации, поддерживающим синхронный и асинхронный режимы. Синхронная репликация гарантирует, что данные записаны на кворум реплик до подтверждения транзакции.

Основные стратегии шардирования

Выбор стратегии определяет, как именно данные распределяются по шардам, и у каждого подхода свои компромиссы между простотой, равномерностью распределения и гибкостью.

Range-Based Sharding. Данные делятся по диапазонам значений ключа шардирования: пользователи с ID 1–1 000 000 попадают на первый шард, 1 000 001–2 000 000 на второй. Подход простой и предсказуемый, диапазонные запросы выполняются эффективно, потому что связанные записи лежат рядом. Но если новые записи концентрируются в одном диапазоне, последний шард окажется перегружен, поэтому для данных с неравномерным распределением ключа этот метод не подходит.

Hash-Based Sharding. Значение ключа пропускается через хеш-функцию, результат определяет номер шарда по формуле shard_id = hash(key) mod N, где N — количество шардов. Метод обеспечивает равномерное распределение и балансировку нагрузки, но при изменении числа шардов приходится перераспределять значительную часть данных, потому что изменение N в формуле меняет привязку почти всех ключей.

Consistent Hashing (Hash Ring). Шарды и ключи данных размещаются на виртуальном кольце хеш-значений, и каждый ключ попадает на ближайший по часовой стрелке узел. Главное преимущество перед классическим hash-шардированием в том, что при добавлении нового узла перемещается только около 1/N данных, а не почти весь объём. Виртуальные узлы (vnodes) обеспечивают равномерность: каждый физический сервер представлен несколькими точками на кольце. Диапазонные запросы этот подход не поддерживает, поскольку данные распределяются по хешу, а не по порядку значений.

Lookup Table (Directory-Based). Отдельный сервис хранит маппинг: какой ключ на каком шарде. Каждый запрос сначала обращается к справочнику, получает адрес нужного шарда и только потом идёт за данными, что даёт максимальную гибкость: данные можно перемещать между шардами без изменения логики приложения. Но справочник при этом становится единой точкой отказа и потенциальным узким местом, поэтому его кэшируют и реплицируют.

Как устроено шардирование в Tarantool

Tarantool реализует шардирование через модуль vshard, который использует подход виртуальных бакетов на основе консистентного хеширования. Весь датасет делится на фиксированное число виртуальных бакетов — по умолчанию их 3 000 (значение DEFAULT_BUCKET_COUNT в конфигурации vshard). Для крупных кластеров документация vshard рекомендует увеличивать это число до 30 000+ из расчёта 100–1 000 бакетов на каждый планируемый узел. Количество бакетов задаётся при инициализации кластера и не меняется в рантайме, поэтому значение закладывают с запасом на рост.

Архитектура Router и Storage

Кластер vshard состоит из двух типов компонентов. Router — stateless-маршрутизатор, который принимает запросы от приложения и направляет их на нужный шард, кэширует таблицу маршрутизации «бакет → реплика-сет» и обновляет её в фоне через специальный файбер (discovery fiber). Количество роутеров не ограничено, их добавляют при нехватке пропускной способности.

Storage — узел, который хранит подмножество бакетов. Несколько Storage-инстансов образуют реплика-сет (шард): один master принимает запросы на чтение и запись, остальные реплики обслуживают только чтение, рекомендуемый фактор избыточности составляет три копии данных. Серверная маршрутизация (server-side routing) принципиально отличает Tarantool от Redis Cluster, где маршрутизация реализована на стороне клиента: приложение обращается к любому роутеру, а тот прозрачно перенаправляет запрос на нужный Storage.

Ребалансировка без простоя

При добавлении нового реплика-сета ребалансировщик vshard автоматически перемещает часть бакетов на новый узел. Процесс работает в фоне с интервалом 10 секунд: ребалансировщик опрашивает все узлы, вычисляет эталонное распределение с учётом весов и запускает миграцию при дисбалансе свыше 1%. Во время миграции бакет в состоянии SENDING продолжает обслуживать запросы на чтение, кластер не останавливается. Нужно учитывать, что ребалансировка создаёт дополнительную нагрузку на I/O и сеть, что может снижать пропускную способность операций записи на время миграции.

Failover и отказоустойчивость

Router поддерживает горячие соединения с каждой репликой и при недоступности master-узла автоматически перенаправляет запросы на чтение к реплике. Для stateful failover используется внешний координатор — etcd или отдельный Tarantool-инстанс (stateboard), который отслеживает состояние кластера и назначает нового мастера.

Производительность

Tarantool хранит данные в оперативной памяти (движок memtx), что обеспечивает до 1 млн простых операций (get/put) в секунду на одном CPU-ядре по результатам бенчмарка на AWS (документация Tarantool). Для задач, где объём данных превышает доступную RAM, предусмотрен дисковый движок Vinyl, и оба движка работают в одном инстансе: горячие данные хранятся в памяти, холодные на диске. Реальная производительность зависит от профиля нагрузки: сложные запросы с Lua-обработкой дают меньшие цифры, чем синтетические тесты на простых операциях.

Сравнение подходов к шардированию

Характеристика Tarantool vshard Redis Cluster MongoDB Sharding
Виртуальные слоты Настраиваемое при создании кластера (3 000–300 000) Фиксированное: 16 384 Чанки (~64 Мб)
Маршрутизация Серверная (Router) Клиентская (smart client) Серверная (mongos)
Ребалансировка Полуавтоматическая перед удалением шарда, автоматическая при добавлении шарда Ручная / полуавтоматическая Автоматическая
ACID-транзакции Да, в пределах шарда Нет (multi-key ограничения) Да (с версии 4.0)
Хранение данных In-memory + диск Только in-memory Только диск (WiredTiger)
Бизнес-логика на сервере Lua / SQL Lua-скрипты JavaScript
Язык запросов SQL + Lua API Команды Redis MQL

Настраиваемое число бакетов — преимущество для крупных кластеров: в Redis Cluster число слотов фиксировано (16 384) и его нельзя изменить. Встроенный application server в Tarantool позволяет размещать бизнес-логику рядом с данными, сокращая сетевые задержки.

Шардирование на практике: кейсы компаний

Шардирование активно используется в production крупных российских сервисов.

VK. Tarantool с шардированием через vshard работает более чем в половине сервисов VK: Почта, Облако, Мой Мир. По данным инженерной команды VK (доклад на Highload++), профили пользователей обслуживаются 8 серверами с Tarantool вместо сотен серверов на традиционных СУБД.

Авито. Кластер из 16 шардов Tarantool заменил Redis-кэш в проекте Avito Smart Cache. Архитектура устроена так, что при падении одного шарда PostgreSQL принимает 1/16 запросов напрямую, остальные продолжают обслуживаться из Tarantool.

Альфа-Банк. Tarantool выбран для транзакционного ядра инвестиционного бизнеса: система агрегирует данные из разных источников, а сам проект лёг в основу продукта Tarantool Data Grid (TDG).

NtechLab. Система распознавания лиц FindFace обрабатывает видеопоток с камер менее чем за 0,5 секунды при миллионах изображений в базе данных.

Когда стоит внедрять шардирование

Шардирование увеличивает архитектурную сложность системы: появляется роутинг запросов, распределённые транзакции, мониторинг каждого шарда и механизмы ребалансировки. Внедрять его целесообразно, когда другие методы оптимизации уже исчерпаны:

  • вертикальное масштабирование достигло предела или стало экономически невыгодным;
  • партиционирование, кэширование и оптимизация запросов применены, но не решают проблему;
  • объём данных приближается к ёмкости одного сервера;
  • требования к пропускной способности записи превышают возможности одного узла.

Шардирование не подходит, если данные умещаются на одном сервере с запасом, проблема решается индексами или команда не готова поддерживать распределённую инфраструктуру.

Managed-решения снижают порог входа. Tarantool доступен как управляемый сервис (DBaaS) на платформе VK Cloud: развёртывание кластера с шардированием через vshard, автоматический failover и мониторинг без необходимости администрировать инфраструктуру вручную.

Ссылка скопирована
Поделиться

Почитать по теме

9.jpg
2 апреля

Column store базы данных: когда они быстрее реляционных решений

8.jpg
11 марта

Горячие и холодные данные в БД: что это и как снизить стоимость хранения

28.jpg
24 февраля

Реляционные vs нереляционные БД: как сделать правильный выбор