Settings¶
The library reads one Django setting, the DB_TENANTS dictionary. Every key is optional; missing keys take the defaults below (conf.py).
# settings.py
DB_TENANTS = {
"CONTROL_HOSTS": ["admin.example.com"],
"ENCRYPTION_KEY": os.environ["ENCRYPTION_KEY"],
"CACHE_TTL": 30,
}
Reference¶
| Key | Type | Default | Effect |
|---|---|---|---|
TEMPLATE_ALIAS |
str |
"default" |
DATABASES alias of the shared database, which holds the client registry. A copy of its settings is passed to every database strategy; the built-in TemplateOverlay derives tenant connections from it. Clients cannot use it as slug |
SHARED_APPS |
iterable of app labels | ("django_db_tenants",) |
Apps whose tables live only in the shared database. Keep it small: an app with a foreign key to auth.User or contenttypes must stay a tenant app |
TENANT_APPS_ON_DEFAULT |
bool |
True |
Also create tenant-app tables in the shared database, so superusers can log in on a control host |
DATABASE_STRATEGIES |
iterable of dotted paths | () |
Extra database strategies clients may use, registered when the app is ready. The built-in TemplateOverlay is always registered |
RESOLVER |
dotted path or callable | "django_db_tenants.resolvers.resolve_by_host" |
callable(request) -> Client | None. None means no tenant (shared database); raise TenantNotFound or TenantInactive to refuse the request. See Resolvers |
CONTROL_HOSTS |
iterable of host names | () |
Hosts that resolve_by_host serves from the shared database. Compared without port, case-insensitively |
EXEMPT_PATHS |
iterable of path prefixes | ("/healthz",) |
Requests whose path starts with one of these skip resolution; request.tenant is None |
NOT_FOUND_HANDLER |
dotted path, callable or None |
None |
callable(request, exc) -> HttpResponse for requests whose resolver raised TenantError. None returns 404 Unknown tenant. |
CACHE_ALIAS |
str |
"default" |
CACHES alias for host and slug lookups |
CACHE_TTL |
int, seconds |
60 |
Lifetime of the cached lookups; the longest a per-process cache can serve a stale client |
ENCRYPTION_KEY |
str or bytes, or None |
None |
Fernet key for db_params. None derives a key from SECRET_KEY. See Encryption |
RESOLVER and NOT_FOUND_HANDLER accept a dotted path, imported on each access, or the callable itself. |
Other settings the library depends on¶
| Setting | Requirement |
|---|---|
INSTALLED_APPS |
contains "django_db_tenants" |
MIDDLEWARE |
"django_db_tenants.middleware.TenantMiddleware" before SessionMiddleware and AuthenticationMiddleware |
DATABASE_ROUTERS |
["django_db_tenants.router.TenantRouter"] |
DATABASES[TEMPLATE_ALIAS] |
the shared database, and the template the built-in strategy derives tenant connections from; the resulting account needs the right to create databases for provisioning |
ALLOWED_HOSTS |
every tenant domain, for example [".example.com"] |
CACHES |
a shared backend (Redis, Memcached) in production; KEY_FUNCTION = "django_db_tenants.cache.tenant_key_func" on caches tenant code uses |
SECRET_KEY |
source of the encryption key when ENCRYPTION_KEY is unset |
Reading settings in code¶
from django_db_tenants.conf import app_settings
app_settings.CACHE_TTL # value from DB_TENANTS, or the default
app_settings.RESOLVER # already imported: a callable
app_settings.UNKNOWN_KEY # AttributeError
app_settings reads settings.DB_TENANTS on every access, so override_settings in tests takes effect immediately. The Fernet instance is the exception: it is cached, see Encryption.
django_db_tenants.conf ¶
App settings.
Override any key in your Django settings:
DB_TENANTS = {
"CONTROL_HOSTS": ["admin.example.com"],
"CACHE_TTL": 30,
}
DEFAULTS
module-attribute
¶
DEFAULTS = {
"TEMPLATE_ALIAS": "default",
"SHARED_APPS": ("django_db_tenants",),
"TENANT_APPS_ON_DEFAULT": True,
"DATABASE_STRATEGIES": (),
"RESOLVER": "django_db_tenants.resolvers.resolve_by_host",
"CONTROL_HOSTS": (),
"EXEMPT_PATHS": ("/healthz",),
"NOT_FOUND_HANDLER": None,
"CACHE_ALIAS": "default",
"CACHE_TTL": 60,
"ENCRYPTION_KEY": None,
}
app_settings
module-attribute
¶
app_settings = AppSettings(
DEFAULTS, frozenset({"RESOLVER", "NOT_FOUND_HANDLER"})
)
AppSettings ¶
The keys of DB_TENANTS, falling back to defaults.
Values of import_strings keys given as dotted paths are imported.