Skip to content

v0.6.0 — Optional multi-tenancy

Choose a tag to compare

@igun997 igun997 released this 23 Jun 18:28

Optional multi-tenancy

Adds opt-in multi-tenancy controlled by the MULTI_TENANCY env flag. Default is false, which preserves the original single-tenant behavior exactly.

When enabled

  • Identity = (Authorization key, X-Session-Id). Auth key sent as today (Authorization: Bearer / X-API-Key); the tenant additionally sends a static, client-controlled X-Session-Id header.
  • Auto-provisioning, no admin. First time a (key, session_id) pair is seen, a tenant is created and an opaque, stable tenant_id is derived. Raw key never stored (only SHA-256 hash).
  • Data scoping. Every owned table has a tenant_id column; all queries filter by the tenant resolved from context. Name/natural-key uniqueness is per-tenant (email, template name, mailbox, chat, external object ids).
  • Channel config stays global. WhatsApp / Threads / IMAP gateway + tokens are shared via env; only the data is scoped.
  • Public routes (/t, /o, /export, /u, wa webhook) resolve the owning tenant from the globally-unique random code/id on the matched row.
  • Background jobs record the owning tenant per task and re-inject it into context before tenant-scoped work.

Migration

  • 0010_multi_tenancy adds the tenants table, a tenant_id column on every owned table (default 'default'), and per-tenant composite unique keys. Existing rows backfill to 'default'. Auto-applied on startup; no manual steps.

Backward compatibility

Verified on a real MySQL upgrade (v9 → 0010): legacy single-tenant data backfilled and fully reachable, multi-tenant isolation verified, full integration suite green.

Config

Variable Default Notes
MULTI_TENANCY false true scopes all data per tenant; tenants auto-provisioned from (Authorization, X-Session-Id).

PR #23.


⚠️ Security note: a stray www.threads.com_cookies.txt session file was briefly committed during merge and has been purged from history via a force-push rewrite. If you have a local clone from before this release, re-clone or hard-reset to the new master. Rotate any affected Threads/Instagram session.