This page covers configuration and management of View tenant objects.

Object Overview

View is a multi-tenant system allowing you to configure separate virtual deployments within the same physical deployment. Objects other than nodes refer to a specific tenant by GUID, meaning users in one tenant have no access rights to data in another tenant.

Endpoint, URL, and Supported Methods

Objects are managed via the configuration server API at [http|https]://[hostname]:[port]/v1.0/tenants

Supported methods include: GET HEAD PUT DELETE

Structure

Objects have the following structure:

{
    "GUID": "00000000-0000-0000-0000-000000000000",
    "AccountGUID": "00000000-0000-0000-0000-000000000000",
    "DefaultPoolGUID": "00000000-0000-0000-0000-000000000000",
    "Name": "Default Tenant",
    "Region": "us-west-1",
    "S3BaseDomain": "localhost",
    "RestBaseDomain": "localhost",
    "Active": true,
    "IsProtected": true,
    "CreatedUtc": "2025-03-23T07:57:38.758241Z"
}

Properties:

  • GUID GUID globally unique identifier for the object
  • AccountGUID GUID globally unique identifier for the account
  • DefaultPoolGUID stringdefault pool's unique identifier for the tenant.
  • Name string name for the object
  • Region string S3 region string
  • S3BaseDomain string the hostname on which View should listen for S3 requests for this tenant
  • RestBaseDomain string the hostname on which View should listen for REST storage requests for this tenant
  • DefaultPoolGUID string the default storage pool GUID to which new buckets should be mapped by default
  • Active bool indicates whether or not the tenant is considered active and able to be used
  • CreatedUtc datetime timestamp from creation, in UTC time

Create

To create, call PUT /v1.0/tenants with the following properties using the configuration server: Name Region S3BaseDomain RestBaseDomain DefaultPoolGUID

Note: DefaultPoolGUID can be set to null when creating. It is recommended that after creating a tenant, you create its storage pool, and update the tenant object with the storage pool's GUID. The result will be the created object.

curl -X PUT http://localhost:8000/v1.0/tenants \
     -H "Content-Type: application/json" \
     -H "x-token: [accesToken]
     -d '
{
  "Name": "My tenant",
  "Region": "us-west-1",
  "S3BaseDomain": "localhost",
  "RestBaseDomain": "localhost",
  "DefaultPoolGUID": "df6c9117-a1ea-44ca-bddc-fa7a3d932fe9"
}'
import { ViewConfigurationSdk } from "view-sdk";

const api = new ViewConfigurationSdk(
  'default', //tenant Id
  'default', //access token
  'http://localhost:8000/' //endpoint
);

api.accessToken = "<adminToken>" //This API requires Admin access

const createTenant = async () => {
  try {
    const createdTenant = await api.writeTenant(
      {
        Name: 'My tenant',
        Region: 'us-west-1',
        S3BaseDomain: 'localhost',
        RestBaseDomain: 'localhost',
        DefaultPoolGUID: 'df6c9117-a1ea-44ca-bddc-fa7a3d932fe9',
      }
    );
    console.log(createdTenant, 'Tenant created successfully');
  } catch (err) {
    console.log('Error creating Tenant:', err);
  }
};

createTenant();

Enumerate

Refer to the Enumeration page in REST API for details about the use of enumeration APIs.

Enumerate objects by using GET /v2.0/tenants. The resultant object will appear as:

{
    "Success": true,
    "Timestamp": {
        "Start": "2024-10-21T02:36:37.677751Z",
        "TotalMs": 23.58,
        "Messages": {}
    },
    "MaxResults": 10,
    "IterationsRequired": 1,
    "EndOfResults": true,
    "RecordsRemaining": 16,
    "Objects": [
        {
            "GUID": "example-tenant",
            ... tenant details ...
        },
        { ... }
    ],
    "ContinuationToken": "[continuation-token]"
}
curl --location --head 'http://view.homedns.org:8000/v1.0/tenants/00000000-0000-0000-0000-000000000000' \
--header 'Authorization: ••••••'
import { ViewConfigurationSdk } from "view-sdk";

const api = new ViewConfigurationSdk(
  "default", //tenant Id
  "default", //access token
  "http://localhost:8000/" //endpoint
);

api.accessToken = "<adminToken>" //This API requires Admin access

export const enumerateTenant = async () => {
  try {
    const tenants = await api.enumerateTenants();
    console.log(tenants, "Tenants fetched successfully");
  } catch (err) {
    console.log("Error fetching Tenants:", err);
  }
};
enumerateTenant();

Read

To read an object by GUID, call GET /v1.0/tenants/[tenant-guid]. If the object exists, it will be returned as a JSON object in the response body. If it does not exist, a 404 will be returned with a NotFound error response.

{
    "GUID": "default",
    "Name": "Default Tenant",
    "Region": "us-west-1",
    "S3BaseDomain": "localhost",
    "RestBaseDomain": "localhost",
    "DefaultPoolGUID": "default",
    "Active": true,
    "CreatedUtc": "2024-07-10T05:09:31.000000Z"
}
curl --location 'http://view.homedns.org:8000/v1.0/tenants/00000000-0000-0000-0000-000000000000' \
--header 'Authorization: Bearer ******'
import { ViewConfigurationSdk } from "view-sdk";

const api = new ViewConfigurationSdk(
  'default', //tenant Id
  'default', //access token
  'http://localhost:8000/' //endpoint
);

const retrieveTenantById = async () => {
  try {
    const tenant = await api.retrieveTenant('00000000-0000-0000-0000-000000000000');
    console.log(tenant);
  } catch (err) {
    console.log('err: ', err);
  }
};

retrieveTenantById();

Note: the HEAD method can be used as an alternative to get to simply check the existence of the object. HEAD requests return either a 200/OK in the event the object exists, or a 404/Not Found if not. No response body is returned with a HEAD request.

Read all

To read all objects call GET /v1.0/tenants/. If the objects exists, it will be returned as a array of JSON object in the response body. If it does not exist, a 404 will be returned with a NotFound error response.

curl --location 'http://view.homedns.org:8000/v1.0/tenants/' \
--header 'Authorization: ••••••'
import { ViewConfigurationSdk } from "view-sdk";

const api = new ViewConfigurationSdk(
  "default", //tenant Id
  "default", //access token
  "http://localhost:8000/" //endpoint
);

api.accessToken = "<adminToken>" //This API requires Admin access

const fetchTenant = async () => {
  try {
    const tenants = await api.retrieveTenants();
    console.log(tenants, "Tenant fetched successfully");
  } catch (err) {
    console.log("Error fetching Tenant:", err);
  }
};
fetchTenant();

Update

To update an object by GUID, call PUT /v1.0/tenants/[tenant-guid] with a fully populated object in the request body. The updated object will be returned to you.

Note: certain fields cannot be modified and will be preserved across updates.

Request body:

{
    "GUID": "default",
    "Name": "My Updated Tenant",
    "Region": "us-west-1",
    "S3BaseDomain": "localhost",
    "RestBaseDomain": "localhost",
    "DefaultPoolGUID": "default",
    "Active": true,
    "CreatedUtc": "2024-07-10T05:09:31.000000Z"
}
curl --location --request PUT 'http://view.homedns.org:8000/v1.0/tenants/00000000-0000-0000-0000-000000000000' \
--header 'content-type: application/json' \
--header 'Authorization: ••••••' \
--data '{
    "Name": "Updated Tenant",
    "Region": "us-west-1",
    "S3BaseDomain": "localhost",
    "RestBaseDomain": "localhost",
    "DefaultPoolGUID": "00000000-0000-0000-0000-000000000000"
}'
import { ViewConfigurationSdk } from "view-sdk";

const api = new ViewConfigurationSdk(
  'default', //tenant Id
  'default', //access token
  'http://localhost:8000/' //endpoint
);

api.accessToken = "<adminToken>" //This API requires Admin access

const updateTenant = async () => {
  // tenant object to update
  const tenant = {
    Name: 'Tenant - name updated',
  };

  try {
    const updatedTenant = await api.updateTenant(
      'd11af02b-85f5-4cb4-ae25-844e42692bd7', // tenant guid
      tenant, // tenant object
    );
    console.log(updatedTenant, 'Tenant updated successfully');
  } catch (err) {
    console.log('Error creating Tenant:', JSON.stringify(err));
  }
};
updateTenant();

Response body:

{
    "GUID": "default",
    "Name": "My Updated Tenant",
    "Region": "us-west-1",
    "S3BaseDomain": "localhost",
    "RestBaseDomain": "localhost",
    "DefaultPoolGUID": "default",
    "Active": true,
    "CreatedUtc": "2024-07-10T05:09:31.000000Z"
}

Delete

To delete an object by GUID, call DELETE /v1.0/tenants/[tenant-guid]. Note that deletion of a tenant does not delete subordinate data, as it may be preferred to retain it for later use. If you wish to entirely delete a tenant, delete subordinate data as described by other APIs.


curl --location --request DELETE 'http://    view.homedns.org:8000/v1.0/tenants/    00000000-0000-0000-0000-000000000000' \--header 'Authorization: ••••••' \--data ''
import { ViewConfigurationSdk } from "view-sdk";

const api = new ViewConfigurationSdk(
  "default", //tenant Id
  "default", //access token
  "http://localhost:8000/" //endpoint
);

api.accessToken = "<adminToken>" //This API requires Admin access

const deleteTenant = async () => {
  try {
    await api.deleteTenant("<tenantGUID>");
    console.log("Tenant deleted successfully");
  } catch (err) {
    console.log("Error deleting Tenant:", err);
  }
};

Check Existence

To check existence of an object by GUID, call HEAD /v1.0/tenants/[tenant-guid].

curl --location --head 'http://view.homedns.org:8000/v1.0/tenants/00000000-0000-0000-0000-000000000000' \
--header 'Authorization: ••••••'
import { ViewConfigurationSdk } from "view-sdk";

const api = new ViewConfigurationSdk(
  "default", //tenant Id
  "default", //access token
  "http://view.homedns.org:8000/" //endpoint
);

api.accessToken = "<adminToken>" //This API requires Admin access
 
export const tenantExists = async () => {
  try {
    const tenant = await api.existsTenant(
      "904a458b-8e62-4a8d-baa4-dae577245930"
    );
    console.log(tenant, "Tenant exists"); //true
  } catch (err) {
    console.log("Error fetching Tenant:", err);
  }
};
tenantExists();