Подходы SaaS/Multi-Tenancy для веб-приложений на основе Java (GWT, Spring, Hibernate)

В настоящее время я изучаю преобразование однопользовательского веб-приложения на основе Java, которое использует Spring, GWT, Hibernate, Jackrabbit, Hibernate Search/Lucene (среди прочих) в полноценное приложение стиля SaaS.

Я наткнулся на статью, в которой подчеркиваются следующие 7 "вещей" как важные изменения, сделанные для одного приложения-арендатора, чтобы сделать его SaaS-приложением:

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

Мой вопрос: кто-нибудь выполнил любую из вышеуказанных 7 вещей в приложении SaaS/multi-tenant, используя аналогичные технологии для тех, которые я перечислил? Я очень хочу получить столько информации о наилучших способах сделать это, прежде чем я пойду по тому пути, который я сейчас рассматриваю.

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

У меня, однако, есть некоторые проблемы с производительностью, особенно когда наше количество арендаторов растет довольно высоко.

Любые предложения о том, как реализовать такое решение, будут очень благодарны (и я приношу свои извинения, если этот вопрос слишком открыт).

4 ответа

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

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

  • настройка уровня арендатора a) темы и логотипы пользовательского интерфейса; б) формы и сетки; в) расширения модели данных и настраиваемые поля; d) шаблоны уведомлений; д) сбор списков и основных данных.
  • уровень арендатора и управление ролями и привилегиями, разрешения доступа на уровне поля, политики области данных
  • Настройки контроля доступа уровня арендатора для модулей и функций, чтобы определенные модули и функции могли быть включены/отключены в зависимости от пакета подписки.
  • Измерение и мониторинг задач/событий/транзакций и ограничение контроля доступа после превышения покупной квоты. Возможность отслеживать любое новое лицо в будущем, если и когда ваша бизнес-модель изменится.
  • Внешние бизнес-правила и рабочие процессы выходят из вашей базы кода и представляют их как метаданные, поэтому вы можете настроить их для каждой группы арендаторов/арендаторов.
  • Создатель запросов для создания настраиваемых отчетов, которые знают о арендаторе, а также настраиваемые поля, добавленные отдельными арендаторами.
  • Связывание с инкапсуляцией арендаторов и управление строками уровня уровня, так что вашим разработчикам не нужно беспокоиться о идентификаторах арендаторов при написании запросов.

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

Но технические потребности любого многопользовательского SaaS-продукта (нового или перенесенного) одинаковы независимо от используемого вами технологического стека.


Все перечисленные вами технологии довольно распространены и разумны для приложений с одним и несколькими арендаторами. Я бы сказал, что поддержка 7 "вещей" для SaaS намного больше зависит от того, как вы используете технологии, чем это. Похоже, у вас уже есть приложение с одним арендатором, которое работает. Поэтому, вероятно, не так много причин отклоняться от выбора технологий там, если только что-то не работает уже очень хорошо. В противном случае ваш вопрос будет довольно открытым, так что здесь трудно быть более конкретным.

У меня есть некоторые отзывы о разделении базы данных (и, возможно, других вещей) на идентификатор арендатора. Если вы знаете, что в конечном итоге у вас может быть много арендаторов (скажем, много тысяч или более, особенно если они маленькие), то, по вашему мнению, возможно, лучше всего. Если, однако, у вас будет меньшее количество арендаторов (особенно если они большие), вы можете захотеть рассмотреть базу данных на каждого арендатора, поэтому у каждого из них есть собственное табличное пространство. Под этим я подразумеваю единую установку базы данных с несколькими экземплярами одной и той же схемы внутри нее, по одному на каждого арендатора.

Есть несколько причин, по которым это может быть преимуществом. Один из них - это производительность, о которой вы говорили. Добавление идентификатора арендатора в каждую отдельную таблицу является накладными расходами на доступ к диску, временем запроса и увеличением сложности кода. Каждый индекс в базе данных должен также включать идентификатор арендатора. У вас возникает дополнительный риск смешивания данных между арендаторами, если вы не будете осторожны (хотя фильтр Hibernate поможет смягчить это). С базой данных для каждого арендатора вы можете ограничить доступ только к правильному. Портирование вашего текущего приложения, вероятно, будет намного проще, вам просто нужно перехватить ваш запрос где-нибудь раньше, чтобы определить арендатора на основе URL-адреса и указать правильную базу данных. Резервные копии также легко выполняются для каждого арендатора, особенно полезны, если вы когда-либо планируете загрузить резервную копию.

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

Конечно, это зависит от вашего случая использования. Вы упомянули одного арендатора, который заставляет меня думать, что у вас сейчас слишком мало арендаторов, однако вы говорите, что растет много арендаторов. Я не уверен, если вы имеете в виду сотни или миллионы, но в любом случае я надеюсь, что это поможет некоторым вашим соображениям. Удачи!


Нет простого ответа. Я могу описать свое собственное решение. Это может послужить источником вдохновения для других.

  • арендатор на базу данных (postgres)
  • одна дополнительная база данных, разделяемая между арендаторами
  • Spring + MyBatis
  • Spring Аутентификация по безопасности

Подробности здесь: http://blog.trixi.cz/2012/01/multitenancy-using-spring-and-postgresql/


Для (1): Hibernate поддерживает многопользовательские конфигурации из коробки с версии 4. На момент написания поддержки поддерживаются DB-per-tenant и schema-per-tenant, и сохранение всех арендаторов в одной и той же БД с использованием дискриминатора пока не поддерживается. Мы успешно использовали эту функциональность в нашем приложении (подход DB-per-client).

Для (3): после некоторого расследования мы решили пойти с Braintree для осуществления выставления счетов. Другие решения, рекомендуемые многими людьми: Authorize.net, Stripe, PayPal.

Для (4): мы использовали кластерную конфигурацию с Hibernate/ Spring и JBoss Cache для кэширования второго уровня. В эти дни это стало "общим" и, используя сервисы PaaS, такие как Jelastic, вы даже можете настроить его заранее.

licensed under cc by-sa 3.0 with attribution.