Суть шардинга в том, что приложение должно знать, какой шард запрашивать. Как правило, это делается путем шардинга на что-то вроде клиента. Я адаптирую один из моих старых постов в блоге, чтобы использовать его в качестве ответа.
Когда вы создаете приложение для большого количества клиентов, есть два распространенных способа проектирования баз данных:
- Вариант А: Поместите всех клиентов в одну базу данных.
- Вариант 2: создать одну базу данных для каждого клиента
Поместить всех клиентов в одну базу данных
Все просто: просто добавьте таблицу Client в верхней части схемы, добавьте таблицу ClientUsers, чтобы люди могли видеть только свои данные, и все, и мы начнем.
Преимущества этого подхода:
Более простое управление схемами. Когда разработчики развертывают новую версию приложения, они должны вносить изменения схемы только в одну базу данных. Не стоит беспокоиться о том, что разные клиенты не синхронизированы или имеют неправильную версию.
Более простая настройка производительности. Мы можем проверить использование индексов и статистику в одном месте, легко внедрить улучшения и сразу увидеть результаты для всех наших клиентов. С сотнями или тысячами баз данных даже малейшее изменение может быть сложно координировать. Мы можем проверить содержимое кэша наших процедур и точно знать, какие запросы или хранимые процедуры наиболее интенсивны во всем нашем приложении, в то время как если мы используем отдельные базы данных для каждого клиента, у нас может быть более сложное использование запросов агрегации во времени для разных планов выполнения.
Проще построить внешний API. Если нам нужно предоставить доступ ко всей нашей базе данных для посторонних для создания продуктов, мы можем сделать это проще, если все данные находятся в одной базе данных. Если API имеет дело с группировкой данных из нескольких баз данных на нескольких серверах, это увеличивает время разработки и тестирования. (С другой стороны, эта вещь «несколько серверов» начинает намекать на ограничение для сценария «одна база данных - правило их всех»: одна база данных обычно означает, что вся наша нагрузка влияет только на один сервер базы данных.) В вашем случае Благодаря PowerBI все в одной базе данных значительно упростят управление соединениями.
Более высокая доступность и аварийное восстановление. Управлять зеркальным отображением базы данных, доставкой журналов, репликацией и кластеризацией действительно очень просто, если все, о чем нам нужно беспокоиться - это только одна база данных. Мы можем быстро построить инфраструктуру.
Помещение каждого клиента в его собственную базу данных или шард
Вам по-прежнему нужен список клиентов, но теперь он становится каталогом - для каждого клиента вы также отслеживаете фрагмент, в котором он находится. При запуске ваше приложение запрашивает эту таблицу и кэширует ее в ОЗУ. Когда ему нужны данные для клиента, он подключается напрямую к этому фрагменту (базе данных и серверу).
Преимущества этого подхода:
Более простое восстановление для одного клиента. Клиенты ненадежные мясные пакеты. (За исключением моего - они надежные мешки с мясом.) У них есть все виды «упс», когда они хотят получить все свои данные в определенный момент времени, и это огромная боль в тылу, если их данные смешаны с другие данные клиента в тех же таблицах. Восстановление в сценарии с базой данных с одним клиентом невероятно просто: просто восстановите базу данных клиента. Никто не затронут.
Более простой экспорт данных. Клиенты любят получать свои данные. Они хотят, чтобы они знали, что могут получить свои данные в любое время, избегая страшного сценария блокировки поставщиков, и хотят создавать свои собственные отчеты. Поскольку данные каждого клиента изолированы в их собственной базе данных, мы можем просто дать им копию их собственной резервной копии базы данных. Нам не нужно создавать API экспорта данных.
Более простая масштабируемость на нескольких серверах. Когда нашему приложению требуется больше энергии, чем мы можем получить от одного сервера, мы можем разделить базы данных между несколькими серверами. Мы также можем распределить нагрузку географически, сделав серверы в Азии или Европе ближе к клиентам.
Более простая настройка производительности для каждого клиента. Если некоторые клиенты используют разные функции или отчеты, мы можем создать специализированный набор индексов или индексированных представлений только для этих клиентов, не увеличивая объем данных каждого. Конечно, здесь есть некоторый риск - допустив различия в схемах между клиентами, мы просто сделали наши развертывания кода немного более рискованными, а управление производительностью - более сложным.
Более простое управление безопасностью. Пока мы правильно заблокировали безопасность с одним пользователем на базу данных, нам не нужно беспокоиться о клиенте X, обращающемся к данным клиента Y. Однако, если мы просто используем один логин для всех, тогда мы не решаем эту проблему.
Более легкое обслуживание окон. В глобальной среде, где клиенты разбросаны по всему миру, проще перевести клиентов в автономный режим для обслуживания, если мы можем сделать это в группах или зонах.
Какой из них подходит вам?
Нет единственно правильного выбора: вы должны знать сильные и слабые стороны своей компании. Давайте возьмем двух моих клиентов в качестве примеров.
Компания А выделяется в настройке производительности оборудования. Они действительно очень хороши в том, чтобы выжать из оборудования самую последнюю часть производительности, и они не возражают против замены своего оборудования SQL Server в течение 12-18 месяцев. (Они обновляют веб-серверы каждые 4-6 месяцев!) Их ахиллесова пята - экстремальные требования к соблюдению требований и безопасности. У них невероятные потребности в аудите, и им просто легче реализовать пуленепробиваемые элементы управления на одном сервере, в одной базе данных, чем управлять этими требованиями в тысячах баз данных на десятках серверов. Они выбрали одну базу данных, один сервер, много клиентов.
Компания 2 отлично справляется с разработками. Управление изменениями схемы и развертыванием кода в тысячах баз данных для них не является проблемой. У них есть клиенты по всему миру, и они круглосуточно обрабатывают транзакции по кредитным картам для этих клиентов. Им нужна возможность распределять нагрузку географически, и они не хотят заменять серверы по всему миру каждые 12-18 месяцев. Они выбрали одну базу данных для каждого клиента, и это окупается, когда они начинают устанавливать SQL Server в Азии и Европе для своих оффшорных клиентов.
Еще одно соображение я еще не видел в других ответах.
Наличие дизайна, который учитывает много арендаторов в единой базе данных, даст гибкость позже. Если требования загрузки / масштабирования / безопасности / геолокации позже предполагают, что у арендатора должна быть отдельная база данных, ее можно создать путем восстановления правильной БД в новом экземпляре. Данные других арендаторов по-прежнему защищены какими бы то ни было механизмами. Устаревшие данные могут быть удалены по частям как из старых, так и из новых баз данных, если позволяет время.
Обратное неверно. Консолидация многих баз данных с одним арендатором потребует значительно больше работы.
источник
Одна практика, которая делает мультитенантные модели намного проще, даже если это нарушает нормализацию *, - это включение столбца в каждую таблицу для арендатора. Вы могли бы назвать это TenantID. Таким образом, каждый запрос, выполняемый к базе данных, может фильтроваться по TenantID для каждой таблицы, и вы можете использовать разбиение базы данных, чтобы изолировать данные для каждого арендатора и ускорить запросы путем выравнивания разделов. Гораздо проще иметь всех арендаторов в одной базе данных таким образом.
* Это не всегда нарушает нормализацию, но может. Например, если у вас есть
Person
иPersonAddress
таблица.Person
Таблица будет иметь вTenantID, PersonID
качестве первичного ключа.PersonAddress
Таблица будет иметь вTenantID, PersonID, AddressTypeID
качестве первичного ключа с тем, что я предлагаю.Обычно
PersonID
этого будет достаточно, потому что вы можете присоединить это кPerson
таблице и найтиTenant
. Я предлагаю вам перенестиTenantID
на каждую последующую таблицу, даже когда сработает более тонкий ключ.Насколько я понимаю, перенос любой информации в таблицу, которая может быть получена из других данных, считался нарушением нормализации. Но, возможно, использование тонких клавиш - это просто лучшая практика.
источник