Skip to main content

Multi-Tenancy

Semaswift is a multi-tenant platform where each organization's data is completely isolated from others.

How It Works

Every resource in Semaswift belongs to an organization. When you authenticate, your JWT token includes your organization_id, and all API requests are automatically scoped to that organization.

{
"sub": "usr_123456",
"organization_id": "org_789",
"roles": ["admin"]
}

Data Isolation

Automatic Scoping

You don't need to specify organization_id in most requests - it's extracted from your token:

# This returns only users in YOUR organization
GET /api/v1/users

Cross-Organization Access

Cross-organization access is not possible through the API. Each organization's data is completely separate:

  • Users can only see resources in their organization
  • Admins cannot access other organizations
  • Even super admins are scoped to one organization per session

Organization Structure

Organization (org_789)
├── Users
│ ├── usr_001 (Admin)
│ ├── usr_002 (Supervisor)
│ └── usr_003 (Agent)
├── Roles
│ ├── Admin
│ ├── Supervisor
│ └── Agent
├── Teams
│ ├── Sales Team
│ └── Support Team
├── Resources
│ ├── Tickets
│ ├── Calls
│ ├── Recordings
│ └── Files
└── Settings
├── Business Hours
├── SLA Policies
└── Integrations

Organization Settings

Each organization can configure:

General Settings

  • Organization name and branding
  • Timezone and locale
  • Business hours

Security Settings

  • Password policies
  • MFA requirements
  • Session timeouts
  • IP allowlisting

Feature Flags

  • Enabled modules (Voice, Ticketing, etc.)
  • Feature limits (users, storage, etc.)

API Responses

All resources include organization_id:

{
"id": "tkt_123",
"organization_id": "org_789",
"subject": "Support request",
"created_at": "2024-01-15T10:30:00Z"
}

Managing Organizations

Get Current Organization

GET /api/v1/organization
{
"id": "org_789",
"name": "Acme Corp",
"slug": "acme-corp",
"plan": "professional",
"settings": {
"timezone": "America/New_York",
"locale": "en-US"
},
"limits": {
"users": 100,
"storage_gb": 50
}
}

Update Organization

PATCH /api/v1/organization
Content-Type: application/json

{
"name": "Acme Corporation",
"settings": {
"timezone": "America/Los_Angeles"
}
}

User Organization Membership

Users belong to exactly one organization. To switch organizations, users need separate accounts.

Inviting Users

POST /api/v1/users/invite
Content-Type: application/json

{
"email": "newuser@example.com",
"role": "agent",
"teams": ["team_sales"]
}

Best Practices

  1. Trust the token - Don't try to access other organizations
  2. Handle 404s gracefully - Resources from other orgs return 404
  3. Store org_id - Include it in your app's context
  4. Scope webhooks - Webhook payloads include organization_id
  5. Audit logging - All actions are logged per organization