> ## Documentation Index
> Fetch the complete documentation index at: https://docs.lerian.studio/llms.txt
> Use this file to discover all available pages before exploring further.

# Multi-tenancy

> Cómo Lerian aísla datos entre tenants en despliegues compartidos.

Multi-tenancy permite que un solo despliegue sirva a múltiples clientes independientes — llamados **tenants** — con aislamiento completo de datos entre ellos. Cada tenant opera como si tuviera su propio entorno dedicado, aunque la infraestructura subyacente sea compartida.

En Lerian, multi-tenancy está disponible en despliegues **SaaS** (siempre activo) y **BYOC Multi-Tenant**.

### Productos que soportan multi-tenancy

El mismo modelo de tenant basado en JWT aplica en toda la plataforma. Soportados actualmente:

| Producto                 | Soporte multi-tenant | Notas                                                                                                                                     |
| ------------------------ | -------------------- | ----------------------------------------------------------------------------------------------------------------------------------------- |
| **Midaz** (Ledger + CRM) | ✅ Sí                 | Organizaciones, ledgers, cuentas, transacciones y saldos están escopados al tenant.                                                       |
| **Tracer**               | ✅ Sí                 | Reglas, límites, validaciones y eventos de auditoría están escopados al tenant. Cada tenant tiene su propio catálogo de reglas y límites. |
| **Reporter**             | ✅ Sí                 | Los reportes corren solo sobre los datos del tenant que llama.                                                                            |

Integrar con cualquiera de estos productos es idéntico desde el punto de vista de la API — el JWT lleva el claim `tenantId` y el servicio resuelve el tenant automáticamente.

## Cómo funciona

***

El aislamiento de tenants se aplica a nivel de aplicación a través de tu token de autenticación.

1. Te autentificas vía [Access Manager](/es/platform/access-manager/access-manager) y recibes un JWT.
2. Ese token incluye un *claim* `tenantId` que identifica tu tenant.
3. En cada solicitud de API, la plataforma resuelve tu tenant a partir del token automáticamente.
4. Todas las operaciones — crear organizaciones, consultar ledgers, registrar transacciones — se limitan a tu tenant.

Nunca envías un identificador de tenant en headers ni en el cuerpo de la solicitud. El token se encarga de ello.

<Note>
  Multi-tenancy es transparente a nivel de API. Tu código de integración es el mismo ya sea que ejecutes single-tenant o multi-tenant — la única diferencia es que los despliegues multi-tenant requieren autenticación en cada solicitud.
</Note>

## Cómo se ve el alcance del tenant en cada producto

***

El `tenantId` del JWT escopa todo recurso que el usuario que llama puede ver o crear. El modelo de recursos varía por producto:

### Midaz

Un tenant **no** es lo mismo que una [organización](/es/midaz/organizations). Un solo tenant puede crear y gestionar múltiples organizaciones — por ejemplo, para representar subsidiarias, sucursales regionales o diferentes unidades de negocio.

```
Tenant (resuelto desde JWT)
├── Organización A
│   ├── Ledger 1
│   └── Ledger 2
├── Organización B
│   └── Ledger 3
```

Cuando listas organizaciones, solo ves las que pertenecen a tu tenant. Lo mismo aplica para cada recurso de Midaz — ledgers, cuentas, transacciones y balances se limitan a tu tenant automáticamente.

### Tracer

Tracer escopa su catálogo directamente bajo el tenant — no existe capa de organización.

```
Tenant (resuelto desde JWT)
├── Reglas
├── Límites
├── Validaciones
└── Eventos de auditoría
```

Cuando listas reglas o límites, solo ves entradas creadas por tu tenant. Las validaciones se ejecutan contra las reglas y límites del propio tenant, nunca contra los de otro tenant. Los eventos de auditoría también están escopados al tenant — incluso la verificación de la cadena de hash corre solo sobre la cadena del tenant que llama.

### Otros productos

Reporter y el resto de la plataforma siguen el mismo patrón: el tenant es el alcance más externo, y el JWT es la única fuente de verdad sobre a qué tenant pertenece el llamador.

## Aislamiento de datos

***

Los datos de cada tenant están aislados a nivel de base de datos. Cada tenant opera en una base de datos separada, lo que significa:

* Los datos de diferentes tenants nunca se almacenan juntos.
* Las consultas de un tenant no pueden alcanzar los datos de otro tenant.
* Incluso si dos tenants crean estructuras organizativas idénticas, sus datos permanecen completamente separados.

Este aislamiento se aplica mediante middleware que enruta cada solicitud a la base de datos correcta basándose en el *claim* `tenantId` de tu JWT. No hay forma de eludir esto a través de la API.

<Note>
  Los operadores BYOC pueden elegir entre aislamiento a nivel de base de datos o a nivel de esquema según sus requisitos de infraestructura. Consulta [Modos de aislamiento](#modos-de-aislamiento) más abajo.
</Note>

## Modos de aislamiento

***

Los operadores BYOC eligen con qué intensidad se aíslan los tenants en la capa de almacenamiento. La elección se hace **por servicio**, de modo que distintos productos — o incluso distintos tenants en el mismo producto — pueden usar modos diferentes.

* **`DATABASE`** — cada tenant obtiene una **base de datos dedicada**. Aislamiento máximo, mayor costo.
* **`SCHEMA`** — cada tenant obtiene un **esquema dedicado** dentro de una base de datos compartida. Densidad eficiente, menor costo.

### DATABASE vs. SCHEMA

| Dimensión                      | `DATABASE`                                                                                   | `SCHEMA`                                                                                                                                 |
| :----------------------------- | :------------------------------------------------------------------------------------------- | :--------------------------------------------------------------------------------------------------------------------------------------- |
| **Aislamiento físico**         | Completo — una base de datos separada por tenant.                                            | Lógico — un esquema separado dentro de una base de datos compartida.                                                                     |
| **Radio de impacto**           | Confinado a la base de datos de un solo tenant.                                              | Más amplio — un incidente a nivel de base de datos puede afectar a todos los tenants de esa instancia.                                   |
| **Restauración selectiva**     | Restaura un tenant de forma independiente, incluida la recuperación a un punto en el tiempo. | Más difícil — las restauraciones operan sobre la base de datos compartida; la restauración por tenant requiere extraer un único esquema. |
| **Costo**                      | Mayor — la infraestructura escala por tenant.                                                | Menor — los tenants comparten una instancia de base de datos.                                                                            |
| **Aislamiento de rendimiento** | Fuerte — los tenants no compiten dentro de la misma base de datos.                           | Más débil — los tenants comparten los recursos de la instancia y pueden competir.                                                        |
| **Ideal para**                 | Tenants grandes, regulados, de alto volumen o sensibles al efecto de vecino ruidoso.         | Muchos tenants más pequeños donde la densidad y la eficiencia de costos importan.                                                        |

### Radio de impacto

El **radio de impacto** (*blast radius*) es el alcance de tenants afectados cuando algo sale mal — una migración fallida, un índice corrupto, una consulta descontrolada o una restauración. En modo `DATABASE` el radio de impacto es un solo tenant, porque cada tenant está físicamente separado. En modo `SCHEMA` el radio de impacto es más amplio, porque los tenants comparten una instancia de base de datos y, por tanto, comparten su superficie de fallos y mantenimiento. Minimizar el radio de impacto es la principal razón por la que los tenants regulados o de alto valor se colocan en modo `DATABASE`.

### Otros almacenes de datos

La distinción entre `DATABASE` y `SCHEMA` anterior se aplica a PostgreSQL. Otros almacenes de datos aplican el aislamiento de tenants de forma diferente:

* **MongoDB** usa una **base de datos separada por tenant** (una base de datos por `tenantId`). Esto se aplica tanto en modo `DATABASE` como en modo `SCHEMA` — MongoDB no usa esquemas, por lo que la unidad de aislamiento es siempre una base de datos dedicada con el nombre del `tenantId`.
* **RabbitMQ** usa un **virtual host (vhost) separado por tenant**. El vhost se aprovisiona automáticamente durante el flujo de onboarding del tenant y se nombra según el `tenantId`. Las credenciales tienen alcance al vhost, por lo que un consumidor mal configurado no puede acceder a las colas de otro tenant.

<Note>
  **Restauración selectiva:** la restauración por tenant es compatible con PostgreSQL y MongoDB — ambos tienen alcance por tenant. El estado de RabbitMQ es efímero por naturaleza, por lo que "restaurar" significa reaprovisionar el vhost y reentregar los mensajes sin confirmar (unacked) desde el almacenamiento persistente cuando corresponda.
</Note>

### Migrar de SCHEMA a DATABASE

Un tenant puede promoverse de modo `SCHEMA` a modo `DATABASE` a medida que crece, sin reemitir tokens ni cambiar la identidad del tenant — el aislamiento es una propiedad del *servicio*, no del tenant.

<Steps>
  <Step title="Aprovisionar una base de datos dedicada">
    La plataforma aprovisiona una nueva base de datos aislada para el tenant y ejecuta las migraciones, como se describe en [aprovisionamiento automático](/es/multi-tenancy/auto-provisioning).
  </Step>

  <Step title="Migrar los datos del tenant">
    Los datos del tenant se mueven desde su esquema en la base de datos compartida hacia la nueva base de datos dedicada.
  </Step>

  <Step title="Reapuntar el servicio">
    El registro de servicio del tenant se actualiza a la configuración de modo `DATABASE`. El *claim* `tenantId` no cambia, por lo que las integraciones siguen funcionando sin modificaciones.
  </Step>
</Steps>

<Tip>
  Comenzar en modo `SCHEMA` y promover tenants individuales a modo `DATABASE` mantiene bajos los costos iniciales mientras reserva bases de datos dedicadas para los tenants que las necesitan. Consulta [Casos de uso](/es/multi-tenancy/use-cases) para ejemplos prácticos.
</Tip>

## Lo que esto significa para ti

***

### Si eres cliente SaaS

Nada cambia en cómo usas la API. Autentícate, obtén tu token y realiza solicitudes. La plataforma gestiona el aislamiento de forma transparente. No necesitas gestionar identificadores de tenant ni preocuparte por fugas de datos entre clientes.

### Si eres operador BYOC ejecutando multi-tenant

Tú configuras qué tenants existen y cómo se aprovisionan sus bases de datos. Tus clientes se autentifican a través de Access Manager y reciben tokens con alcance definido. La plataforma enruta cada solicitud a la base de datos correcta del tenant automáticamente.

### Si ejecutas single-tenant (BYOC o desarrollo local)

Multi-tenancy está deshabilitado por defecto. Tu configuración existente sigue funcionando sin cambios. No se requiere un *claim* de tenant en el JWT, y la autenticación puede ser opcional dependiendo de tu configuración.

## Configuración (operadores BYOC)

***

Multi-tenancy está deshabilitado por defecto en cada producto. Para habilitarlo, configura `MULTI_TENANT_ENABLED=true` en el entorno de cada producto que quieras correr en modo multi-tenant (Midaz, Tracer, Reporter). Una vez habilitado, el producto requiere autenticación en cada solicitud y un endpoint del servicio de multi-tenancy accesible.

### Configuraciones principales

Estas variables aplican a cada producto con soporte multi-tenant (Midaz Ledger, Midaz CRM, Tracer, Reporter):

| Variable                                      | Descripción                                                                                                                              | Predeterminado |
| :-------------------------------------------- | :--------------------------------------------------------------------------------------------------------------------------------------- | :------------- |
| `MULTI_TENANT_ENABLED`                        | Habilita el modo multi-tenant. Cuando es `false`, la plataforma se ejecuta en modo single-tenant.                                        | `false`        |
| `MULTI_TENANT_URL`                            | URL del endpoint del servicio de multi-tenancy. Requerido cuando multi-tenant está habilitado.                                           | —              |
| `MULTI_TENANT_SERVICE_API_KEY`                | API key para autenticarse con el servicio de multi-tenancy. Requerido cuando multi-tenant está habilitado.                               | —              |
| `MULTI_TENANT_CONNECTIONS_CHECK_INTERVAL_SEC` | Frecuencia (segundos) con la que la plataforma revalida las configuraciones de tenants desde el servicio.                                | —              |
| `MULTI_TENANT_CACHE_TTL_SEC`                  | Cuánto tiempo (segundos) se cachea localmente la configuración de un tenant antes de re-consultarla. Usa `0` para deshabilitar el caché. | `120`          |

### Circuit breaker

Protege contra interrupciones del servicio de multi-tenancy fallando rápido cuando el servicio no está disponible:

| Variable                                   | Descripción                                                                 | Predeterminado |
| :----------------------------------------- | :-------------------------------------------------------------------------- | :------------- |
| `MULTI_TENANT_CIRCUIT_BREAKER_THRESHOLD`   | Fallas consecutivas antes de que el circuito se abra.                       | `5`            |
| `MULTI_TENANT_CIRCUIT_BREAKER_TIMEOUT_SEC` | Cuánto tiempo (segundos) el circuito permanece abierto antes de reintentar. | `30`           |

### Caché en Redis

El modo multi-tenant usa Redis para cachear las configuraciones de tenants entre instancias:

| Variable                      | Descripción                              | Predeterminado |
| :---------------------------- | :--------------------------------------- | :------------- |
| `MULTI_TENANT_REDIS_HOST`     | Hostname del servidor Redis.             | —              |
| `MULTI_TENANT_REDIS_PORT`     | Puerto del servidor Redis.               | `6379`         |
| `MULTI_TENANT_REDIS_PASSWORD` | Contraseña de autenticación de Redis.    | —              |
| `MULTI_TENANT_REDIS_TLS`      | Habilita TLS para la conexión con Redis. | `false`        |

### Configuraciones específicas del CRM

Estas variables solo están disponibles en el componente CRM y controlan el comportamiento del pool de conexiones para las conexiones de base de datos multi-tenant:

| Variable                        | Descripción                                                                                  | Predeterminado |
| :------------------------------ | :------------------------------------------------------------------------------------------- | :------------- |
| `MULTI_TENANT_TIMEOUT`          | Timeout (segundos) del cliente HTTP para las solicitudes al servicio de multi-tenancy.       | `30`           |
| `MULTI_TENANT_MAX_TENANT_POOLS` | Número máximo de pools de conexión a base de datos concurrentes (uno por tenant activo).     | `100`          |
| `MULTI_TENANT_IDLE_TIMEOUT_SEC` | Cuánto tiempo (segundos) antes de que un pool de conexiones de tenant inactivo sea evictado. | `300`          |

<Tip>
  Para la mayoría de los deployments, los valores predeterminados funcionan bien. Ajusta `MULTI_TENANT_CACHE_TTL_SEC` y `MULTI_TENANT_CONNECTIONS_CHECK_INTERVAL_SEC` según la frecuencia con la que agregas o modificas tenants — valores más bajos significan propagación más rápida de los cambios de tenants, valores más altos reducen la carga sobre el servicio de multi-tenancy.
</Tip>

<Note>
  `MULTI_TENANT_ENABLED=true` requiere `PLUGIN_AUTH_ENABLED=true`. La autenticación debe estar activa para que el aislamiento de tenants funcione — la plataforma resuelve los tenants desde el claim del JWT.
</Note>

## Páginas relacionadas

***

<CardGroup>
  <Card title="Aprovisionamiento automático" icon="wand-magic-sparkles" href="/es/multi-tenancy/auto-provisioning" cta="Ver aprovisionamiento">
    Cómo se aprovisionan las bases de datos, el broker y las credenciales de un tenant.
  </Card>

  <Card title="Casos de uso" icon="lightbulb" href="/es/multi-tenancy/use-cases" cta="Ver ejemplos">
    Cuándo elegir aislamiento DATABASE vs. SCHEMA, con una ruta de migración.
  </Card>

  <Card title="Modelos de despliegue" icon="cloud" href="/es/deployment-models" cta="Comparar SaaS y BYOC">
    Comprende las diferencias entre SaaS, BYOC Single-Tenant y BYOC Multi-Tenant.
  </Card>

  <Card title="Seguridad" icon="shield-halved" href="/es/midaz/security" cta="Leer sobre seguridad">
    Conoce las garantías de aislamiento de tenants y el modelo de responsabilidad compartida.
  </Card>

  <Card title="Access Manager" icon="key" href="/es/platform/access-manager/access-manager" cta="Conocer la autenticación">
    Comprende cómo funcionan la autenticación y la resolución de tenants basada en JWT.
  </Card>

  <Card title="Organizaciones" icon="building" href="/es/midaz/organizations" cta="Gestionar organizaciones">
    Aprende cómo se estructuran las organizaciones dentro de un tenant.
  </Card>
</CardGroup>
