Finbuckle.
Configuration and Usage
Configuration
Finbuckle.MultiTenant uses the standard application builder pattern for its configuration. In addition to adding the services, configuration for one or more MultiTenant Stores and MultiTenant Strategies are required:
using Finbuckle.MultiTenant;
var builder = WebApplication.CreateBuilder(args);
// ...add app services
// add Finbuckle.MultiTenant services
builder.Services.AddMultiTenant<TenantInfo>()
.WithHostStrategy()
.WithConfigurationStore();
var app = builder.Build();
// add the Finbuckle.MultiTenant middleware
app.UseMultiTenant();
// ...add other middleware
app.Run();
Adding the Finbuckle.MultiTenant Service
Use the AddMultiTenant<TTenantInfo> extension method on IServiceCollection to register the basic dependencies
needed by the library. It returns a MultiTenantBuilder<TTenantInfo> instance on which the methods below can be called
for further configuration. Each of these methods returns the same MultiTenantBuilder<TTenantInfo> instance allowing
for chaining method calls.
Configuring the Service
WithStore Variants
Adds and configures an IMultiTenantStore to the application. Only the last store configured will be used. See MultiTenant Stores for more information on each type.
WithStore<TStore>WithInMemoryStore<TTenantStore>WithConfigurationStore<TTenantStore>WithEFCoreStore<TTenantStore>WithDistributedCacheStore<TTenantStore>WithHttpRemoteStore<TTenantStore>
WithStrategy Variants
Adds and configures an IMultiTenantStrategy to the application. Multiple strategies can be configured and each will be used in the order registered. See MultiTenant Strategies for more information on each type.
WithStrategy<TStrategy>WithBasePathStrategyWithClaimStrategyWithDelegateStrategyWithHeaderStrategyWithHostStrategyWithRouteStrategyWithSessionStrategyWithStaticStrategy
WithPerTenantAuthentication
Configures support for per-tenant authentication. See Per-Tenant Authentication for more details.
Per-Tenant Options
Finbuckle.MultiTenant integrates with the standard .NET Options pattern (see also the ASP.NET Core Options pattern and lets apps customize options distinctly for each tenant. See Per-Tenant Options for more details.
Tenant Resolution
Most of the capability enabled by Finbuckle.MultiTenant is utilized through its middleware and use the Options pattern with per-tenant options. For web applications the middleware will resolve the app's current tenant on each request using the configured strategies and stores, and the per-tenant options will alter the app's behavior as dependency injection passes the options to app components.
Getting the Current Tenant
There are several ways an app can see the current tenant:
Dependency Injection
IMultiTenantContextAccessorandIMultiTenantContextAccessor<TTenantInfo>are available via dependency injection and behave similar toIHttpContextAccessor. Internally anAsyncLocal<T>is used to track state and in parent async contexts any changes in tenant will not be reflected. For example, the accessor will not reflect a tenant in the post-endpoint processing in ASP.NET Core middleware registered prior toUseMultiTenant. Use theHttpContextextensionGetMultiTenantContext<TTenantInfo>to avoid this caveat.IMultiTenantContextSetteris available via dependency injection and can be used to set the current tenant. This is useful in advanced scenarios and should be used with caution. Prefer using theHttpContextextension methodTrySetTenantInfo<TTenantInfo>in use cases whereHttpContextis available.
Prior versions of Finbuckle.MultiTenant also exposed
IMultiTenantContext,ITenantInfo, and their implementations via dependency injection. This was removed as these are not actual services, similar to how HttpContext is not a service and not available directly via dependency injection.
HttpContext Extension Methods
For web apps these convenience methods are also available:
GetMultiTenantContext<TTenantInfo>Use this
HttpContextextension method to get theMultiTenantContext<TTenantInfo>instance for the current request. This should be preferred toIMultiTenantContextAccessororIMultiTenantContextAccessor<TTenantInfo>when possible.var tenantInfo = HttpContext.GetMultiTenantContext<TenantInfo>().TenantInfo; if(tenantInfo != null) { var tenantId = tenantInfo.Id; var identifier = tenantInfo.Identifier; var name = tenantInfo.Name; var something = tenantInfo.Items["something"]; }TrySetTenantInfo<TTenantInfo>For most cases the middleware sets the
TenantInfoand this method is not needed. Use only if explicitly overriding theTenantInfoset by the middleware.Use this
HttpContextextension method to set the current tenant to the providedTenantInfo. Returns true if successful. Optionally it can also reset the service provider scope so that any scoped services already resolved will be resolved again under the current tenant when needed. This has no effect on singleton or transient services. Setting theTenantInfowith this method sets both theStoreInfoandStrategyInfoproperties on theMultiTenantContext<TTenantInfo>tonull.var newTenantInfo = new TenantInfo(...); if(HttpContext.TrySetTenantInfo(newTenantInfo, resetServiceProvider: true)) { // This will be the new tenant. var tenant = HttpContext.GetMultiTenantContext().TenantInfo; // This will regenerate the options class. var optionsProvider = HttpContext.RequestServices.GetService<IOptions<MyScopedOptions>>(); }