Pull to refresh

Comments 70

Подобная конфигурация (Master-Master + переключение трафика) не только защищает от простоев во время аварий, но и очень помогает при проведении любых работ с базой (установка апдейтов, переконфигурирование и т.п.) — без даунтайма для клиентов.
А как быть, если часть данных не успела синхронизироваться со вторым дата-центром? Понятно, что когда связь восстановится, данные синхронизируются, но что делать с критически важными данными?
Увы, это реалии жизни :-(. При аварийном рестарте mysql также могут потеряться отдельные транзакции, а ext2/3/4 — иногда при резете могут угробить метаданные и не автоматически не восстановиться.
Если для ваш супермегакритична каждая транзакция, то поможет полусинхронная репликация.
Ну, собственно, так я и думал =)
Но по опыту часто хватает возможностей асинхронной репликации же. Поэтому она так распространена, на ее базе строят графы серверов, активно дорабатывают технологию. Значит полезна :-)
Про MySQL NDB Cluster враки. Мы его в боевых условиях для социальной сети 5 лет назад уже использовали. Конечно, тупо перекинуть таблицы ALTER TABLE `bla` ENGINE=NDB и ожидать чуда не получится (однако с тех пор судя по анонсам проблемы с JOIN и многие другие успешно решили). Но если применить здравый смысл, понимать что у вас сетевой кластер (смотрите коммент под спойлером), хорошо проверить свои запросы — то отличная штука, которая позволяет перемолоть очень большой поток запросов.
Конечно не каждый запрос можно легко перенести, некоторые вообще не переносятся, но учитывая что NDB это просто движок, то в одной базе могут сосуществовать как InnoDB таблицы, так и NDB таблицы. Они даже неплохо используются одновременно в пределах одного запроса, т.е. в приложениях не нужно специально что-то наворачивать. Всё что нужно, это использовать кластер там где надо (т.е. обращаться к NDB нодам), а где не надо — обращаться к обычному MySQL.

коммент про сетевой кластер и джоины
Запрос с десятком сложных джоинов (хватает и 1-2 джоинов, просто на массивные таблицы) по определению не может быстро работать в сетевой среде, ибо temporary таблицы — а значит данные нужно подтянуть с нод. Зато фокус с derived table, т.е. вложенными запросами, отлично сработал и позволил ускорить часть запросов даже по сравнению с InnoDB
Для редких кейсов он безусловно подходит. Ничего не имею против, просто предостерег что это не замена InnoDB, и стоит посмотреть на Галеру.
Насчёт редких кейсов я бы поспорил, он довольно много куда пойдёт. Проблема там скорее в другом — кластер это 5 и более машин, а такие мощности не так уж часто нужны, вот и применяют его редко. Но если проект приличных масштабов, то определённо есть смысл его использовать.
Спасибо за комменты. Вообще я в душе где-то уже начал хоронить NDB кластер если честно, может зря :-)
Очень зря. Даже тогда, лет 5 назад, он нас очень сильно удивил и позволил не заниматься разработкой собственных кеширующих сервисов, как это происходит почти с любой социалкой, которая вырастает в прибыльный проект. Начальное тестирование на живую показало возможности масштабирования во всей красе — было у нас там пару тяжелых мест, которые обычный MySQL (InnoDB, 2 x 4 Quad Core, 16 GB RAM при базе в 5 гигов, основательно отюнингованный под проект) мог обслужить в районе 50-60 rps на конкретной странице (мерили через JMeter и грузили живую систему, поэтому там по статистике SQL обслуживал порядка 3к запросов в секунду). Перенос нескольких критичных мест на NDB (ествественно с переделанными запросами, но логика кода 1 в 1 осталась — поменялся только SQL) за несколько минут дало разогнаться JMeter до 400 rps и росло по мере прогрева кластера.

Так что если вам приходится иметь дело с большими нагрузками на базу — очень стоит тестировать. И ведь он не только чтение масштабирует, но и запись. Если у вас поток данных входящий больше чем способна записать физическая машина — репликация вообще не поможет. Или read/write может быть таким, что репликация будет работать на пределе своих возможностей и грузить записью все ноды так, что сильно скажется на скорости чтения.

Я вот лично жалею что мне не приходится работать с NDB Cluster больше — нету таких проектов у меня, где применить. А хочется :)
Давно используем Mysql мастер-мастер. В принципе полет нормальный. Еще хотел бы напомнить о таких небезопасных функциях как например NOW() и RAND(). Советую не использовать их при репликации (это касается и обычной MASTER-SLAVE репликации). Хотя вот тут (http://dev.mysql.com/doc/refman/5.1/en/replication-features-functions.html) пишут, что вроде как они реплицируются корректно, но на практике результат может быть непредсказуем. У нас например репликация залипала на полчаса предположительно из-за этих функций.
Я бы посоветовал mixed, в row-based может случиться коллапс с объемом траффика :-)
Я бв не советовал mixed. Так как там до сих пор баги.
А можно подробнее про балансировщик? Используете что-то свое или mysql proxy?
Мы размещены в амазоне и перекидываем трафик между ДЦ веб-сервисом ELB. А в каждом ДЦ машины хотят в свою локальную шарду БД. Поэтому если запахло жареным, чик, трафик переходит в другой ДЦ — проветрилось, возвращается в первый ДЦ. Возможно также эффективно для этого заюзать Elastic IPs, у них время переключения меньше (tcp/ip все таки)
т.е., по сути, у вас нет master-master between regions?
в каждом регионе запущен свой application?
Идея такая — одна база данных в м-м между датацентрами, но, т.к. Active-Passive, то запись в нее идет ТОЛЬКО из одного датацентра. При переключении трафика запись переключается в другой датацентр. Таким образом мы можем на уровне балансировщиков http-трафика переключать домены между датацентрами.

Т.к. балансировщик амазона может переключать трафик только между датацентрами региона, мы работаем внутри региона. Но в принципе через DNS или амазоновский Route53 можно поднять конфигурацию между регионами/материками.
а, так вы под датацентрами подразумеваете AZ, а я сразу и не понял.
а я-то, было, подумал, что вы что-то новое придумали :)
Ничего в принципе нового, просто описал технологию, относительно которой вижу кучу заблуждений и разнотолкований.
UFO just landed and posted this here
Локальная база становится «активной», когда веб-морды, пишущие в нее, начинают получать трафик. А т.к. одновременно может быть активен только один ДЦ из двух, то следовательно получаем Active-Passive мастер-мастер.
UFO just landed and posted this here
В каждом ДЦ — несколько тысяч баз данных. Одновременно трафик идет в оба ДЦ, но соблюдается важное правило — писать в БД только в одном ДЦ. При необходимости можно отлючить один из ДЦ от трафика, а можно вернуть трафик одновременно в 2 ДЦ — главное, чтобы не было одновременно записи из обеих ДЦ в одну БД.
UFO just landed and posted this here
:-) Мы просто делим трафик. Домен ru — на первый ДЦ, домены com,de — на второй ДЦ. В случае аварии все домены идут в один ДЦ. Как видите — в любом режиме распределения трафика запись идет только в одну, локальную для ДЦ базу данных.
UFO just landed and posted this here
Мы балансим на ELB, без VPC. Внутри одного региона. Да, 4 часа простоя SLA в год. Редко бывает трясет регион, но редко. У них много сервисов на уровне региона живут, не резервировать же их всех:
-s3
— autoscaling
— IAM
— cdn

Да, можно балансеры в каждом регионе и м-м между регионами. Но трафик сколько будет стоить такой…
UFO just landed and posted this here
Как происходит процесс переключения с одного работающего мастера на другой, как-то принудительно вызывается синк бинлога и перевод ноды из статуса мастер в статус слейв? Сколько времени данные докатываются с активного мастера на пассивный?
Запись в локальную БД в одном датацентре прекращается, т.к. http-трафик направляется через балансировщик амазона (командой АПИ) в другой датацентр на другую локальную БД, связанную м-м с первой.

Данные не докатываются, они постоянно синхронизируются между БД датацентров. В mysql репликация — непрерывный процесс. Но время задержки конечно может плавать, иногда в районе секунд.
Так вот самое интересное же, как вы определяете, что эти секунды уже прошли и что можно начинать лить в другую ноду? Ведь именно тут можно данные потерять.
В mysql репликации все проходит автоматически, никто секунды не считает. Лить можно в любую ноду, главное — не одновременно.
Хм, а если вы добавили запись, сразу после этого произошла смена мастера и сразу за этим вы делаете апдейт на эту самую запись — ошибки не будет?
Тут такая идея. Переключение записи с одного мастера на другой возникает в 2-х случаях:
1) Мастер завис, сдохло железо или несколько дисков рейда, обесточился датацентр и т.п. Понимаете, в этом случае какие нить данные да и могут потеряться. Зато клиенты продолжают обслуживаться в другом ДЦ. Да, возможно придется ручками поправить запрос репликации, который не может из потока репликации вставится в БД в другом ДЦ — редко но бывает.

2) Нужно провести обновление ПО на мастере. Мы сначала переключаем трафик и ждем пару минут. Затем тушим мастер. Теоретически ситуация описанная вами возможна (произошла запись в БД1, затем пока эта запись доходит по каналу репликации произошла конфликтующая запись в БД2 — но такие вещи разруливаются руками, просто поток репликации временно остановится, нужно будет его подредактировать, но конечно клиенты этого не заметят), но на практике не ловили еще. Зато удобно :-)
Вооот, теперь всё понятно, спасибо!
HighAvailability-льность ночью читается совершенно по-другому :)
Да уж, иначе чем днем :-) А в сочетании с лошадками вообще башню сносит :-)
Т.е. вместо master-master делаем master-slave с быстрым fallover :) А сколько громких слов про рабочий master-master было сказано :)
А нет. Это мастер-мастер, т.к. каждый сервер является слейвом для другого :-)
Есть еще Percona XtraDB Cluster — логическое продолжение Galera. Выглядит более перспективно, чем репликация MySQL или MySQL MMM.
Вот хочу ее посмотреть внимательно, мы используем Percona Server, отлично себя ведет.
Если не упираетесь в производиьтельность по записи, то вполне можно переходить.
Анналогично.
Напишите чего нибудь, если посмотрите раньше меня :)
За Российский data center зачёт :)

А по теме: спасибо, довольно интересно и актуально для меня.
Даже залогинился чтобы написать коммент.
1. Хранить в скрипте пароль для root от mysql это глупо (PCI DSS)
2. linux-ha мёрт — да здравствует pacemaker
3. Мониторить жизнь сервиса баш скриптом это худшее что можно придумать (опять же pacemaker)
pacemaker это та же запутанная и непрозрачная хрень, стоит посмотреть в документацию и попробовать настроить на продакшене :-)
Кластер на pacemaker/corosync разваливался в продакшене регулярно. Тогда уже лучше MySQL MMM — хоть немного стабильнее.
Сделайте на активной ноде долгий селект/апдейт и переключитесь на другую ноду — разваливания кластера на МММ гарантированно.
Что у вас именно разваливается?
При переключении нод запросы могли висеть очень долго, пока не отвалятся по таймауту. Проблема решалась реконнектом.
Такая проблема присутствует. Но любое существующее решение не решает этой проблемы. Как я и писал выше долгие запросы нужно либо убивать по таймауту при switch over'e либо ждать. + Местами помогает переписанный апликейшен.
Pacemaker это в первую очередь готовый стек для написания своих обвзязок. И конечно, в него нужно въехать. А писать кучу баш скриптов который при флапе сетки, проседания по спю и других не штатных ситуациях сделают вам сплит брейн с разсинхронном не только данных, а и клиентов, это действие на любителя.
А теперь представьте, что у вас таких машинок не 2, 3, 5,10 а 20, 30, 50.
nagios, 1500 тестов у нас и обработчики событий
Очень классно написа статья. Никакой воды! Всё кратко, ясно и понятно + шутке место нашлось. Мерси.
А как вы первый мастер востанавливаете после сбоя? Вы просто делаете его слейвом запасного мастера, даёте время пока он синхронизируется и переключаете балансер обратно на первый мастер? А если он скажем не просто остановился и не работал часик-другой, а вообще вся информация на нём испортилась и вам надо полностью всю базу из бэкапа востановить и заодно настроить с какого места бинлог включать… Вы же не пойдёте сейчас на единственный работающий мастер сервер и начнёте делать полный бэкап да ещё и с залочеными таблицами, вы ведь так весь ваш сервис можете на часик отрубить… Наверняка вы используете хотбэкапы?
Конечно. Мы делаем горячий снепшот машин средствами амазона (EBS снэшпот + наш скрипт для создания целостного снепшота рейд10). В случае подобной катастрофы:
— поднимается машина из снепшота с отставшим мастером
— мастер автоматически догоняет живой мастер
— трафик снова переключаестя на ставший актуальным мастер

Мы пробовали XtrаBackup incremental binary снепшоты, но пользоваться амазоновскими вроде проще. Еще конечно мы постоянно бэкапим мастер на третий сервер, слейв. Там тоже бэкап.
UPDATE mytable SET mycol=mycol+1; - на одном сервере UPDATE mytable SET mycol=mycol*3; - на втором сервере

>> также приведет к рассинхронизации данных в обеих БД

Тут наверное стоит упомянуть, что рассинхронизация произойдёт только потому, что мы для нового значения колонки используем не константу, а другую колонку. А то я 5 минут тупил пока дошло почему.
Смотри что происходит.
1) Изначально допустим в колонке на обеих серверах стоит 1.
2) На первом сервере прибавляем к колонке 1 и получаем 2.
3) На втором сервере в это же самое время умножаем колонку на 3 и получаем 3.
4) По потоку (который только один) репликации с первой на вторую машину приходит команда — прибавить 1. 3+1 = 4.
5) По потоку (который только один) репликации со второй машины на первую приходит команда — умножить на 3. 2*3 = 6.
В результате на первом сервере — 6, на втором — 4.
Отличия в том, что на первом сервере к колонке сначала прибавляют 1, затем умножают на 3. А на втором — сначала умножают на 3, затем прибавляют 1. :-)
Это я понял, я просто считаю, что этому место в статье.
Так обсуждали вроде выше для чего можно и нельзя применять NDB. Слишком сложно и громоздко же, но для некторых кейсов пишут что неплохо работает :-)
Дык там вроде не только NDB, а абсолютно прозрачно можно поставить за ним n серверов.
поправка насчет того что вы пишите
недостаточная поддержка транзакционности (спасибо патчу Percona Server, в котором эта фича реализована)

Эта фича к сожалению не работает, так как нужно. Хотя она все еще остается полезной, но когда я ее проверял на работоспособность обнаружил баг. Который заключается в том что репликация стартует со старой позиции из master.info, а не из той что записана в релей логе. Собственно баг репорт bugs.launchpad.net/bugs/937852
Кто-нибудь подскажет, за 2 года в лучшую сторону что-нибудь изменилось? А то эта надпись красным «море подводных камней» перед глазами маячит и не понятно, стоит ли браться вообще.
Sign up to leave a comment.