Multi-tenancy
Multi-tenancy is the ability of the system to cope with multiple tenants. Such a tenant can be a company or department typically consisting of a number of users and groups. The main point of multi-tenancy is that the data of a given tenant is inaccessible by users of another tenant.
The Tenant Identifier
Multi-tenancy in Flowable Work or Engage follows the same pattern as the open source engines: all types of data get a so-called tenant identifier added to distinguish which tenant the data belongs to.
When running in single tenant mode, the tenant identifier is an empty string (consistent with the default in open source).
When running in multi-tenant mode, a default tenant (also named default) is created, in addition to all configured regular tenants.
All users and groups in the system have such a tenant identifier to indicate the tenant they are members of.
The Default Tenant
The default tenant is handled specially:
Definitions deployed to this tenant are considered shared by all tenants. This means that if you have, for example, a process definition with key abc and start a process instance by key:
a lookup is first done in the current tenant of the user starting the process instance. If found, that process definition is used (this means that it is always possible to override in a tenant specific way the shared definition).
if the previous lookup returns no results, a lookup in the default tenant is done.
This applies to all definitions: process, case, user definition, template, action, etc.
Users that are part of the default tenant and are part of the flowableAdministrator group are considered super administrators. Such users have access to data of all tenants.
Users in a tenant that are part of the flowableAdministrator group are considered tenant administrators and have only access to all data of that particular tenant.
Configuration
To enable multi-tenancy, set the following property:
flowable.platform.multi-tenant.enabled=true
It is also needed to configure for which tenants the default apps are deployed. This is done with the following setting:
flowable.platform.multi-tenant.auto-deploy-tenants=acme,megacorp
With this setting, all definitions (apps, user deployments, process definition, case definitions, etc.) are deployed to both the 'acme' and the 'megacorp' tenant.
If you want to deploy all models to only the default tenant, use:
flowable.platform.multi-tenant.auto-deploy-tenants=default
This, therefore, makes everything on the classpath shared by all tenants. This is typically the proper use case for the classpath models.
The package for the apps is com/flowable/app/default or com/flowable/app/custom. When apps are placed in the custom package, the apps from default are ignored. This way, projects can easily override any defaults that might be present.
To create users or groups per tenant, it is required to have a tenant setup JSON file for each tenant. The tenant JSON files are put in either (similar to single tenant): com/flowable/tenant-setup/default or com/flowable/tenant-setup/custom.
For example, the tenant JSON file for the 'acme' tenant is named acme-tenant-setup.json. The file has the following format where the tenantKey is the tenant identifier.
{
"name": "Acme ",
"tenantKey": "acme",
"groups": [
{ "key": "flowableUser", "name": "Flowable User" },
{ "key": "flowableAdministrator", "name": "Flowable Administrator" },
...
],
"users": [
{
"firstName": "Shane",
...
}
]
}
Note: A tenant setup file without tenantKey has all users and groups created in the default tenant.
Deploying from Flowable Design to a specific tenant
To deploy an app from Design to a certain tenant by changing/setting the following property in Design:
flowable.design.deployment-api-tenant-id=default
where default is the tenantKey of the tenant you want to deploy to.
It is also possible to configure a specific tenant for a specific deployment destination.
e.g.
#flowable.design.deployment.<id>.name=Acme Tenant
#flowable.design.deployment.<id>.deployment-api-url=http://localhost:8080/flowable-work/app-api
#flowable.design.deployment.<id>.undeployment-api-url=http://localhost:8080/flowable-work/platform-api/app-deployments
#flowable.design.deployment.<id>.deployment-api-tenant-id=acme
When no deployment-api-tenant-id
is set, then the tenant will be implicitly determined on the Work or Engage side by that user invoking that REST publish call.
Deploying from Flowable Design to different tenants
When using a system user for communicating between Design and Work the tenant id to which the app needs to be deployed can be configured using the flowable.design.deployment-tenant-source
property.
The values for this property are the following:
model-tenant-id
- This means that the tenant id is taken from tenant id that the app belongs to. A mapping between the app tenant id and the deployment tenant id can be provided using theflowable.design.deployment-tenant-mapping
property. If no mapping is provided the app tenant id is used as the deployment tenant id.
e.g. if you want the design-acme
tenant to deploy to the acme
tenant the property should be set to:
flowable.design.deployment-tenant-mapping.design-acme=acme
model-workspace-key
- This means that the tenant id is determined using the workspace key of the app. A mapping between the workspace key and the deployment tenant id should be provided using theflowable.design.deployment-tenant-mapping
property. If no mapping is provided then the configured flowable.design.deployment-api-tenant-id is used.
e.g. if you want the design-acme
workspace to deploy to the acme
tenant the property should be set to:
flowable.design.deployment-tenant-mapping.design-acme=acme
If you are looking for the Design Angular properties you can find them here.
Multi-tenancy Implementation Notes
Group ids in a tenant are prefixed with their tenant identifier. The reason is that group ids need to be unique within the whole system (like user ids).
For this purpose, a group key exists that holds the original group id (for people that are used to working with the open source users and groups). When writing multi-tenant aware logic, one must take into account (e.g., for permissions) that the group keys need to be checked and not the ids.
In single tenant mode, the id and group key are equivalent.