MATIH Platform is in active MVP development. Documentation reflects current implementation status.
1. Introduction
Multi-Tenancy

Multi-Tenancy

Multi-tenancy is a foundational architectural principle of the MATIH Platform, not a feature added after the fact. Every component -- from the database layer to the Kubernetes infrastructure -- is designed to securely isolate tenant data while sharing the same underlying compute resources.


Isolation Model

The platform implements a hybrid isolation model that operates at four distinct layers, providing defense in depth:

LayerMechanismImplementation
InfrastructureKubernetes namespace per tenantDedicated namespace with NetworkPolicy, ResourceQuota, RBAC
NetworkNetwork policiesPer-namespace ingress/egress rules, TLS everywhere
ApplicationThread-local tenant contextTenantContextHolder with ThreadLocal storage
DataSchema-per-tenantPer-tenant PostgreSQL schemas via Hibernate multi-tenancy

Each layer operates independently. A failure at one layer does not compromise the others.


Tenant Lifecycle

Each tenant passes through a well-defined provisioning workflow:

PhaseActionOutcome
1. ValidateCheck tenant details and uniquenessTenant record created
2. Create NamespaceProvision Kubernetes namespaceIsolated namespace with RBAC
3. Deploy SecretsCreate required Kubernetes secretsCredentials provisioned
4. Deploy DatabasesProvision per-tenant PostgreSQL schemasData isolation established
5. Deploy ServicesHelm install Data Plane servicesWorkloads running
5.5. Deploy IngressNGINX ingress controller, DNS zone, TLSExternal access enabled
6. ConfigureApply tenant-specific configurationCustom settings active
7. VerifyHealth check all deployed servicesAll services healthy
8. ActivateMark tenant as activeTenant ready for users

Per-Tenant Resources

Each tenant receives its own set of isolated resources:

ResourceIsolation MethodExample
Kubernetes namespaceDedicated namespacematih-data-plane-acme-corp
Database schemasSchema-per-tenantacme_corp schema in PostgreSQL
DNS zoneChild zone per tenantacme.matih.ai
TLS certificatePer-tenant cert via cert-managerWildcard for tenant domain
NGINX ingress controllerDedicated per namespaceOwn LoadBalancer IP
Redis key namespaceTenant-prefixed keysacme-corp:service:key
Kafka partitioningTenant ID as message keyOrdering within tenant stream
Resource quotasPer-namespace quotasCPU, memory, pod limits

Tenant Context Propagation

The tenant context flows through every layer of the request processing chain:

1. Browser sends request with JWT token
   Authorization: Bearer <token with tenant_id claim>

2. Kong Gateway validates JWT and extracts tenant_id
   Adds header: X-Tenant-ID: acme-corp

3. Backend service establishes context
   TenantContextHolder.setTenantId("acme-corp")

4. Service layer reads context
   TenantContext.requireCurrentTenantId() --> "acme-corp"

5. Repository layer scopes database queries
   SET search_path TO 'acme_corp';

6. Event publishing includes tenant context
   DataPlaneEvent.tenantId = "acme-corp"
   Kafka message key = "acme-corp"

Resource Quotas by Tier

Tenant tiers determine the resource allocation and feature access:

TierCPU QuotaMemory QuotaMax UsersFeatures
Free2 cores4Gi5Basic analytics
Professional8 cores16Gi50Full analytics, AI chat
EnterpriseCustomCustomUnlimitedAll features, custom models

Security Guarantees

GuaranteeMechanism
No cross-tenant data accessSchema-per-tenant isolation in PostgreSQL
No cross-namespace communicationKubernetes NetworkPolicies
No resource starvationKubernetes ResourceQuotas per namespace
No cache pollutionTenant-prefixed Redis keys
No event leakageTenant ID as Kafka partition key
No identity spoofingTenant ID extracted from server-signed JWT

Related Pages