/// <summary> /// Uses a database table, in order to manage queue items. The underlying database access is managed by pure T-SQL queries. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseSqlServerStorage(this WorkerHostOptions options) { options.ScheduledTaskStoreType = typeof(EFScheduledTaskStore <>); options.QueueStoreType = typeof(SqlServerMessageQueue <>); var serviceProvider = options.Services.BuildServiceProvider(); Action <DbContextOptionsBuilder> sqlServerConfiguration = builder => builder.UseSqlServer(serviceProvider.GetService <IConfiguration>().GetConnectionString("WorkerDb")); options.Services.AddDbContext <TaskDbContext>(sqlServerConfiguration); options.Services.AddScoped <IDbConnectionFactory>(x => new SqlServerConnectionFactory(serviceProvider.GetService <IConfiguration>().GetConnectionString("WorkerDb"))); return(options); }
/// <summary> /// Uses Azure Storage service as the store for distributed locking. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <param name="configureAction">Configure the azure options.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseAzureStorageLock(this WorkerHostOptions options, Action <LockManagerAzureOptions> configureAction = null) { options.Services.TryAddSingleton(typeof(ILockManager), serviceProvider => { var azureOptions = new LockManagerAzureOptions { StorageConnection = serviceProvider.GetService <IConfiguration>().GetConnectionString("StorageConnection"), EnvironmentName = serviceProvider.GetService <IHostEnvironment>().EnvironmentName }; configureAction?.Invoke(azureOptions); return(new LockManagerAzure(azureOptions)); }); return(options); }
/// <summary> /// Registers a hosted service that manages and configures the lifetime of background tasks. /// </summary> /// <param name="services">Specifies the contract for a collection of service descriptors.</param> /// <param name="configureAction">The delegate used to configure the worker host options.</param> /// <returns>The <see cref="WorkerHostBuilder"/> used to configure the worker host.</returns> public static WorkerHostBuilder AddWorkerHost(this IServiceCollection services, Action <WorkerHostOptions> configureAction) { var workerHostOptions = new WorkerHostOptions(services); configureAction.Invoke(workerHostOptions); services.AddSingleton(workerHostOptions.JsonOptions); var quartzConfiguration = new NameValueCollection { { "quartz.threadPool.maxConcurrency", "100" } }; services.AddSingleton <ISchedulerFactory>(serviceProvider => new StdSchedulerFactory(quartzConfiguration)); services.AddSingleton <IJobFactory, QuartzJobFactory>(); services.AddTransient <QuartzJobRunner>(); services.AddTransient <TaskHandlerActivator>(); services.AddHostedService <WorkerHostedService>(); return(new WorkerHostBuilder(services, workerHostOptions)); }
/// <summary> /// Uses a database table, in order to manage queue items. The underlying database access is managed by Entity Framework. /// If no <paramref name="configureAction"/> is provided, then SQL Server is used as a default provider. /// </summary> /// /// <typeparam name="TContext"></typeparam> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <param name="configureAction">The delegate used to configure the database table that contains the background jobs.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseEntityFrameworkStorage <TContext>(this WorkerHostOptions options, Action <DbContextOptionsBuilder> configureAction = null) where TContext : TaskDbContext { var isDefaultContext = typeof(TContext) == typeof(TaskDbContext); var serviceProvider = options.Services.BuildServiceProvider(); Action <DbContextOptionsBuilder> sqlServerConfiguration = builder => builder.UseSqlServer(serviceProvider.GetService <IConfiguration>().GetConnectionString("WorkerDb")); configureAction = configureAction ?? sqlServerConfiguration; options.Services.AddDbContext <TContext>(configureAction); options.Services.AddDbContext <LockDbContext>(configureAction); if (!isDefaultContext) { options.Services.AddScoped <TaskDbContext, TContext>(); } options.ScheduledTaskStoreType = typeof(EFScheduledTaskStore <>); options.QueueStoreType = typeof(EFMessageQueue <>); options.LockStoreType = typeof(SqlServerLockManager); options.Services.AddTransient <ILockManager, SqlServerLockManager>(); return(options); }
/// <summary> /// Uses the tables of a relational database in order to manage queue items. /// </summary> /// <typeparam name="TContext">The type of <see cref="DbContext"/>.</typeparam> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <param name="configureAction">The delegate used to configure the database table that contains the background jobs.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseStoreRelational <TContext>(this WorkerHostOptions options, Action <DbContextOptionsBuilder> configureAction = null) where TContext : TaskDbContext { var isDefaultContext = typeof(TContext) == typeof(TaskDbContext); var connectionString = options.Services.BuildServiceProvider().GetService <IConfiguration>().GetConnectionString("WorkerDb"); void sqlServerConfiguration(DbContextOptionsBuilder builder) => builder.UseSqlServer(connectionString); configureAction ??= sqlServerConfiguration; options.Services.AddDbContext <TContext>(configureAction); options.Services.AddDbContext <LockDbContext>(configureAction); if (!isDefaultContext) { options.Services.TryAddScoped <TaskDbContext, TContext>(); } options.ScheduledTaskStoreType = typeof(RelationalScheduledTaskStore <>); options.QueueStoreType = typeof(RelationalMessageQueue <>); options.LockStoreType = typeof(RelationalLockManager); options.UseLockManager <RelationalLockManager>(); return(options); }
/// <summary> /// Registers a hosted service that manages and configures the lifetime of background tasks. /// </summary> /// <param name="services">Specifies the contract for a collection of service descriptors.</param> /// <param name="configureAction">The delegate used to configure the worker host options.</param> /// <returns>The <see cref="WorkerHostBuilder"/> used to configure the worker host.</returns> public static WorkerHostBuilder AddWorkerHost(this IServiceCollection services, Action <WorkerHostOptions> configureAction = null) { var serviceProvider = services.BuildServiceProvider(); var builderInstance = serviceProvider.GetService <WorkerHostBuilder>(); if (builderInstance is not null) { return(builderInstance); } var workerHostOptions = new WorkerHostOptions(services) { ScheduledTaskStoreType = typeof(NoOpScheduledTaskStore <>), QueueStoreType = typeof(NoOpMessageQueue <>), LockStoreType = typeof(LockManagerNoop) }; configureAction?.Invoke(workerHostOptions); services.AddSingleton(workerHostOptions.JsonOptions); var quartzConfiguration = new NameValueCollection { { "quartz.threadPool.maxConcurrency", "100" }, { "quartz.threadPool.threadCount", "100" } }; services.AddSingleton <ISchedulerFactory>(serviceProvider => new StdSchedulerFactory(quartzConfiguration)); services.AddSingleton <IJobFactory, QuartzJobFactory>(); services.AddTransient <QuartzJobRunner>(); services.AddTransient <TaskHandlerActivator>(); services.AddLockManagerNoop(); var configuration = serviceProvider.GetRequiredService <IConfiguration>(); if (!configuration.WorkerHostDisabled()) { services.AddHostedService <WorkerHostedService>(); } var builder = new WorkerHostBuilder(services, workerHostOptions); services.AddSingleton(builder); return(builder); }
/// <summary> /// Registers an implementation of <see cref="ILockManager"/> which is used for distributed locking. /// </summary> /// <typeparam name="TLockManager">The concrete type of <see cref="ILockManager"/> to use.</typeparam> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseLockManager <TLockManager>(this WorkerHostOptions options) where TLockManager : ILockManager { options.Services.AddScoped(typeof(ILockManager), typeof(TLockManager)); return(options); }
/// <summary> /// Manages access to queues using an in-memory mechanism. Not suitable for distributed scenarios. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseLockManagerInMemory(this WorkerHostOptions options) { options.Services.AddLockManagerInMemory(); return(options); }
/// <summary> /// Uses Azure Storage service as the store for distributed locking. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <param name="configureAction">Configure the azure options.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseLockManagerAzure(this WorkerHostOptions options, Action <IServiceProvider, LockManagerAzureOptions> configureAction = null) { options.Services.AddLockManagerAzure(configureAction); return(options); }
/// <summary> /// Uses the tables of a relational database in order to manage queue items. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <param name="configureAction">The delegate used to configure the database table that contains the background jobs.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseStoreRelational(this WorkerHostOptions options, Action <DbContextOptionsBuilder> configureAction = null) => options.UseStoreRelational <TaskDbContext>(configureAction);
/// <summary> /// Registers an implementation of <see cref="ILockManager"/> which is used for distributed locking. /// </summary> /// <typeparam name="TLockManager">The concrete type of <see cref="ILockManager"/> to use.</typeparam> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <param name="implementationFactory">The factory that creates the service.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseLockManager <TLockManager>(this WorkerHostOptions options, Func <IServiceProvider, TLockManager> implementationFactory) where TLockManager : ILockManager { options.Services.AddScoped(typeof(ILockManager), serviceProvider => implementationFactory(serviceProvider)); return(options); }
/// <summary> /// Uses an in-memory storage mechanism in order to manage queue items. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseInMemoryStorage(this WorkerHostOptions options) => throw new NotImplementedException();
/// <summary> /// Registers an implementation of <see cref="ILockManager"/> which is used for distributed locking. /// </summary> /// <typeparam name="TLockManager">The concrete type of <see cref="ILockManager"/> to use.</typeparam> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseLock <TLockManager>(this WorkerHostOptions options) where TLockManager : ILockManager { options.Services.TryAddSingleton(typeof(ILockManager), typeof(TLockManager)); return(options); }
/// <summary> /// Manages access to queues using an in-memory mechanism. Not suitable for distributed scenarios. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseInMemoryLock(this WorkerHostOptions options) => options.UseLock <LockManagerInMemory>();
/// <summary> /// Uses a database table, in order to manage queue items. If no <paramref name="configureAction"/> is provided, then SQL Server is used as a default provider. /// </summary> /// <param name="options">The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</param> /// <param name="configureAction">The delegate used to configure the database table that contains the background jobs.</param> /// <returns>The <see cref="WorkerHostOptions"/> used to configure locking and queue persistence.</returns> public static WorkerHostOptions UseEntityFrameworkStorage(this WorkerHostOptions options, Action <DbContextOptionsBuilder> configureAction = null) => UseEntityFrameworkStorage <TaskDbContext>(options, configureAction);