Azure CosmosDB и один синглтон для нескольких классов - PullRequest
1 голос
/ 12 января 2020

Теория: Итак, в моей попытке всегда улучшаться, я столкнулся с этой загадкой. Ниже приведен код существующего кода. Насколько я понимаю, приложение будет создавать отдельное соединение для каждого из следующих синглетонов. Поскольку все они указывают на один и тот же экземпляр, я совершенно уверен, что если вы нажмете на индекс, в котором есть 2 из этих классов, использование Cosmos DB будет больше.

Вопрос: Можете ли вы сократить использование следующих одноэлементных объявлений универсальный c объект T, так что вы можете использовать один синглтон против N + 1?

        services.AddSingleton<IDocumentDBRepository<Car>>(new DocumentDBRepository<Car>("Database"));
        services.AddSingleton<IDocumentDBRepository<House>>(new DocumentDBRepository<House>("Database"));
        services.AddSingleton<IDocumentDBRepository<Employer>>(new DocumentDBRepository<Employer>("Database"));
        services.AddSingleton<IDocumentDBRepository<Photo>>(new DocumentDBRepository<Photo>("Database"));

Также, если у вас есть альтернативное предложение для меня или что-то еще, чтобы посмотреть, пожалуйста, сообщите я могу исследовать это также!

Ответы [ 2 ]

1 голос
/ 13 января 2020

У вас, кажется, есть несколько вопросов:

A) Ваше использование Космоса зависит только от вызовов, которые вы делаете в базу данных, и не зависит от того, сколько сервисов вы создаете для доступа к база данных.

B) Глядя на ваш код, кажется, что вы используете Microsoft.Extensions.DependencyInjection. Эта структура поддерживает открытые генерики, которые теоретически могут сократить ваши четыре одноэлементные регистрации до одной регистрации с использованием открытого универсального типа c. Что-то вроде:

.AddSingleton(typeof(IDocumentDBRepository<>), typeof(DocumentDBRepository<>)

Здесь тип сервиса open generi c равен IDocumentDBRepository<>, а тип реализации - DocumentDBRepository<>. Когда инфраструктура внедрения зависимостей должна создать службу IDocumentDBRepository<Car>, она создаст экземпляр DocumentDBRepository<Car>. Это означает, что все еще будет экземпляр репозитория для каждого указанного c типа документа (Car, House et c.), Но вам не нужно внедрять службу для каждого указанного типа c.

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

public interface IDocumentDBRepositoryFactory<T>
{
    IDocumentDBRepository<T> Create(string databaseName);
}

И реализацию:

internal class DocumentDBRepositoryFactory<T>
{
    public IDocumentDBRepository<T> Create(string databaseName)
        => return new DocumentDBRepository(databaseName);
}

Затем вы регистрируете эту фабрику (используя открытые обобщения):

.AddSingleton(typeof(IDocumentDBRepositoryFactory<>), typeof(DocumentDBRepositoryFactory<>)

Теперь потребителям репозиториев придется использовать экземпляр IDocumentDBRepositoryFactory<T>, вызывать метод Create и указывать имя базы данных, чтобы получить действительный экземпляр IDocumentDBRepository<T>. Другой вариант - избавиться от аргумента databaseName для фабричного метода и вместо этого сконфигурировать экземпляр фабрики для его предоставления (предположительно из конфигурации).

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

1 голос
/ 13 января 2020

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

Однако я не думаю, что вы должны это делать. Потому что счетчик использования CosmosDB основан на RU, а не на соединении. Ссылка для Цены CosmosDB

Azure Счета Cosmos DB за предоставленную пропускную способность и потребленное хранилище по часам.

Предоставленная пропускная способность выражается в единицах запроса в секунду (RU / s), который может использоваться для различных операций с базой данных (например, вставки, чтения, замены, загрузки, удаления, запросов и т. Д. c.). Например, 1 RU / s достаточно для обработки одной в конечном итоге согласованной операции чтения в секунду для элемента 1K, а 5 RU / s достаточно для обработки одной записи в секунду для элемента 1K.

За хранение взимается плата за каждый ГБ используется для данных и индекса на основе SSD.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...