private static IFhirServerBuilder AddCosmosDbPersistence()

in src/Microsoft.Health.Fhir.CosmosDb/Registration/FhirServerBuilderCosmosDbRegistrationExtensions.cs [55:231]


        private static IFhirServerBuilder AddCosmosDbPersistence(this IFhirServerBuilder fhirServerBuilder, Action<CosmosDataStoreConfiguration> configureAction = null)
        {
            IServiceCollection services = fhirServerBuilder.Services;

            if (services.Any(x => x.ImplementationType == typeof(CosmosContainerProvider)))
            {
                return fhirServerBuilder;
            }

            services.Add(provider =>
                {
                    var config = new CosmosDataStoreConfiguration();
                    provider.GetService<IConfiguration>().GetSection("CosmosDb").Bind(config);
                    configureAction?.Invoke(config);
                    return config;
                })
                .Singleton()
                .AsSelf();

            services.Add<CosmosContainerProvider>()
                .Singleton()
                .AsSelf()
                .AsService<IHostedService>() // so that it starts initializing ASAP
                .AsService<IRequireInitializationOnFirstRequest>(); // so that web requests block on its initialization.

            services.Add<CosmosClientReadWriteTestProvider>()
                .Singleton()
                .AsService<ICosmosClientTestProvider>();

            // Register Container
            // We are intentionally not registering Container directly, because
            // we want this codebase to support different configurations, where the
            // lifetime of the document clients can be managed outside of the IoC
            // container, which will automatically dispose it if exposed as a scoped
            // service or as transient but consumed from another scoped service.

            services.Add<IScoped<Container>>(sp => sp.GetService<CosmosContainerProvider>().CreateContainerScope())
                .Transient()
                .AsSelf()
                .AsFactory();

            services.Add<CosmosQueryFactory>()
                .Singleton()
                .AsService<ICosmosQueryFactory>();

            services.Add<CosmosDbDistributedLockFactory>()
                .Singleton()
                .AsService<ICosmosDbDistributedLockFactory>();

            services.Add<RetryExceptionPolicyFactory>()
                .Singleton()
                .AsSelf();

            services.AddTransient<IConfigureOptions<CosmosCollectionConfiguration>>(
                provider => new ConfigureNamedOptions<CosmosCollectionConfiguration>(
                    Constants.CollectionConfigurationName,
                    cosmosCollectionConfiguration =>
                    {
                        var configuration = provider.GetRequiredService<IConfiguration>();
                        configuration.GetSection("FhirServer:CosmosDb").Bind(cosmosCollectionConfiguration);
                        if (string.IsNullOrWhiteSpace(cosmosCollectionConfiguration.CollectionId))
                        {
                            IModelInfoProvider modelInfoProvider = provider.GetRequiredService<IModelInfoProvider>();
                            cosmosCollectionConfiguration.CollectionId = modelInfoProvider.Version == FhirSpecification.Stu3 ? "fhir" : $"fhir{modelInfoProvider.Version}";
                        }
                    }));

            services.Add<CosmosFhirDataStore>()
                .Scoped()
                .AsSelf()
                .AsImplementedInterfaces();

            services.Add<CosmosTransactionHandler>()
                .Scoped()
                .AsSelf()
                .AsImplementedInterfaces();

            services.Add<CollectionUpgradeManager>()
                .Singleton()
                .AsSelf()
                .AsService<IUpgradeManager>();

            services.Add<CosmosQueryLogger>()
                .Singleton()
                .AsService<ICosmosQueryLogger>();

            services.Add<CollectionInitializer>(sp =>
                {
                    var config = sp.GetService<CosmosDataStoreConfiguration>();
                    var upgradeManager = sp.GetService<CollectionUpgradeManager>();
                    var retryExceptionPolicyFactory = sp.GetService<RetryExceptionPolicyFactory>();
                    var loggerFactory = sp.GetService<ILoggerFactory>();
                    var cosmosClientTestProvider = sp.GetService<ICosmosClientTestProvider>();
                    var namedCosmosCollectionConfiguration = sp.GetService<IOptionsMonitor<CosmosCollectionConfiguration>>();
                    var cosmosCollectionConfiguration = namedCosmosCollectionConfiguration.Get(Constants.CollectionConfigurationName);

                    return new CollectionInitializer(
                        cosmosCollectionConfiguration,
                        config,
                        upgradeManager,
                        retryExceptionPolicyFactory,
                        cosmosClientTestProvider,
                        loggerFactory.CreateLogger<CollectionInitializer>());
                })
                .Singleton()
                .AsService<ICollectionInitializer>();

            services.Add<FhirCollectionSettingsUpdater>()
                .Transient()
                .AsService<ICollectionUpdater>();

            services.Add<StoredProcedureInstaller>()
                .Transient()
                .AsService<ICollectionUpdater>();

            services.Add<CosmosDbSearchParameterStatusInitializer>()
                .Transient()
                .AsService<ICollectionUpdater>();

            services.TypesInSameAssemblyAs<IStoredProcedure>()
                .AssignableTo<IStoredProcedure>()
                .Singleton()
                .AsSelf()
                .AsService<IStoredProcedure>();

            services.Add<CosmosFhirOperationDataStore>()
                .Scoped()
                .AsSelf()
                .AsImplementedInterfaces();

            services.Add<FhirCosmosClientInitializer>()
                .Singleton()
                .AsService<ICosmosClientInitializer>();

            services.Add<CosmosResponseProcessor>()
                .Singleton()
                .AsSelf()
                .AsImplementedInterfaces();

            services.Add<CosmosDbSearchParameterStatusDataStore>()
                .Singleton()
                .AsSelf()
                .ReplaceService<ISearchParameterStatusDataStore>();

            // Each CosmosClient needs new instances of a RequestHandler
            services.TypesInSameAssemblyAs<FhirCosmosClientInitializer>()
                .AssignableTo<RequestHandler>()
                .Transient()
                .AsService<RequestHandler>();

            // FhirCosmosClientInitializer is Singleton, so provide a factory that can resolve new RequestHandlers
            services.AddFactory<IEnumerable<RequestHandler>>();

            services.Add<ReindexJobCosmosThrottleController>()
                .Transient()
                .AsImplementedInterfaces();

            services.Add<CosmosDbCollectionPhysicalPartitionInfo>()
                .Singleton()
                .AsSelf()
                .AsImplementedInterfaces();

            services.Add<QueryPartitionStatisticsCache>()
                .Singleton()
                .AsSelf()
                .AsImplementedInterfaces();

            services.Add<PurgeOperationCapabilityProvider>()
                .Transient()
                .AsImplementedInterfaces();

            services.Add<CompartmentSearchRewriter>()
                .Singleton()
                .AsService<ICosmosExpressionRewriter>();

            return fhirServerBuilder;
        }