Пользователь
0,0
рейтинг
3 ноября 2009 в 13:37

Разработка → MongoDB или как разлюбить SQL

Введение

Коллеги, при разработке приложений, мы каждый день сталкиваемся с потребностью в гибком хранении информации (обновлении, поиске по ней, и т.д.). Класс продуктов, которые решают этот круг задач, как все мы знаем — Базы данных. Но что это такое в нашем понимании? У многих «база данных» твердо ассоциируется с MySQL, таблицами и SQL-запросами. И это устраивает до определенного момента. Действительно, реляционные базы данных дают массу преимуществ в работе: поскольку данные имеют сильную связанность, не нужно контролировать целостность базы данных. Используя простой под-запрос можно выбрать количество комментариев к каждому посту в блоге. Используя JOIN нетрудно делать сложные связанные выборки и получать данные сразу о нескольких сущностях.

Масштабировали, масштабировали, да не вымасштабировали

Однако, когда вдруг понимаешь, что одного сервера перестает хватать, и хочется раскидать базу на несколько физических машин, то первое что предлагается — master-slave репликация, при которой запись идёт на одну машину, а чтение — с нескольких. Но при достаточно большом количестве изменений в скором времени master только и будет делать что раздавать логи, и придётся прибегнуть к изощренной настройке, чтобы каждый узел имел один шефствующий сервер (master) и мог иметь несколько подчиненных серверов (slave). Данная схема весьма сложна в реализации и содержит single point of failure (т.е. при выходе из строя одного сервера, все его подчиненные стремительно превращаются в динозавров). Опять же, все эти ухищрения позволят увеличить лишь количество чтений. А если для внесения изменений в состояние базы данных не хватает мощности одного сервера, то приходится распределять нагрузку, храня разные таблицы на разных серверах. Но тогда потеряется связанность. Или приходится разбивать таблицу на несколько частей, храня их в разных местах, согласно заданному закону (например по ID), однако это унесет в могилу прелести JOIN. Чем дальше мы пытаемся масштабировать реляционные базы данных, тем большим удобством мы за это платим. Например, при использовании master-master, мы заплатим auto increment'ами.

Спасут ли нас MemcacheDB и Redis?

Подобные key-value решения существуют довольно давно. На мой взгляд, MemcacheDB это поделка, паразитирующая на добром имени замечательного продукта: данные там абсолютно не связаны между собой, мы можем лишь проводить операции над значением зная ключ. Я потратил уйму времени на написание инструментария, позволяющего выгодно работать с key-value БД вроде MemcacheDB, и это даже работает, однако пришел к тому что простые насущные задачи решаются настолько криво, что невольно думаешь в сторону реляционки: например, нету даже элементарной реализации времени жизни объекта (TTL), т.е. нельзя взять и удалить сессии старше месяца. Это не доставляет.

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

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

Что делать если хотим каталог товаров по типу Яндекс.Маркета?

Допустим, мы хотим сделать каталог, в котором осуществляется поиск по таким параметрам как цена, рейтинг, кратность зума у фотоаппарата и количество передач у велосипеда. Допустим, мы используем реляционную базу данных типа MySQL. Что мы должны сделать? Мы должны либо создать таблицу goods, в которой будет как кратность зума, так и количество передач для велосипеда, и к примеру, показатель гибкости щетины зубной щетки (в этом случае мы упремся в лимит полей для таблицы, или потеряем на дисковом пространстве, скорости, и удобстве), либо мы должны завести табличку вида good_id, key, value и делать страшные JOIN'ы для выборки и поиска, не заикаясь о масштабировании.

Еще можно натравить на это дело Sphinx или что-нибудь похлеще, однако это скорее всего будет выглядеть как забивание гвоздей ноутбуком.

У реляционок налицо серьезная родовая травма.

MongoDB говорите?

MongoDB — резкая как понос объектно-документарная база данных. Идеологически это некий симбиоз между привычной реляционной БД и key-value хранилищем, и на мой взгляд, весьма удачный. С одной стороны, она позволяет делать очень быстрые операции над объектом, зная его идентификатор, а с другой, предоставляет мощнейший инструмент для сложных взаимодействий.

Коллекция — именованное множество объектов, при этом один объект принадлежит лишь одной коллекции.
Объект — совокупность свойств, включая уникальный идентификатор _id.
Свойство — совокупность названия и соответствующего ему типа и значения.
Типы свойств — строка, целое число, число с плавающей точкой, массив, объект, бинарная строка, байт, символ, дата, boolean, null.
Поддерживаются операции выборки (count, group, MapReduce...), вставки, изменения и удаления. Связей между объектами нет, объекты могут лишь хранить другие объекты в свойствах. Поддерживаются как уникальные, так и композитные индексы. Индексы можно накладывать на свойства вложенных объектов.
Поддерживается репликация (даже подразумевается), реализован fail-over.
Реализован MapReduce и шардинг.
Поскольку объекты могут иметь произвольный набор свойств, для каталога достаточно создать коллекцию goods и складывать туда объекты. При этом поиск будет вестись по индексам.
Резкость MongoDB ярко выражена на insert'ах, они происходят ну очень быстро. Кстати, приятно что формат хранения и формат передачи объектов по сети один и тот же, так что для выборки какого-то объекта надо всего лишь найти его позицию по индексу и вернуть клиенту кусок файла определенной длины — никакой абстракции над storage engine.
В качестве уникального идентификатора используется не auto-increment'ное поле, а 12-байтное уникальное число, генерируемое на клиенте. Таким образом, во-первых нет проблемы с синхронизацией реплик, т.е. можно независимо делать вставки на две разные машины, и конфликта не возникнет. Во-вторых, не будет ерунды с переполнением целого числа, ну и после пересоздания базы данных, поисковики не будут адресовать на новые статьи по старым ссылкам.

MongoDB + Memcached? Покруче чем Бонни и Клайд!

С базой данных более-менее разобрались, теперь подумаем как нам всё это дело кешировать, ведь нам же хочется отдавать горячие пирожки со скоростью Memcached!

Во-первых, кеширование самих объектов. Как многие успели догадаться, или узнать из опыта — в большинстве случаев операция выборки объекта по ID является самой частой. Например, выборка объекта пользователя, выборки этого поста из базы Хабрахабра (аминь), и т. д.

Как мы уже выяснили выше, перекладывать сей труд на приложение неразумно, т.к. мы должны были бы нагородить огород распределенных блокировок. Пойдем другим путем, напишем асинхронное приложение, которое подключится к MongoDB и, прикинувшись slave'ом, будет получать лог изменений, и сбрасывать изменения в Memcached (если объект содержит ключ в свойстве _key). Поскольку приложение асинхронно, это будет происходить быстро, однако гонки возникать не будет. Написать несложно, моя реализация тут. Более того, я еще присобачил туда отправку изменений серверу событий, так что мне стоит только изменить объект откуда угодно (да хоть из консоли), как он тут же будет передан всем подписанным на него клиентам.

Кеширование запросов и девалидация кеша должна работать несколько иначе. Существует несколько подходов:
  • Кешировать на определенное время. Если запрос один и тот же или их не так много, то можно обновлять кеш не чаще раза в секунду — это уже значительно снизит нагрузку.
  • Удалять кеш по требованию приложения. Подход довольно муторный, но имеющий право на жизнь.
  • Использовать сервис блокировок для того, чтобы не делать одну работу два раза. Однозначно — это добро.

Минусы с которыми придется столкнуться.
  • MongoDB — продукт довольно молодой, и в нем встречаются баги (бывает Segmentation fault, core dumped), появляются новые фичи, и т.д. Я использую его в продакшене, но с осторожностью. Однако, несомненным плюсом является высокий темп разработки (проект пишут не только волонтеры, но и компания людей на полной занятости), так что вы вполне можете рассчитывать на быстрый багфикс, помощь в решении ваших проблем и реализацию ваших идей (если конечно они хорошие). Также доступна коммерческая поддержка.
  • Накладные расходы на хранение названий свойств.
  • По-умолчанию максимальный размер объекта — 4 мегабайта.
  • На 32-битных машинах, максимальный размер одной базы данных — 2 гигабайта.

Finita la comedia!
Страничка проекта — MongoDB.
Найденный бенчмарк MongoDB vs MySQL.

Эта статья рискует положить начало циклу о MongoDB. В следующий раз я поподробнее расскажу о шардинге, MapReduce, и приведу живой пример.

Друзья, спасибо за внимание! Буду рад конструктивным комментариям.

Опубликовано продолжение: «MongoDB — варим хороший кофе».
@TravisBickle
карма
2,0
рейтинг 0,0
Реклама помогает поддерживать и развивать наши сервисы

Подробнее
Спецпроект

Самое читаемое Разработка

Комментарии (99)

  • НЛО прилетело и опубликовало эту надпись здесь
    • 0
      Спасибо, Вы правы, добавил ссылку в конце материала.
      • НЛО прилетело и опубликовало эту надпись здесь
        • –1
          и, желательно, с несколькими СУБД. Наиболее интересны PostgreSQL, Oracle, MS SQL Server.
          Мускул это все же не самая скоростная БД…
          • +2
            «Мускул это все же не самая скоростная БД…»

            Вы просто не умеете её готовить :) Просто все перечисленные субд хороши в своей стихии.

            mysql > load data infile = 1млн строк за 4-10 секунд — как вам такая скорость?

            Это конечно самый утрированный пример, но все жё — есть разные методы оптимизации и прежде всего лучше исходить из задачи и её ограничений (читать условий)


            PS. если тц опубликует сорцы бенч'а (который возможно сделает) — то думаю найдутся добровольцы самостоятельно прогнать по другим субд и поделиться результатами. Так что — пусть покажет нам — скорость! ;)
            • –7
              не буду спорить — я не самый спец в этом. просто знаю, что мускул редко используют в высоконагруженных проектах (исключения, обычно, строятся на неких доработанных вериантах, наподобие варианта для телекомов).
              • +1
                А сам Хабр разве не на MySQL работает?

                Вообще-то разработчики MySQL ставили себе в цель именно скорость работы. Поэтому многие вещи до сих пор не поддерживаются.
                • –6
                  На MySQL. А откуда спрашивается пролежни так часто?)))
                  • 0
                    Может из желания поддержать «многие вещи»? :)
          • +1
            А вот меня Firebird Интересует…
        • 0
          мой сегодняшний тест
          stas-agarkov.livejournal.com/17659.html
    • +2
      Такие тесты ничего не покажут, так как подход в реализации задач слишком разный.
      «типовые задачи» в скорости могут отличаться в сотни и тысячи раз, как с преимуществом у key-value баз данных, так и у реляционных.
      • –1
        в этом случае нужно рассматривать задачи более высокого уровня, чем извлечение/помещение данных в БД. Например, реализовать несколько небольших проектов и поглядеть их сложность и скорость (потому что если и сложнее и медленней — то нафиг оно вообще нужно).
        • +3
          Ну вот есть у меня проект, который изначально был на mysql, а потом был переписан на couchdb, потому что mysql просто не справлялся с нагрузкой, а couchdb я даже в top не вижу. Как мне их сравнивать? :)

          На маленьких проектах разница в скорости будет на уровне погрешности измерений (нереляционные базы долго запрягают, но быстро едут, а реляционные быстро запрягают, но туго ездят), а на больших сравнивать банально нечего — либо нереляционные нельзя применять, либо реляционные не тянут и 1% нагрузки от того, что дают нереляционные.
          • +1
            Плюсую. Так и есть. И с приходом Mongo, область применения не-реляционных значительно расширились :-)
          • НЛО прилетело и опубликовало эту надпись здесь
            • +2
              Подробности раскрывать не могу, опишу общими словами.
              Есть несколько потоков, читающие и пишущие в базу.
              Структура базы — две таблицы. Одна — список сущностей (около 200.000 на тот момент было). Вторая — история обработки сущностей (около миллиона).
              Потоки брали сущности из базы (select from table1), блокировали их (update table1), какое-то время работали с ними, дописывали во вторую таблицу логи (insert into table2), потом обновляли состояние сущности (update table1) на основании истории (select from table2).

              Пока использовался mysql, больше 6-8 запустить было невозможно, mysql отъедал одно ядро полностью и дальше не давал рости.
              Был так же web-interface для просмотра статистики, запросы на котором (2-3 запроса по хорошим ключам) отрабатывали секунд по 20. С него так же генерилось небольшое количество insert/update (порядка 1-2 в минуту), которые так же отрабатывали с дикими тормозами.

              В случае с couchdb, его не видно в top, процессов запущено около 30, они грузят полностью 4 ядра и больше потестировать не могу. При этом, база выросла в несколько раз (количество сущностей — около 1.700.000).
              Организована couchdb так: один документ — одна сущность из table1, у каждой из них история в виде списка в одном из полей.
              Веб-интерфейс теперь отрабатывает мгновенно.
              • НЛО прилетело и опубликовало эту надпись здесь
              • +1
                о, живой опыт людей всегда интересен. Сейчас как раз присматриваюсь к подобным БД (Couch и Mongo), нет ли в планах статьи на тему?
                И тогда по CouchDB сразу вопрос — а запросы в виде материализованных видов не напрягают? Каждый раз их определять на мой взгляд несколько муторно по сравнению с приснопамятным SQL или запросами к Mongo.
  • +1
    а скорость работы по сравнению с sql подобными?
    например тот же пример с " каталог товаров по типу Яндекс.Маркета".
    • +1
      Ссылку на бенчмарк в конце добавил. На элементарных задачах скорость выше, поскольку нет парсинга запроса и абстракции над storage engine. Реализацию же Яндекс.Маркета даже сравнивать бессмысленно, разница будет на порядок, т.к. подходы разные.
      • +4
        а в каких задачах все же лучше использовать sql? или можно смело изучать и пересаживаться на MongoDB?
        • +1
          С ходу не могу придумать такую задачу. Думаю, если кажется что MongoDB не справится, а SQL справится, то значит это проблемы с проектированием. Как показала практика, сложные выборки нужны довольно редко, выборки сильно упрощаются при правильном проектировании.
          Не знаю ваших задач, но думаю, можно смело пересаживаться.
          • +1
            ответ от Mike Dirolf, который собственно презентовал MongoDB на RubyEnRails '09:
            если вам нужно что-то с большим числом транзакций, то MongoDB вам скорее всего не подойдет
      • +1
        Бенчмарк не понравился — автор использовал для хранилища MongoDB свою флешку, база была всего лишь на 2 млн записей и нет информации о том, насколько обе базы во время тестирования загрузили компьютер. Нет ли еще тестов? Впрочем у всех настолько разные цели использования БД, что лучше будет провести свой собственный тест.
  • 0
    Как в тему, буквально недавно шерстил их сайт и читал документацию, очень понравилась идея, ну и еще, конечно же, жду v3 шардинга, они обещали улучшить реализацию MapReduce и взаимных блокировок
  • +2
    Ждем продолжения, интересно
  • +2
    Давненько хотел познакомиться с MongoDB, но никак руки не доходили. Теперь появилась надежда, но хотелось бы побольше информативного материала — схемы, диаграммы, сводные таблицы и т.д. Очень сложно читать новый для себя материал, представленный голым текстом.

    Спасибо, жду продолжения.
  • 0
    Удобство — эт очень хорошо.
    Но как дела со скоростью сложных выборок?
    • 0
      там где надо kv-системы, НЕТ сложных выборок или они заменяются логикой приложения + серия быстрых простых выборок. Тех приложений, где реально надо сложные выборки — они использую СУБД
      • 0
        Что Вы подразумеваете под СУБД? Реляционную СУБД? MySQL? :-)
        Не могу придумать задачи, где хватит простой kv-базы. Обычно бывает так что нужны простые «by id» операции с коллекцией, ну и элементарный постраничный вывод с сортировкой по ключу. Вряд ли разумно ради этого использовать реляционную СУБД, со всей её беспощадностью.
        • 0
          если изначально проектировать систему под такое — везде можно применить. Я вот не могу придумать, где в обычных задачах НАДО SQL :)
        • 0
          Банковская книга? Там надо хранить каждую запись, однако в тоже время надо делать сложнейшие выборки, когда надо.
  • 0
    что насчет couchdb?
    • 0
      это документ-ориентированая база, скорее даже хранилище. а не kv-storage
      • 0
        я знаю что это, интересно в сравнении с mongo, последняя вроде как взрослее, но кауч догоняет наверное
  • 0
    Можно упомянуть, что лимит размера объекта в коллекции в 4 мегабайта может создать проблемы при сильной вложенности…
    • 0
      Да, тоже об этом подумал. Дописал про это и про 2 гига на 32 битах.
  • +6
    "MongoDB + Memcached? Покруче чем Бонни и Клайд!". при таких утверждениях, всегда приходит на ум мысль о том, как эти ребята кончили… так что нужно по аккуратней в сравнениях )))
  • НЛО прилетело и опубликовало эту надпись здесь
    • 0
      То есть вы предлагаете разрезать MySQL'ю мозг скальпелем и вставить чип XML-парсера чтоб он индекс строил по XML-полям? Во-первых это будет тормознее чем MongoDB, во-вторых получатся те же яйца только сбоку. Кстати, в этой приблуде надо будет еще нагородить нечто для атомарных update'ов.
      Не уловил мысль про изменчивые атрибуты и быстрый доступ к полю…
      • НЛО прилетело и опубликовало эту надпись здесь
        • 0
          Оо… уже разрезали… да еще и криво зашили :-)

          mysql> SELECT CONCAT('\n\n',
          -> GROUP_CONCAT(' ', name, '\n' SEPARATOR ''),
          -> '') AS xmldoc
          -> FROM cities\G

          Оставлю это без комментариев :-)
  • 0
    Автор забыл указать один существенный недостаток — ограничение размера базы на 32-битных машинах в 2 Гб. Для преодоления этого барьера, разработчики рекомендуют использовать 64-битные процессоры, однако умалчивают, каким будет ограничение размера базы в этом случае. Подозреваю, что не больше размера ОЗУ. А вы как думали, откуда берется такая скорость? Правильно, объекты хранятся в памяти. Как-то совсем нерационально получается с точки зрения хранения данных, особенно если использовать довольно интересную возможность хранения бинарных данных в MongoDB.
    • +2
      Автор написал об этом полчаса назад. Это действительно так, но ведь 32-битные сервера это редкость, тем более что на них можно использовать эмуляторы 64-битности.
      > Подозреваю, что не больше размера ОЗУ.
      Вы заблуждаетесь, я знаю людей, которые хранят свыше 200 гигабайт в одной коллекции, и всё замечательно и быстро работает. Посмотрите хотя бы бенчмарк по ссылке.
    • +3
      Лимиты про 2Гб — это из-за использования mmap. К размеру ОЗУ отношения не имеет.
  • 0
    MongoDB может со временем заменить MySQL?
    • 0
      Что значит заменить? Это разные вещи, которые нужно применять для разныз задач. Реляционные БД никуда не денутся. А вот нереляционные документоориентированные и объекториентированные БД, надеюсь, найдут свое место в веб-приложениях. Я вообще считаю, что веб испорчен SQL'ем. Если бы изначально реляционные БД не применялись там, где их функционал явно избыточен, то современный веб выглядел бы совершенно иначе. Все эти френдленты и плоские комментарии — явное следствие использования реляционных БД. JSON куда более природен для восприятия человеком, чем линейные выборки из реляционных БД.
      • 0
        Так а где была альтернатива? Если бы объектные развились лет на 10 пораньше, то наверняка бы они заняли своё место в Вебе, но увы…
        • +2
          идея объектных баз данных не нова. была и есть такая страшная штука Zope, в ней объектная база данных и ей уже лет 10.
          есть целый выводок xml баз данных и это тоже далеко не новость.
          Все эти проекты заняли свое место но мейнстримом не стали да и не станут.

          Вообще уход от реляционных бд это шаг назад на несколько десятков лет. И не все так хорошо в нереляционных базах как оно хотелось бы. Нужно 10 раз думать предже чем начать приманять подобные вещи на практике.

          Ради спортивного интереса последнее время ковыряю CouchDB. В течении пары недель думаю выжму из себя несколько статей на эту тему с живыми примерами и может быть тестами.
          • 0
            > есть такая страшная штука Zope
            Воистину страшная!
            После работы с этим чудом инженерной мысли я с большим предубеждением воспринимаю все «самопальные» (то есть не имеющие ~100К серьезных внедрений) базы данных. Как почитаешь про ZODB так все выглядит очень гладко, но на практике как обычно «забыли про овраги». При росте базе (всего ~10K записей) начались серьезные тормоза, кроме того база, заявленная как очень надежная, постоянно сыпалась почище myisam, хуже того — средств восстановления для нее нет.
            После работы с этим зопом я понял почему его так назвали.
            А «геморрой — это зопяная боль».
        • 0
          Были и есть более удачные реализации многомерных БД (и построенной поверх них объектности), к примеру www.cache.ru/
          да она коммерческая — но уже десятки лет ( а точнее раньше самой каше ) были и есть M системы ( а каше ей и является )
          и были умники которые говорили что реляционки теперь не нужны — сам был среди них.
          а теперь оглянитесь и посмотрите на чем сделана большая часть проектов.
      • +3
        > Все эти френдленты и плоские комментарии — явное следствие использования реляционных БД.
        Ага, какже. Каменты деревьями нереляционная база данных конечно построит сама ))) Гемороя будет в лучшем случае столько же.

        > JSON куда более природен для восприятия человеком, чем линейные выборки из реляционных БД.
        Как сказать, у меня в мозгу к сожалению не крутиться V8 или greaseMonkey чтоб json был понятней
        • +1
          В MongoDB деревья можно хранить прямо деревом ;-) То есть вкладывать объекты друг в друга.
          • +3
            ага а если дерево вдруг стало больше 4 метров мы увидим болт вместо каментов )))
            • 0
              Во-первых лимит можно повысить, во-вторых можно ID сообщений хранить в объекте, а тексты хранить в отдельной коллекции. Т.е. мы выдергиваем первым запросом нужную нам структуру, а затем уже выдергиваем одним запросом все нужные тексты, это даже быстрее будет работать, т.к. структура со ссылками на тексты будет совсем простая. Это нормальная практика — хранить дерево отдельно от данных.
              • 0
                А как повысить лимит без проблем? В официальной гуглгруппе создатели ничего такого не говорили…
        • 0
          V8 и greaseMonkey — это просто инструмент формирования нужной выборки. И он может быть любым, хоть Python, хоть Ruby, хоть даже Io language. Говоря человеческим языком, данные прогоняются через программу, которая отсеивает все лишнее и оставляет только нужное, которое потом складывается/добавляется в отдельную коллекцию, которая при последующем запросе отдается уже без протаскивания через «программный фильтр», а потому — достаточно быстро.
          JS-движки в качестве бэкендов применяются по умолчанию видимо потому, что JSON — это родной формат JS (JavascriptObjectNotation).
          • 0
            речь шла о восприятии человеком, у меня как у человека плохое восприятие json.
            • 0
              это не значит что json плох.
        • 0
          > Ага, какже. Каменты деревьями нереляционная база данных конечно построит сама )))
          Вообще JSON он на то и JSON, чтоб позволять хранить документ поста вместе с деревом комментариев и строить вообще ничего не придется. Но с таким подходом возникают уже другие проблемы, например, «одновременное» добавление комментариев, что по сути будет означать «одновременное» редактирование документа поста.
          • 0
            Это не проблема ;-) В MongoDB есть атомарный push в массив.
          • 0
            Можно хранить комменты отдельной сущностью и подтягивать вместе с постом одним запросом (это я про couchdb). Работать это будет исключительно быстро. Создание комментов ничего блокировать не будет, race condition тоже вызвать не получится.
    • 0
      На высоких нагрузках, думаю очень заменит скоро. Однако, сообщество инертно, и вряд ли стоит ожидать массового перехода в скором времени… mainstream весьма ленивая вещь.
  • 0
    >> Для многих, «база данных» твердо ассоциируется с MySQL, таблицами и SQL-запросами…

    У меня она ассоциируется с Oracle и Microsoft SQL Server.
    • 0
      Автор, имхо, немного неправильный порядок употребил. Логично или «таблицы, SQL, MySQL» (академический взгляд), или прямо наоборот (практический).
  • –6
    А вообще, статья уж больно похожа на рекламу.
    • +1
      Вы это всерьёз?
    • +5
      Ваш комментарий похож на самопиар :)
  • +1
    вопросы автору:
    1. почему именно MongoDB, а не Redis, например? ну, то есть ты (ничего, если на «ты»? заранее прошу прощения) смотрел сравнивал и выбрал в итоге mongo, или просто именно монго попалась под руку?
    2. а какая примерно нагрузка на проект, и сколько приходится на mongo?
    3. я так понял (код, правда, читал совсем бегло), что внутри phpdaemon :: appInstance кэшируются результаты из memcached, а сам memcached кэширует монгу. то есть слоёв кэширования два. зачем столько?
    и есть ли профит между mongo+memcached и просто mongo?
    • +1
      1. В статье упоминается Redis. Ничего. Я его очень конкретно изучал и юзал, даже свой драйвер написал. Redis однотредовый и убогий.
      2. Пока небольшая, однако тесты оптимистичные. Намного лучше чем на MySQL (с нее слезаю), хотя поверь, я далеко не новичок в MySQL.
      3. phpDaemon::MongoNode читает в реальном времени бинарной лог Mongo и бросает в memcached объекты в которых есть _key.
      Безусловно есть. Нельзя сравнивать производительность кластера memcached и любой другой базы данных, которая хранит данные на диске. Хотя я кеширование использую только для небольших горячих объектов которых в сумме метров на 10, их целесообразнее дергать из памяти.
      • 0
        > Redis однотредовый
        И что с этого? Там используется асинхронный способ работы с данными
        • +1
          Для того чтобы выжрать ресурсы Quad Xeon'а автор предлагает запустить 8 редисок и балансировать между ними по ключам:-)
          • 0
            Ради простоты внутренней архитектуры и быстродействия было решено сделать редис однопоточным. Он простой в понимании => простой в применении.

            С другой стороны, непонятно, зачем нагружать редис так, что нужны все 8 ядер? Этоже kv- _store_. Т.е. основное предназначение сохранять данные, а обрабатывать их должно приложение, которое уже может работать на нескольких потоках.
            • +1
              Я скажу банальщину, но пользователи нагружают, им этого не объяснишь. Ведь мы явно не в шину упрёмся. Я и не говорю про обработку, я говорю о get/set/increment.
  • НЛО прилетело и опубликовало эту надпись здесь
    • +1
      Значит, я добился своей цели :))
      • НЛО прилетело и опубликовало эту надпись здесь
        • 0
          Оффтоп, но чаты лучше писать с использованием RTEP (phpDaemon), без БД. Т.е. роутить события сразу, а не кидать в БД и потом проверять.
          Скоро выложу чат который держит сотни тысяч пользователей одновременно, как ejabberd прям :-)
          • НЛО прилетело и опубликовало эту надпись здесь
      • 0
        Но всё-таки основные преимущества в hi-load проектах и чисто по быстродействию в условиях масштабирования и множественных добавлений и изменений? Как насчёт простоты (особенно привыкшим к реляционным БД, не обязательно SQL ;) ) проектирования и реализации на уровне серверов приложений, что в «голом» SQL, что по сравнению с ORM «прокладками»? В общем «серебряная пуля» или нужно досконально знать все плюсы и минусы разных альтернатив, хотя бы на уровне ORM vs «объектно-документарная база данных» (не знаю как написать на инглише — гугл и рамблер дают ссылку только на этот топик — термин ваш лично? )
        • +1
          Для домашней странички можно использовать что угодно, однако я лично не вижу чем работа с Mongo сложнее написания SQL-запросов, в чем-то даже проще. Проектировать значительно проще, поскольку не надо думать о схеме и об изменениях в ней. В MySQL и иже с ним меня сильно демотивирует что каждый раз надо поле ручками добавлять или менять его тип.
          Да, термин мой, просто на мой взгляд, она и не объектная (это все же немного другое) и не документарная (не BigTable). Кстати я планирую написать парсер SQL-запросов и конвертатор в Mongo-запросы на лету: то есть просто подключаете этот слой и делаете например SELECT * FROM collection WHERE x > 1 AND y < 5. По большому счету ничего сложного.
          • НЛО прилетело и опубликовало эту надпись здесь
    • +1
      ага) особенно после слов «резкая как понос» ))
  • +2
    а ещё MongoDB может работать как database backend для Django — bitbucket.org/kpot/django-mongodb/
    • 0
      Я тоже обратил на это внимание :)
      Осталось понять насколько хорошо это будет работать. Все же делалось django с реляционными бэкендами, насколько хорошо оно будет работать с нераляционным? Конечно, делали его люди талантливые, и написано довольно абстрактно от хранилища. Но все же хотелось бы реальных тестов, насколько одно к другому подходит. Не вылезет ли там гигантский оверхед, который убьет затею на корню?
  • 0
    > либо делать партишенинг таблиц, разбивая таблицу на несколько частей и храня их в разных местах,
    > согласно заданному закону (например по ID), однако это унесет в могилу прелести JOIN

    А как эта проблема решена в монго? Он позволяет сделать некий JOIN данных между разными шардами?
    • 0
      Sharding Introduction
      Это тема второй, более подробной статьи на эту тему. Там я рассмотрю все эти аспекты вполне детально.
  • 0
    Сама БД клёвая, и я как-то тестировал ее, но, почему-то, получилось медленнее MySQL:
    blog.knopkodav.ru/2009/10/mongodb-vs-mysql.html

    Специально ни тот ни другой не настраивал, всё, можно сказать, из коробки.
    Что тут не так?
    • +1
      Коллекция в Mongo создается не при вызове mongo = mongo_db.collection(«beta»), а при первом вызове mongo.insert(doc). Ну и по умолчанию в Mongo большой pre-allocation места для коллекции, так что грубо говоря 4.999 создавался пустой файл размером порядка 2.5 гб (зависит от свободного места на разделе), а остальные 0.001 делались полезные операции.
      Создайте пустую коллекцию изначально, а потом протестируйте ;-) В init достаточно делать «mongo.remove».
      • 0
        Сделал как вы сказали, прописал:

        mongo = mongo_db.collection(«beta»)
        mongo.remove

        и всё равно:
        $ ruby mymongo.rb 
              user     system      total        real
        mysql:  0.300000   0.100000   0.400000 (  1.754915)
        mongodb:  5.910000   0.230000   6.140000 (  6.880819)
        

        :-/
        • 0
          А второй запуск?
          • 0
            (отписал в личку)
  • 0
    Нереалиационные БД хороши и быстры,
    однако реалицонность можно сделать нормально только с РСУБД.
    Хорошо что есть и те, и те :)
    А ещё лучше то, что есть такие как MySQL и TokyoCabinet
  • 0
    >В качестве уникального идентификатора используется не auto-increment'ное поле, а 12-байтное уникальное число, генерируемое на клиенте.

    А может 24-байтное?
    • 0
      ясн, 24-байтный HEX конвертится в 12-байтный BIN
  • 0
    Например, при использовании master-master, мы заплатим auto increment'ами.

    Не заплатим. Схема стара как мир. Например, пусть у нас два мастера. На первом стартовое значение делаем 1, на втором — 2 и на обоих шаг делаем в два. Всё.
  • 0
    Интересно, а вот спустя 6 лет, автор статьи не разочаровался в mongoDB?

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