Se ha denunciado esta presentación.
Utilizamos tu perfil de LinkedIn y tus datos de actividad para personalizar los anuncios y mostrarte publicidad más relevante. Puedes cambiar tus preferencias de publicidad en cualquier momento.

"Кластеры баз данных: делаем сложные вещи просто" Андрей Тихонов (Avito)

1.156 visualizaciones

Publicado el

Порой в процессе развития высоконагруженного проекта наступает момент, когда необходимо масштабирование. Возможно, ваш проект впервые упёрся в производительность железа (и таким образом перешёл в разряд высоконагруженных); возможно, это уже не первое масштабирование — не важно. Какие же проблемы могут возникнуть?

Во-первых, если вы увеличиваете количество бэкенд-серверов, и, соответственно, количество рабочих процессов, то с ростом количества одновременных клиентских подключений вырастают и накладные расходы на базах данных.
Во-вторых, достаточно быстро может кончиться ресурс in-memory баз данных. Потребуется создать (либо увеличить) кластер, а это каждый раз влечёт за собой необходимость модифицировать логику приложения.
В-третьих, чем больше серверов, тем больше вероятность, что один из них выйдет из строя. Поэтому неплохо задуматься о том, как обеспечить отказоустойчивость, а это, опять же, потребует модифицировать логику приложения.

В этом докладе я расскажу, как и какими инструментами можно легко решить все вышеперечисленные проблемы: уменьшить накладные расходы от большого количества подключений к базам данных, создать/модифицировать кластер БД прозрачно для приложения, а также прозрачно добавить устойчивость к падениям серверов БД.

Publicado en: Internet
  • Sé el primero en comentar

"Кластеры баз данных: делаем сложные вещи просто" Андрей Тихонов (Avito)

  1. 1. Кластеры баз данных: делаем сложные вещи просто Андрей Тихонов atikhonov@avito.ru Avito.ru DevOps
  2. 2. Содержание ● Как начинается Highload? ● Балансируем нагрузку на Backend ● Методы масштабирования БД ● Создаём кластер Redis/Memcached/Tarantool ● Создаём кластер PostgreSQL 2/47
  3. 3. Немножко статистики Avito ● 1M+ запросов в минуту к Backend ● 1Gb/s+ исходящий трафик (не считая картинки) ● 100K+ запросов в секунду на nginx-балансеры ● Терабайты или миллиарды картинок 3/47
  4. 4. Как начинается Highload?
  5. 5. Web-server Backend Database 5/47
  6. 6. Web-server Backend Database Cache 6/47
  7. 7. Web-server Backend * Database Cache 7/47
  8. 8. Web-server Backend * Database CacheStorage Queue 8/47
  9. 9. Web-server * Backend * Database * Cache *Storage * Queue * 9/47
  10. 10. Как работает Avito: 10/47
  11. 11. Балансируем нагрузку на Backend
  12. 12. 12/47 nginx.conf: ... location / { proxy_pass http://backend.local; } ...
  13. 13. 13/47 nginx.conf: ... upstream backend { server backend01.local:80; server backend02.local:80; server backend03.local:80; } ... location / { proxy_pass http://backend; } ...
  14. 14. Методы масштабирования БД
  15. 15. 15/47 Backend Database Read Write
  16. 16. 16/47 Backend Read Write MasterSlave Read Replication *репликация Master-Master здесь не рассматривается Репликация Master-Slave
  17. 17. 17/47 Backend Read Write Shard02Shard01 Read Write Шардирование
  18. 18. Создаём кластер Redis/Memcached/Tarantool
  19. 19. Проблемы 19/47 ● Установление подключения – долгая операция ● Малый срок жизни подключения ● Больше подключений – больше накладных расходов на сервере
  20. 20. Решаем проблемы с помощью Twemproxy* 20/47 ● Прозрачно проксирует на уровне протокола Memcached/Redis/Tarantool** ● Держит постоянное подключение к серверу ● Устанавливает мало подключений к серверу * см. также mcrouter, redis-proxy, redis-resharding-proxy, etc ** нужен патч
  21. 21. 21/47 twemproxy-redis-single.yml: alpha: listen: 127.0.0.1:22121 redis: true servers: - 127.0.0.1:6379:1
  22. 22. Шардируем с помощью Twemproxy 22/47 ● Автоматическое шардирование ● Поддерживает стойкое хэширование ● Автоматически группирует и конвейеризует запросы и ответы
  23. 23. 23/47 twemproxy-redis-shard.yml: beta: listen: 127.0.0.1:22122 redis: true distribution: ketama hash: murmur servers: - 127.0.0.1:6381:1 server1 - 127.0.0.1:6382:1 server2
  24. 24. Добавляем отказоустойчивость Redis-кластера 24/47 ● Master-Slave Replication средствами Redis
  25. 25. Master-Slave Replication средствами Redis 25/47 redis.conf (slave side): slaveof 192.168.10.1
  26. 26. Добавляем отказоустойчивость Redis-кластера 26/47 ● Master-Slave Replication средствами Redis
  27. 27. Добавляем отказоустойчивость Redis-кластера 27/47 ● Master-Slave Replication средствами Redis ● Автоматическое переключение в случае отказа мастера с помощью Redis Sentinel
  28. 28. Redis Sentinel 28/47 ● Мониторит состояние всех нод кластера ● Уведомляет об ошибках ● Автоматически промотирует slave до master в случае падения master ● Выступает в качестве провайдера конфигурации
  29. 29. Redis Sentinel 29/47 redis-sentinel.conf: sentinel monitor cluster01 192.168.10.1 6379 2 sentinel down-after-milliseconds cluster01 60000 sentinel failover-timeout cluster01 180000 sentinel parallel-syncs cluster01 1
  30. 30. Добавляем отказоустойчивость Redis-кластера 30/47 ● Master-Slave Replication средствами Redis ● Автоматическое переключение в случае отказа мастера с помощью Redis Sentinel
  31. 31. Добавляем отказоустойчивость Redis-кластера 31/47 ● Master-Slave Replication средствами Redis ● Автоматическое переключение в случае отказа мастера с помощью Redis Sentinel ● Прозрачное для клиента переключение с помощью HAProxy
  32. 32. HAProxy 32/47 ● TCP-прокси ● Балансирует нагрузку разными алгоритмами – Round-robin, least connections, first available, param* hash ● Primary/backup группы backend-серверов ● Различные способы проверки доступности серверов – TCP connect, protocol* check, TCP send-expect
  33. 33. HAProxy 33/47 haproxy-redis.conf: listen redis-cluster bind *:16379 option tcp-check balance roundrobin tcp-check send PINGrn tcp-check expect string +PONG tcp-check send info replicationrn tcp-check expect string role:master tcp-check send QUITrn tcp-check expect string +OK server redis01 192.168.10.1:6379 check port 6379 check inter 2s server redis02 192.168.10.2:6379 check port 6379 check inter 2s
  34. 34. Добавляем отказоустойчивость Redis-кластера 34/47 ● Master-Slave Replication средствами Redis ● Автоматическое переключение в случае отказа мастера с помощью Redis Sentinel ● Прозрачное для клиента переключение с помощью HAProxy
  35. 35. 35/47
  36. 36. Создаём кластер PostgreSQL
  37. 37. Проблемы 37/47 ● Одно подключение – один процесс, создание процесса – дорогостоящая операция ● План запросов и т. п. кэшируется внутри процесса, новое подключение – пустой кэш ● Малый срок жизни подключения ● Больше подключений – больше накладных расходов на сервере
  38. 38. Решаем проблемы с помощью PgBouncer* 38/47 ● Прозрачно проксирует на уровне протокола PgSQL ● Держит постоянное подключение к серверу ● Выполняет запросы до и после подключения ● Мультиплексирует клиентские подключения в трёх режимах: session, transaction, statement pooling * см. также PgPool
  39. 39. Решаем проблемы с помощью PgBouncer 39/47 pgbouncer.ini: [databases] main = host=db-main pool_size=5 connect_query= 'select prepare_statements_and_stuff()' [pgbouncer] pool_mode = transaction max_client_conn = 1024
  40. 40. Синхронная и асинхронная репликация 40/47 Синхронная: ● Надёжная ● Медленная Асинхронная: ● Быстрая ● Теряет ACID, так как слейвы отстают
  41. 41. Физическая и логическая репликация 41/47 Физическая: ● Полная копия всех данных ● Загружает I/O Логическая: ● Можно выбирать, какие данные копировать ● Загружает CPU
  42. 42. Создаём MSR-кластер 42/47 1 master, 1 slave: ● Распределяем нагрузку на чтение ● Нет отказоустойчивости 1 master, 2+ slave: ● Можем выдержать падение мастера
  43. 43. Создаём отдельную реплику для индексации 43/47 ● Логическая репликация: – Не вымывается кеш на мастере – Копируются только нужные данные ● Данные умещаются в RAM – нет медленного I/O
  44. 44. 44/47
  45. 45. Шардируем с помощью PL/Proxy* 45/47 ● Языковое расширение PostgreSQL ● Устанавливается на одной прокси-ноде ● Вся логика шардирования описывается в хранимых процедурах PostgreSQL ● Можно реализовать поддержку шард с MSR * см. также Citus
  46. 46. 46/47
  47. 47. Подведём итоги 47/47 ● Много кратковременных подключений к серверу – плохо, используем прокси ● Нужна отказоустойчивость – используем Master-Slave Replication, делаем несколько слейвов ● Слейвы должны быть не слабее мастера ● Данные не умещаются на одном сервере – шардируем на несколько серверов ● Все эти подходы можно комбинировать

×