npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2025 – Pkg Stats / Ryan Hefner

@supertokens-plugins/tenants-nodejs

v0.2.0

Published

Tenants Base Plugin for SuperTokens

Readme

SuperTokens Plugin Tenants

Add multi-tenancy management to your SuperTokens Node.js backend. This plugin provides comprehensive APIs for creating, managing, and switching between tenants, with support for role-based access control, tenant invitations, and join requests.

Installation

npm install @supertokens-plugins/tenants-nodejs

Quick Start

Backend Configuration

Initialize the plugin in your SuperTokens backend configuration:

import SuperTokens from "supertokens-node";
import Session from "supertokens-node/recipe/session";
import UserRoles from "supertokens-node/recipe/userroles";
import TenantsPlugin from "@supertokens-plugins/tenants-nodejs";

SuperTokens.init({
  appInfo: {
    // your app info
  },
  recipeList: [
    Session.init({}),
    UserRoles.init({}), // Required for role-based access control
    // your other recipes
  ],
  experimental: {
    plugins: [
      TenantsPlugin.init({
        requireNonPublicTenantAssociation: false, // Optional: defaults to false
        requireTenantCreationRequestApproval: true, // Optional: defaults to true
        enableTenantListAPI: true, // Optional: defaults to false
        createRolesOnInit: true, // Optional: defaults to true
      }),
    ],
  },
});

[!IMPORTANT] You also have to install and configure the frontend plugin for the complete tenant management experience.

Configuration Options

| Option | Type | Default | Description | | ------------------------------------- | --------- | ------- | ---------------------------------------------------------------------- | | requireNonPublicTenantAssociation | boolean | false | Require users to be associated with at least one non-public tenant | | requireTenantCreationRequestApproval| boolean | true | Whether tenant creation requires approval from an admin | | enableTenantListAPI | boolean | false | Enable the API to list all available tenants | | createRolesOnInit | boolean | true | Automatically create required roles (TENANT_ADMIN, TENANT_MEMBER) on initialization | | allowPublicTenantAccess | boolean | false | Whether public tenant access should be allowed without an assigned role | | emailDelivery | object | - | Configure email delivery service and overrides |

API Endpoints

The plugin automatically exposes these endpoints:

Tenant Management

List Tenants

  • GET /plugin/supertokens-plugin-tenants/list
  • Authentication: Session required
  • Note: Only available when enableTenantListAPI: true
  • Response:
    {
      "status": "OK",
      "tenants": [
        {
          "id": "tenant1",
          "name": "Tenant 1",
          "role": "admin"
        }
      ]
    }

Create Tenant

  • POST /plugin/supertokens-plugin-tenants/create-tenant
  • Authentication: Session required
  • Body:
    {
      "name": "My Tenant",
      "firstFactors": ["emailpassword", "thirdparty"] // optional
    }
  • Response:
    {
      "status": "OK",
      "createdNew": true,
      "isPendingApproval": false
    }

Switch Tenant

  • POST /plugin/supertokens-plugin-tenants/switch-tenant
  • Authentication: Session required
  • Body:
    {
      "tenantId": "tenant1"
    }
  • Response:
    {
      "status": "OK",
      "message": "Session switched"
    }

Join Tenant

  • POST /plugin/supertokens-plugin-tenants/join-tenant
  • Authentication: Session required
  • Body:
    {
      "tenantId": "tenant1"
    }
  • Response:
    {
      "status": "OK",
      "message": "User associated with tenant"
    }

Leave Tenant

  • POST /plugin/supertokens-plugin-tenants/leave-tenant
  • Authentication: Session required
  • Response:
    {
      "status": "OK",
      "message": "User disassociated from tenant"
    }

User Management

List Users in Tenant

  • POST /plugin/supertokens-plugin-tenants/users
  • Authentication: Session required
  • Permissions: LIST_USERS
  • Response:
    {
      "status": "OK",
      "users": [
        {
          "id": "user123",
          "emails": ["[email protected]"],
          "timeJoined": 1640995200000
        }
      ]
    }

Remove User from Tenant

  • POST /plugin/supertokens-plugin-tenants/remove
  • Authentication: Session required
  • Permissions: REMOVE_USERS
  • Body:
    {
      "userId": "user123"
    }
  • Response:
    {
      "status": "OK"
    }

Change User Role

  • POST /plugin/supertokens-plugin-tenants/role/change
  • Authentication: Session required
  • Permissions: CHANGE_USER_ROLES
  • Body:
    {
      "userId": "user123",
      "role": "tenant-admin"
    }
  • Response:
    {
      "status": "OK",
      "message": "Role changed"
    }

Invitations

Add Invitation

  • POST /plugin/supertokens-plugin-tenants/invite/add
  • Authentication: Session required
  • Permissions: MANAGE_INVITATIONS
  • Body:
    {
      "email": "[email protected]",
      "role": "tenant-member"
    }
  • Response:
    {
      "status": "OK",
      "code": "abc123"
    }

List Invitations

  • POST /plugin/supertokens-plugin-tenants/invite/list
  • Authentication: Session required
  • Permissions: MANAGE_INVITATIONS
  • Response:
    {
      "status": "OK",
      "invitations": [
        {
          "email": "[email protected]",
          "role": "tenant-member",
          "code": "abc123"
        }
      ]
    }

Accept Invitation

  • POST /plugin/supertokens-plugin-tenants/invite/accept
  • Authentication: Session required
  • Body:
    {
      "tenantId": "tenant1",
      "code": "abc123"
    }
  • Response:
    {
      "status": "OK"
    }

Remove Invitation

  • POST /plugin/supertokens-plugin-tenants/invite/remove
  • Authentication: Session required
  • Permissions: MANAGE_INVITATIONS
  • Body:
    {
      "email": "[email protected]"
    }
  • Response:
    {
      "status": "OK"
    }

Join Requests

Request to Join Tenant

  • POST /plugin/supertokens-plugin-tenants/request/add
  • Authentication: Session required
  • Body:
    {
      "tenantId": "tenant1"
    }
  • Response:
    {
      "status": "OK",
      "message": "Request added"
    }

List Join Requests

  • POST /plugin/supertokens-plugin-tenants/request/list
  • Authentication: Session required
  • Permissions: MANAGE_JOIN_REQUESTS
  • Response:
    {
      "status": "OK",
      "users": [
        {
          "id": "user123",
          "emails": ["[email protected]"]
        }
      ]
    }

Accept Join Request

  • POST /plugin/supertokens-plugin-tenants/request/accept
  • Authentication: Session required
  • Permissions: MANAGE_JOIN_REQUESTS
  • Body:
    {
      "userId": "user123"
    }
  • Response:
    {
      "status": "OK",
      "message": "Request accepted"
    }

Reject Join Request

  • POST /plugin/supertokens-plugin-tenants/request/reject
  • Authentication: Session required
  • Permissions: MANAGE_JOIN_REQUESTS
  • Body:
    {
      "userId": "user123"
    }
  • Response:
    {
      "status": "OK"
    }

Tenant Creation Requests

List Tenant Creation Requests

  • POST /plugin/supertokens-plugin-tenants/tenant-requests/list
  • Authentication: Session required
  • Permissions: MANAGE_CREATE_REQUESTS
  • Response:
    {
      "status": "OK",
      "requests": [
        {
          "id": "request123",
          "name": "New Tenant",
          "creatorId": "user123"
        }
      ]
    }

Accept Tenant Creation Request

  • POST /plugin/supertokens-plugin-tenants/tenant-requests/accept
  • Authentication: Session required
  • Permissions: MANAGE_CREATE_REQUESTS
  • Body:
    {
      "requestId": "request123"
    }
  • Response:
    {
      "status": "OK"
    }

Reject Tenant Creation Request

  • POST /plugin/supertokens-plugin-tenants/tenant-requests/reject
  • Authentication: Session required
  • Permissions: MANAGE_CREATE_REQUESTS
  • Body:
    {
      "requestId": "request123"
    }
  • Response:
    {
      "status": "OK"
    }

Roles and Permissions

The plugin automatically creates the following roles:

Tenant Roles

| Role | Description | Permissions | | --------------- | ---------------------------------------------- | ----------------------------------------------------------------------------------------------- | | tenant-admin | Full administrative access within the tenant | tenant-access, list-users, manage-invitations, manage-join-requests, change-user-roles, remove-users | | tenant-member | Basic member access within the tenant | tenant-access | | app-admin | Global application administrator | All permissions across all tenants |

Permissions

| Permission | Description | | ----------------------- | ---------------------------------------------- | | tenant-access | Basic access to tenant | | list-users | View list of users in tenant | | manage-invitations | Create and manage tenant invitations | | manage-join-requests | Approve or reject join requests | | change-user-roles | Modify user roles within tenant | | remove-users | Remove users from tenant | | manage-create-requests| Approve or reject tenant creation requests |

Email Delivery Configuration

Configure custom email delivery for tenant-related notifications:

import { PluginSMTPService } from "@supertokens-plugins/tenants-nodejs";

TenantsPlugin.init({
  emailDelivery: {
    service: new PluginSMTPService({
      smtpSettings: {
        host: "smtp.example.com",
        port: 587,
        from: {
          name: "Your App",
          email: "[email protected]",
        },
        secure: false,
        authUsername: "username",
        password: "password",
      },
    }),
  },
});

Email Types

The plugin sends emails for the following events:

  1. TENANT_REQUEST_APPROVAL: Sent to admins when a user requests to create a tenant
  2. TENANT_CREATE_APPROVAL: Sent to the requester when their tenant creation request is approved

Exported Functions

The plugin exports helper functions for direct backend usage:

import { assignAdminToUserInTenant, assignRoleToUserInTenant } from "@supertokens-plugins/tenants-nodejs";

// Assign admin role to a user in a tenant
await assignAdminToUserInTenant("tenant1", "user123");

// Assign a specific role to a user in a tenant
await assignRoleToUserInTenant("tenant1", "user123", "tenant-member");

Advanced Configuration

Custom Implementation Override

You can override default behaviors by providing custom implementations:

TenantsPlugin.init({
  override: {
    functions: (originalImplementation) => ({
      ...originalImplementation,
      isAllowedToCreateTenant: async (session) => {
        // Custom logic to determine if user can create tenant
        const userId = session.getUserId();
        // Check your custom logic here
        return true;
      },
      canApproveJoinRequest: async (targetUser, tenantId, session) => {
        // Custom logic for approving join requests
        return true;
      },
    }),
  },
});

Session Management

The plugin automatically manages session switching when users join or switch tenants. The session is refreshed with the new tenant context, including updated roles and permissions.

Multi-Tenancy Workflow

  1. User creates a tenant: POST to /create-tenant
  2. Admin assigns roles: Users are automatically assigned the tenant-admin role when they create a tenant
  3. Users join tenant:
    • Via invitation: Accept invitation using invitation code
    • Via request: Request to join and wait for admin approval
  4. Switch tenant: Use /switch-tenant to change active tenant context

Testing

The plugin includes comprehensive test coverage. Run tests with:

npm test

Tests require a running SuperTokens core instance. Configure using environment variables:

  • CORE_BASE_URL: SuperTokens core URL (default: http://localhost:3567)
  • CORE_API_KEY: API key for core authentication

License

See the main repository for license information.