Post on 14-Jan-2015
description
MongoDB is a web-scaleКурс «Базы данных»
Антон Волохов
Yandex
7 октября 2013 г.
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 1 / 51
Содержание
1 Введение
2 API
3 Storage internals
4 Replication
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 2 / 51
Содержание
5 Sharding
6 Секретный ингредиент
7 Заключение
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 3 / 51
Введение Терминология
Терминология
Документ - Ряд в RDBMSКоллекция - Таблица в RDBMSБаза данных - Базы данных в MySqlПространство имён - Пара <база данных,коллекция>Нода - Процесс базы данных, осуществляющийхранение и поиск пользовательских данных надискеРеплика - Множество Node, обладающееполной копией одних и тех же данныхШард - Единица масштабирования БД
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 4 / 51
Введение Disclaimer
Disclaimer
Если есть вопрос, меня можно и нужно перебиватьНе на каждый вопрос я смогу ответить по ходулекцииНе на каждый вопрос я смогу ответить
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 5 / 51
API Декларированные цели
Декларированные цели
ПроизводительностьПростота использованияГоризонтальное масштабированиеОбработка эволюционирующих данныхКонкуренция с RDBMS
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 6 / 51
API MongoDB features
MongoDB features
BSON протоколJS консольХранимые процедурыMaster-slave репликацияШардирование без даунтаймаСистема хранения файлов GridFS
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 7 / 51
API MongoDB features
API
Хранимые процедуры> db.system.js.insert ({"_id" : "inc", "value" : f unc t i on (x)
{ re tu rn x+1}})> db.eval("inc(1)")2
ИндексыMapReduceУникальный первичный ключ> db.books.insert({foo:"bar"})> db.books.find(){ "_id" : ObjectId("5251664b629201a4d4164ec0"), "foo" : "bar" }
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 8 / 51
API Querying
Примеры запросов
Документыisbn = {_id: "0-321-34960-1",author: "B. Goetz",title: "Java Concurrency In Practice",ISBN :{"ISBN-10": "0-321-34960-1","ISBN-13": "978-0-321-34960-6"},"authors-list":["Brian Goetz", "Tim Peierls", "Doug Lea", "Joseph
Bowbeer", "David Holmes"]}
Запросыdb.test.insert(isbn)db.test.find({ "title" : /Java/ })db.test.update(isbn, { $push : { "authors-list" : "Joshua Bloch" }})db.test.insert({ "foo" : "bar" })db.test.find({ "title" : { $gte : "Java" }, "title" : { $lt : "Python"
}})
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 9 / 51
API Querying
Вложенные документы> db.items.insert({ foo : "foo", "bar" : { "first" : 1, "second" : 1 }})> db.items.insert({ foo : "foo", "bar" : { "first" : 1, "second" : 2 }})> db.items.insert({ foo : "foo", "bar" : { "first" : 2, "second" : 1 }})
Запрос на точное совпадение> db.items.find({ bar:{ "first" : 1 , "second" : 1 }})
{ "_id" : ObjectId("52517090629201a4d4164ec1"), "foo" : "foo","bar" : { "first" : 1, "second" : 1 } }
Запрос на диапазон значений> db.items.find({ bar : { $gte : { "first" : 1, "second" : "" }},"bar" : { $lt : { "first" : 2, "second" : "" }}})
{ "_id" : ObjectId("52517090629201a4d4164ec1"), "foo" : "foo","bar" : { "first" : 1, "second" : 1 } }
{ "_id" : ObjectId("5251709e629201a4d4164ec2"), "foo" : "foo","bar" : { "first" : 1, "second" : 2 } }
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 10 / 51
Storage internals Работа с файловой системой
Работа с файловой системой
Аллокейтим файлы на диске отдельно для каждойбазы данных-rw------- 1 mongodb nogroup 16M test.ns-rw------- 1 mongodb nogroup 64M test.0-rw------- 1 mongodb nogroup 128M test.1...-rw------- 1 mongodb nogroup 2.0G test.5-rw------- 1 mongodb nogroup 2.0G test.6
Создаём служебную базу данных (∼ 5% дисковогопространства)
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 11 / 51
Storage internals Работа с файловой системой
Кеширование
Не in-memory databaseНе занимаемся memory managementMemory-mapped filesFile system cache
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 12 / 51
Storage internals Работа с файловой системой
Файлы данных
ЭкстентУказатели на первую и последнюю записьПоложениеДлинаПространство имён
ЗаписьДлинаСмещение внутри экстентаСмещения предыдущей и последующей записейДокументPadding
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 13 / 51
Storage internals Advanced querying
В свете этого
УдалениеПомечаем пространство как свободноеНе пишем на диск
ДобавлениеЛенивоВ первый найденный свободный блок
ОбновлениеДокумент увеличился?Влезает ли обновлённый элемент в свой блок?
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 14 / 51
Storage internals Advanced querying
Администрирование
Проблемы1 Фрагментация данных2 Параллельное изменение одних и тех же файлов3 Неконтролируемое разрастание файлов данных
Решения1 compact2 глобальные блокировки на уровне базы данных3 repair базы
РезюмеНи одного адекватного решения
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 15 / 51
Storage internals Advanced querying
Пространство имён
ИндексыКоллекцииЭкстентыСтатистика
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 16 / 51
Storage internals Индексы
Индексы
B-ДеревоКомпозитный индексПо массиву и поддокументуЗапоминаем оптимальный план запроса.explain()
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 17 / 51
Replication Replication
Master - Slave
Запись только на одну машинуЧтение со всех машинНастраиваемая консистентность
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 18 / 51
Replication Replication
КонсистентностьНе проверяем, удалась ли записьОшибки записи в текущем соединении
getLastError()Ждёт, когда W машин запишут все изменения втекущем соединении с момента предыдущегоgetLastError()По-сути, точка синхронизации
Не верьте бенчмаркам!Если не вызывать getLastError(), клиент будет писать вмонгу, не зная, прошла ли запись. Результат - over9000rps, при неопределённом числе удачных записей.
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 19 / 51
Replication Replication
Replication internals
Лог операцийПростейшие преобразования запросовТранзитивность репликацииТекущий мастер выбирается голосованием
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 20 / 51
Replication Replication
Replication internals: oplog polling
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 21 / 51
Replication Replication
Replication internals: voting
Все машины реплики знают друг о другеМастер пингует все машины своей репликиЕсли мастер не видит кворум, он снимает с себяполномочияПроцесс голосования инициирует машина,которая не может найти мастераГолосование начинается в случае, если мастер невиден кворумом
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 22 / 51
Replication Replication
Replication internals: Rollback andRecovery
1 Откатываются все изменения, которых нет намастере
2 Накатываются все изменения нового мастера
NB!Нет автоматического разрешения конфликтовНет внятного оповещения о существованииконфликтов
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 23 / 51
Sharding Overview
Overview
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 24 / 51
Sharding Overview
Overview
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 25 / 51
Sharding Sharding meta
Sharding meta
Точечные запросы по шардамАвтоматическая балансировкаЛокализация данных
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 26 / 51
Sharding Sharding meta
Sharding metaА что внутри?
Где хранить метаданные?Как обеспечить надёжность?Как сгруппировать данные для шардирования?
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 27 / 51
Sharding Sharding meta
Configuration Server
Нет репликацииСинхронная записьTwo phase commitRead-Only при отказе одной из машин
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 28 / 51
Sharding Sharding in a Nutshell
Шардируем
1 Объявляем коллекцию как шардированную2 Выбираем поле, по которому будут строится чанки
ЧанкНачало диапазонаКонец диапазонаОбъемПринадлежность к шарду
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 29 / 51
Sharding Sharding in a Nutshell
Балансируем
Периодичный бэкграунд процесс роутера
Workflow1 Пытаемся взять lock2 Если удалось, опрашиваем каждое пространство
имён3 Смотрим на распределение и заполненность
чанков4 Определяем, нужно ли делить или перемещать
чанки5 Осуществляем миграцию
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 30 / 51
Sharding Sharding in a Nutshell
Решаем проблемы
ПлохоХодить на каждый запрос в амстердам с западногопобережья - не комильфо.
Кеширование на стороне роутера
Всё ещё плохоПосле каждой миграции, кешированная информациястановится протухшей.
Оповещаем роутеры, они обновляют кеш
На хлеб уже мажется.А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 31 / 51
Sharding Sharding in a Nutshell
Решаем проблемы
Но ещё пахнетНе можем контролировать распределение чанков; нетзаявленной локализации данных
ТэгиСвойство шардаОтображение из диапазона ключей в тэг
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 32 / 51
Sharding Sharding in a Nutshell
Тэги
{ ns : "test.books", minKey : { date : 01.01.2013 }, maxKey : {date : $MaxKey}, tag : "ssd" }
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 33 / 51
Sharding Sharding in a Nutshell
Не решаем проблем
Не предусмотренноеDDL-убивашкаНельзя так просто взять и поменять ключшардированияЕсли поздно объявить коллекцию шардированной,все существующие данные навсегда окажутся водном чанкеЧанки не умеют склеиваться и не умирают приопустении
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 34 / 51
Sharding Ключ шардирования
Выбираем ключ шардированияСхема:
100 000 000 записей{url: "http://www.imdb.com/title/tt0795176/", domain : 1, title:
"Planet Earth", "air date": 2007, seasons:[1], rating:9.5cast:<...>, similar:<...>, description:<...> }
Полный урл уникаленНекоторые домены могут содержать десятки тысячдокументовСписок доменов меняется редко, информация по урламменяется часто, домены имеют возрастающийидентификатор
ЗапросыДостать одну сущность по урлуДостать 1000 сущностей по урламДостать всё из www.imdb.comОтгрузить всю базу
Как правильно выбрать ключ шардирования?А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 35 / 51
Sharding Ключ шардирования
Выборы ключа шардирования (0)
Возможные вариантыObjectId()Поле с рандомным значениемУрлХеш от урлаПара <хеш от домена, хеш от урла>
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 36 / 51
Sharding Ключ шардирования
Выборы ключа шардирования (1)
ObjectId
ПреимуществаМонотонно возрастает - легко собрать чанк
НедостаткиМонотонно возрастает - запись в один шардМонотонно возрастает - пустые чанкиНевозможно поддержать уникальность урлов вразных шардах
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 37 / 51
Sharding Ключ шардирования
Выборы ключа шардирования (2)Случайное значение
ПреимуществаРавномерная распределённость - запись во всешардыРавномерная распределённость - нет пустыхчанков
НедостаткиРавномерная распределённость - очень долгаямиграция, стынет кешНевозможно поддержать уникальность урлов вразных шардах
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 38 / 51
Sharding Ключ шардирования
Выборы ключа шардирования (3)
Урл
ПреимуществаУникальность урловЛокализация запросовЗапись во все шардыМало пустых чанков
НедостаткиТяжеловесный индексСложно собрать чанк - долгая миграция чанка
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 39 / 51
Sharding Ключ шардирования
Выборы ключа шардирования (4)
Пара id домена- хеш от урла
ПреимуществаТе же, что и от урлаПлюс бесплатный индекс по доменуБыстрая миграция, если обновления по доменуприходят батчамиЛегковесный индекс
НедостаткиДолгая миграция, если гипотеза о батчах невернаИногда чанки пустеют
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 40 / 51
Sharding Ключ шардирования
Выборы ключа шардирования (5)
РезюмеНа какие запросы хотим отвечать?Монотонно возрастающий ключ - плохоПолностью рандомный ключ - плохоШардовый ключ участвует в запросе -дополнительный профит
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 41 / 51
Sharding Ключ шардирования
Выборы ключа шардирования. ИтогиСтудент! Помни!
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 42 / 51
Секретный ингредиент Почему MongoDB не production-ready?
Почему MongoDB не production-ready?
Писалась исходя из того, что она работаетТолько SocketException в логахСовершенно не описано поведение внеблагоприятных условияхНекачественные мониторинги
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 43 / 51
Секретный ингредиент Почему MongoDB не production-ready?
Кстати о мониторингах
db.serverStatus()
Возвращает кучу данных о базеВсе показатели - в миллисекундах от старта сервераМониторинг дёргает serverStatus
А теперь представим, что система перегружена1 Дёргаем serverStatus2 Через 20 секунд получаем ответ3 Через минуту дёргаем ещё раз4 Через 20 секунд получаем ответ5 Разность значений может быть статистикой за любой
промежуток времени от 40 до 80 секунд
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 44 / 51
Секретный ингредиент Почему MongoDB не production-ready?
Кстати о мониторингах
А теперь делим разность из предыдущего слайда на 60И получается, что за последнюю минуту половина базбыла заблокирована на чтение в течение не меньшечем 90 секунд.
Не вся статистика разделена по пространствамимёнНе знаем, какие именно запросы перегружаютбазу
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 45 / 51
Секретный ингредиент Почему MongoDB не production-ready?
WAT?
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 46 / 51
Секретный ингредиент Эксплуатация
Если действительно нужен функционал
1 Предельно уяснить, какие запросы важные2 Описать ограничения уникальности3 Построить ключ шардирования4 Не выполнять DDL на боевых базах без крайней
необходимости5 Всегда вручную передёргивать роутеры после DDL6 Заблаговременно масштабировать7 Не тянуть с шардированием
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 47 / 51
Заключение Сухой остаток
Сухой остаток
Почему MongoDB - это действительно крутоОднокнопочные шардирование и репликацияБогатый язык запросовВторичные индексы
Почему нужно трижды подуматьНечитаемые логиНепонятно, где у монги болитПри неосторожном обращении, легко превратитьвсё в тыквуНе жмутся названия полей
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 48 / 51
Заключение Осталось за кадром
Осталось за кадром
http://www.kchodorow.com/blog/2010/08/23/history-of-mongodb/ - История созданияпродуктаАвторизацияGridFSПрофилированиеAggregation frameworkMapReduce
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 49 / 51
Заключение Осталось за кадром
Литература
http://www.amazon.com/MongoDB-Definitive-Guide-Kristina-Chodorow/dp/1449344682http://docs.mongodb.org/manual/http://www.kchodorow.com/blog/index.php?s=mongodb
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 50 / 51
Вопросы?
Вопросы?
Почта a.v.volokhov@gmail.com
А. В. Волохов (Yandex) MongoDB 7 октября 2013 г. 51 / 51