Skip to main content

Super Admin API

Platform-wide operations that cross tenant boundaries: creating tenants, defining the base domain they sit under, and imposing one sign-in or sharing policy on all of them. For operations inside a single tenant, see Admin. Issuing and managing API Keys for any tenant, including on the super admin surface, is covered in Authentication.

Base URL and authorization​

/api/external/v1/super-admin

These endpoints require an API Key issued to an account holding the SUPER_ADMIN role. An ordinary administrator's key does not pass.

Scope is not checked here either

Like the admin endpoints, authorization is by role alone. A key holding only api:read can create tenants, change the base domain, and enforce policy across every tenant. A super administrator key is the most privileged credential in the system regardless of the scope it was issued with.

Tenant entry-key issuance is not available through the external API.

Failures use the common envelope. Each section below lists the codes its endpoints return.

Failure
{
"result": false,
"code": 404,
"errorCode": "TENANT_001",
"message": "..."
}

Base domain​

Tenants are addressed as a subdomain of one shared base domain.

GET /api/external/v1/super-admin/base-domain
PUT /api/external/v1/super-admin/base-domain

Read the base domain​

Read base domain
curl "https://drive.example.com/api/external/v1/super-admin/base-domain" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY"
FieldTypeMeaning
baseDomainSeqintegerAlways 1 once configured; null when not configured
baseDomainstringThe base domain; null when not configured

Reading before a base domain is configured is not an error. It returns 200 with both fields null.

Configured
{
"result": true,
"code": 200,
"message": "OK",
"data": {
"baseDomainSeq": 1,
"baseDomain": "drive.example.com"
}
}
Not configured
{
"result": true,
"code": 200,
"message": "OK",
"data": {
"baseDomainSeq": null,
"baseDomain": null
}
}

Set the base domain​

ParameterTypeRequiredDescription
bdstringYesBase domain as a full domain name, up to 253 characters

bd accepts lowercase letters, digits, and hyphens only - uppercase is rejected. Each dot-separated label is 1-63 characters and starts and ends with a lowercase letter or digit, and the last label (the TLD) is at least two letters. Anything else returns BASE_DOMAIN_002.

Set base domain
curl -X PUT "https://drive.example.com/api/external/v1/super-admin/base-domain" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"bd": "drive.example.com"}'

The call registers the base domain if none exists and changes it otherwise. It returns 200 OK with no data. Sending the current value again also succeeds and repeats the recalculation below.

Changing it rewrites tenant addresses

Setting the base domain recalculates tenant domains:

  • First setting - organization tenants that already have a domain are rewritten. The first label of the existing domain becomes the subdomain, giving {subdomain}.{new base domain}. A domain with no dot becomes the base domain itself.
  • Change - only tenants linked to this base domain are rewritten, each keeping its own subdomain.

Tenants with no domain, or not linked to the base domain, are unchanged. If any recalculation fails, nothing is applied. Rewritten tenant URLs stop resolving at their old addresses, so plan for DNS, certificates, and any hard-coded client URLs before changing it.

CodeStatusMeaning
REQUEST_001400bd is missing or longer than 253 characters
BASE_DOMAIN_002400bd is not a valid domain
RESPONSE_001500Unexpected server error

BASE_DOMAIN_001 is not returned here. It is returned by tenant create and update when bs names a base domain that does not exist.

Tenants​

List tenants​

GET /api/external/v1/super-admin/tenants
ParameterTypeRequiredDescription
psintegerYesPage size, minimum 1
cilongNoCursor - the last tenantSeq of the previous page
List tenants
curl "https://drive.example.com/api/external/v1/super-admin/tenants?ps=20" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY"

Results are ordered by tenantSeq descending. When the page comes back full, the response carries hasNext: true and nextCursor, the last tenantSeq; pass it as ci for the next page.

FieldTypeMeaning
tenantSeqlongTenant identifier
tenantNamestringTenant name
domainstring{subdomain}.{base domain}, or null when there is none
clientUrlstringhttps:// followed by domain
registerDatestringYYYY-MM-DD HH:mm:ss.SSS
licenseobjectLicence summary, or null

license is null for a tenant with no licence and also when its licence fails verification. Otherwise it carries state, expiresOn (YYYY-MM-DD), and seat. seat holds current and max only for a seat-limited licence and is null for any other, so you can spot over-subscribed tenants only among seat-limited licences.

List response
{
"result": true,
"code": 200,
"message": "OK",
"data": {
"list": [
{
"tenantSeq": 12,
"tenantName": "Example",
"domain": "example.drive.example.com",
"clientUrl": "https://example.drive.example.com",
"registerDate": "2026-09-01 10:15:30.123",
"license": null
}
],
"pageSize": 20,
"hasNext": false
}
}

Read a tenant​

GET /api/external/v1/super-admin/tenants/{tenantSeq}
Read tenant
curl "https://drive.example.com/api/external/v1/super-admin/tenants/12" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY"

Returns tenantSeq, tenantName, subdomain, baseDomainSeq, and allowedIps. allowedIps is always in {IP}/{prefix} form - a single address is reported as /32. An unknown tenant returns TENANT_001.

Note that the listing returns the assembled domain while this endpoint returns the subdomain it was built from.

Read response
{
"result": true,
"code": 200,
"message": "OK",
"data": {
"tenantSeq": 12,
"tenantName": "Example",
"subdomain": "example",
"baseDomainSeq": 1,
"allowedIps": ["192.168.0.12/32", "192.168.0.0/24"]
}
}

Create a tenant​

POST /api/external/v1/super-admin/tenants

Creates the tenant, its first administrator, and its IP allowlist in one call.

ParameterTypeRequiredDescription
tnstringYesTenant name
sdstringYesSubdomain, up to 253 characters
bsintegerYesBase domain seq
estringYesAdministrator account id, an email address; unique across all tenants
nstringYesAdministrator display name
pstringYesAdministrator password
ipsarrayNoIPv4 addresses or CIDR ranges allowed to reach the administrator
  • sd accepts lowercase letters, digits, and hyphens only; uppercase returns TENANT_007. Each dot-separated label is 1-63 characters and starts and ends with a lowercase letter or digit. The full domain is {sd}.{base domain}.
  • e must not match an account id already used in any tenant, or it returns USER_004.
  • p is 8-64 characters and contains at least one uppercase letter, lowercase letter, digit, and special character, or it returns USER_001.
  • ips supports IPv4 only, and a single address is stored as /32. A CIDR range must be a network address - 192.168.0.0/24 is accepted, 192.168.0.12/24 returns ACCESS_004.
Create tenant
curl -X POST "https://drive.example.com/api/external/v1/super-admin/tenants" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"tn": "Example", "sd": "example", "bs": 1, "e": "admin@example.com", "n": "Administrator", "p": "Test1234!", "ips": ["192.168.0.12", "192.168.0.0/24"]}'

A successful call returns 201 Created with no data. Find the new tenantSeq through the listing.

The administrator is created with the ADMIN role and zero storage quota, and the tenant's login type is local. If any part - tenant, administrator, allowlist, or default settings - fails, nothing is created.

The new tenant starts with a default configuration. The office domain and adapter name are empty and must be set before the tenant can open documents. Default share settings are created as well: per-tenant, external sharing off, SPECIFIC_USERS on, ORG_LINK on, and PUBLIC_LINK off. Change these through the tenant's own Admin endpoints.

Update a tenant​

PATCH /api/external/v1/super-admin/tenants/{tenantSeq}
ParameterTypeRequiredDescription
tnstringYesTenant name
sdstringYesSubdomain, up to 253 characters
bsintegerYesBase domain seq
ipsarrayNoAllowed IPv4 addresses or CIDR ranges; replaces the whole list

sd and ips follow the same format rules as create. The tenant's own current domain does not count as a duplicate. Changing sd changes the tenant's address.

ips replaces the allowlist

The list you send replaces the existing allowed IPs, and an empty array removes them all. All three of tn, sd, and bs are required too, so read the tenant first and resend its current values - including allowedIps - for anything you are not changing.

Update tenant
curl -X PATCH "https://drive.example.com/api/external/v1/super-admin/tenants/12" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"tn": "Example Inc.", "sd": "example", "bs": 1, "ips": ["192.168.0.12/32", "192.168.0.0/24"]}'

Search a tenant's accounts​

GET /api/external/v1/super-admin/tenants/{tenantSeq}/users/search

Finds accounts in a tenant, for choosing the target of an API Key on the super admin surface.

ParameterTypeRequiredDescription
skstringYesPartial match on account id or name
rtstringNoADMIN or USER; both when omitted. Any other role returns USER_028
Search tenant accounts
curl "https://drive.example.com/api/external/v1/super-admin/tenants/12/users/search?sk=admin&rt=ADMIN" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY"

Only active accounts are returned, ordered by name ascending, with no paging. Each entry has userSeq, userId, userName, status, and roleType. An unknown tenant returns TENANT_001.

Tenant errors​

CodeStatusMeaning
REQUEST_001400A required value is missing or too long
TENANT_001404The tenant was not found
TENANT_006409The domain is already in use
TENANT_007400The subdomain is not valid
BASE_DOMAIN_001404bs names a base domain that does not exist
USER_001400The administrator password does not meet the rules
USER_002400The administrator id is not a valid email address
USER_004409The administrator id is already in use
USER_013500The administrator account could not be saved
USER_028400Account search rt is not ADMIN or USER
ACCESS_004400An IP address or CIDR range is not valid
RESPONSE_001500Unexpected server error

Sign-in policy​

The same sign-in configuration as the tenant-level endpoint, with the addition that a super administrator can impose it on every tenant at once.

GET /api/external/v1/super-admin/login-settings
PUT /api/external/v1/super-admin/login-settings

Read the sign-in policy​

ParameterTypeRequiredDescription
sstringNoScope to build the response for - tenant or global
lstringNoLogin type to build the response for - local, oidc, or jwt

s and l do not filter stored values; they choose which view of the setting is returned. Precedence is s, then l, then the stored enforcement flag:

  • s=tenant returns the per-tenant view: loginType null, isEnforced false, and an empty configs.
  • s=global, or l given, returns the providers for that login type. l takes the place of the stored login type.
  • With neither, the response follows the stored enforcement flag.
Read sign-in policy
curl "https://drive.example.com/api/external/v1/super-admin/login-settings?s=global&l=oidc" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY"

The response carries superAdminLoginSettingSeq, loginType, isEnforced, and configs. configs holds only providers registered for global enforcement. For OIDC, scopes is always null and allowIdpInitiated is always false; registerDate appears only on OIDC providers. With no setting saved, every value is null and configs is empty, whatever the parameters.

Enforced JWT
{
"result": true,
"code": 200,
"message": "OK",
"data": {
"superAdminLoginSettingSeq": 1,
"loginType": "jwt",
"isEnforced": true,
"configs": [
{
"ssoProviderSeq": 3,
"displayName": "Example SSO",
"status": "ACTIVE",
"config": {
"type": "jwt",
"issuer": "https://sso.example.com",
"keySourceType": "public_key",
"publicKey": "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA..."
}
}
]
}
}
The read endpoint returns secrets in clear text

As at tenant level, clientSecret and publicKey come back unmasked. Keep the response server-side.

Set the sign-in policy​

ParameterTypeRequiredDescription
iebooleanYestrue applies this setting to every tenant; false leaves each tenant to its own
lstringConditionalLogin type - local, oidc, or jwt; required when ie is true
psarrayConditionalIdentity providers; required when ie is true and l is oidc or jwt

Providers and their config objects take the same fields as the tenant-level endpoint described in Admin. A config.type that differs from l returns REQUEST_001, and an l value that is not defined, such as saml, returns RESPONSE_001. SSO_PROTOCOL_001 and SSO_PROTOCOL_002 are not returned by this endpoint.

With ie=false, l and ps are ignored and the stored global providers are kept, not deleted.

  • OIDC - saving with l=oidc replaces the provider list with ps. Existing providers missing from the request are deleted; to keep one, send it back with its ssoProviderSeq. Exactly one provider must have status ACTIVE, or the call returns REQUEST_001.
  • JWT - one provider only. If an active JWT provider already exists, send its ssoProviderSeq to update it; sending none returns SSO_PROVIDER_005. status is always saved as ACTIVE. An issuer already used by another JWT provider returns SSO_PROTOCOL_JWT_002.
  • displayName must be unique within the request after trimming, or the call returns REQUEST_001. An ssoProviderSeq that does not exist or is not a global provider returns SSO_PROVIDER_001.
  • publicKey is stored with the PEM header and footer and all whitespace removed, and is read back in that form.

A successful call returns 200 OK with no data. While ie is true, a tenant administrator who tries to change the tenant's sign-in settings gets SSO_PROVIDER_006.

Enforce local sign-in
curl -X PUT "https://drive.example.com/api/external/v1/super-admin/login-settings" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"ie": true, "l": "local"}'
Enforce OIDC
curl -X PUT "https://drive.example.com/api/external/v1/super-admin/login-settings" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"ie": true, "l": "oidc", "ps": [{"displayName": "Example SSO", "status": "ACTIVE", "config": {"type": "oidc", "issuerUrl": "https://sso.example.com", "clientId": "example-client", "clientSecret": "replace-with-your-client-secret"}}]}'
Enforce JWT
curl -X PUT "https://drive.example.com/api/external/v1/super-admin/login-settings" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"ie": true, "l": "jwt", "ps": [{"ssoProviderSeq": 3, "displayName": "Example SSO", "config": {"type": "jwt", "issuer": "https://sso.example.com", "keySourceType": "public_key", "publicKey": "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA..."}}]}'
The field names differ from the tenant endpoint

This endpoint uses l and ps where the tenant endpoint uses loginType and providers, and adds ie. The read response reports isEnforced rather than superAdminEnforced. The config objects are identical.

Sign-in policy errors​

CodeStatusMeaning
REQUEST_001400A required value is missing or a rule is broken; also an invalid s or l on read
SSO_PROVIDER_001404The ssoProviderSeq does not exist or is not a global provider
SSO_PROVIDER_005409An active JWT provider exists and no ssoProviderSeq was sent
SSO_PROTOCOL_JWT_002409The JWT issuer is already used by another provider
RESPONSE_001500Unexpected server error, including an undefined l on save

Sharing policy​

GET /api/external/v1/super-admin/share-settings
PUT /api/external/v1/super-admin/share-settings

Read the sharing policy​

Read sharing policy
curl "https://drive.example.com/api/external/v1/super-admin/share-settings" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY"
FieldTypeMeaning
shareSettingSeqlongSetting identifier
isEnforcedbooleanWhether the policy is applied to every tenant
shareEnabledbooleanWhether sharing is available
externalShareAllowedbooleanSharing outside the organization
allowSpecificUsersbooleanSPECIFIC_USERS share type
allowOrgLinkbooleanORG_LINK share type
allowPublicbooleanPUBLIC_LINK share type

Even when isEnforced is false, the stored values are returned - the values last enforced. With no setting saved, every field is null.

Enforced
{
"result": true,
"code": 200,
"message": "OK",
"data": {
"shareSettingSeq": 1,
"isEnforced": true,
"shareEnabled": true,
"externalShareAllowed": false,
"allowSpecificUsers": true,
"allowOrgLink": true,
"allowPublic": false
}
}

Set the sharing policy​

ParameterTypeRequiredDescription
ebooleanYestrue applies this setting to every tenant; false leaves each tenant to its own
sebooleanConditionalWhether sharing is available; required when e is true
esabooleanConditionalAllow sharing outside the organization; required when e and se are true
suabooleanConditionalAllow the SPECIFIC_USERS share type; required when e and se are true
olabooleanConditionalAllow the ORG_LINK share type; required when e and se are true
pabooleanConditionalAllow the PUBLIC_LINK share type; required when e and se are true

When enforcing with sharing on, at least one of sua, ola, and pa must be true, and enabling pa requires esa to be true as well - the same rules as the tenant endpoint.

Values that do not apply are ignored and the stored ones kept. With e=false, se, esa, sua, ola, and pa are ignored and no shares are cleaned up. With e=true and se=false, esa, sua, ola, and pa are ignored.

A successful call returns 200 OK with no data. While e is true, every tenant's own share settings endpoint reports isEnforced and returns these global values instead of its own.

Enforcing can delete existing shares, and reverting does not restore them

Saving with e=true compares each organization tenant's previous settings with the new ones, and deletes existing shares for every item that narrows from allowed to not allowed:

  • Sharing turned off - every share in the tenant.
  • SPECIFIC_USERS, ORG_LINK, or PUBLIC_LINK disallowed - shares of that type, with their targets and the recent, starred, and pinned-folder entries that depend on them.
  • External sharing disallowed - share targets in other tenants, and those users' recent, starred, and pinned-folder entries.

Setting e back to false returns each tenant to its own settings, but the deleted shares are not recovered.

Leave each tenant to its own
curl -X PUT "https://drive.example.com/api/external/v1/super-admin/share-settings" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"e": false}'
Enforce with sharing off
curl -X PUT "https://drive.example.com/api/external/v1/super-admin/share-settings" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"e": true, "se": false}'
Enforce with sharing on
curl -X PUT "https://drive.example.com/api/external/v1/super-admin/share-settings" \
-H "Authorization: Bearer replace-with-your-SUPERADMIN-API-KEY" \
-H "Content-Type: application/json" \
-d '{"e": true, "se": true, "esa": false, "sua": true, "ola": true, "pa": false}'

Sharing policy errors​

CodeStatusMeaning
REQUEST_001400e missing; se missing when enforcing; esa, sua, ola, or pa missing when enforcing with sharing on; sua, ola, and pa all false; or pa true with esa false
RESPONSE_001500Unexpected server error

Errors​

See Errors for the full list of codes across the API.