Skip to content
Tracon

MutableTenantContext

Namespace Tracon.Testing.Contracts.Storage · Assembly Tracon.Testing.Contracts.Xunit.dll

An ITenantContext whose tenant can be swapped at run time.

public sealed class MutableTenantContext : ITenantContext
Inheritance
object ← MutableTenantContext
Implements
ITenantContext
Inherited Members
object.GetType(), object.ToString(), object.Equals(object?), object.Equals(object?, object?), object.ReferenceEquals(object?, object?), object.GetHashCode()

Some stores take the tenant as a method parameter, others read it from ITenantContext (for example IRunStore, ISessionStore, IAgentDefinitionStore). To write a two-tenant scenario for the second group, we need either two separate store instances or a single context whose tenant can be swapped. The latter was chosen: the same store instance points at the same backend, and the question “does B see what A wrote” can be asked against a single store.

An ITenantContext whose tenant can be swapped at run time.

public MutableTenantContext(string tenantId)

tenantId string

The initial tenant.

Some stores take the tenant as a method parameter, others read it from ITenantContext (for example IRunStore, ISessionStore, IAgentDefinitionStore). To write a two-tenant scenario for the second group, we need either two separate store instances or a single context whose tenant can be swapped. The latter was chosen: the same store instance points at the same backend, and the question “does B see what A wrote” can be asked against a single store.

The current tenant’s identifier. Never returns empty.

public string TenantId { get; set; }

string

The value must be canonical — the form AmbientTenantScope.Normalize returns. The tenant identifier is matched case-insensitively across the product, and every layer achieves that by normalizing the value rather than by comparing case-insensitively. An implementation that returns Acme where another path resolves acme splits one tenant into two on PostgreSQL and SQLite, and merges them on SQL Server’s default collation — the authorization layer and the storage layer then disagree.