Luna2 REST API

Design decisions

  • No implementation of 300 (redirects)

  • Not all errors are implemented

  • Not all methods are supported, only GET and POST

  • All POST request body are required to have valid JSON (RFC 8259). The server will not validate for the client, simply reject any malformed request. There are ways to format and validate it in Linux / python.

  • Monitoring end-points are provided on /monitor.

  • HTTP codes must also be passed back

Changelog

Removals:

  • Removal of lweb (replaced by REST API), same port (7050)

  • auto creation of nodes is removed (Create=True), also removing the nodeprefix and nodedigits configuration items

Changes:

  • newfieldname can be used for cloning ({name}/_clone) and renaming ({name})

  • dhcp configuration has been removed from cluster level and moved to network (now enables/disables per network)

New features:

General:

  • Templating jinja2

  • Standardized jinja2 variables available in the LUNA installer for further customization

  • Full URI is also required in the request body and response body

  • URI is consistent with request and response body

Authentication

  • Role based authentication, default group: admin

Provisioning

  • Provisioning default is torrent

  • Fallback via /files/{tarball} via webservice

  • Configurable via the cluster endpoint, override possible on group or node level

  • Configurable provisioning allows for future provisioning methods such as rsync, kickstart or anything scriptable

Group configuration:

  • Netboot (offering PXE menu or minimized boot menu -> LOCALDISK)

  • Localinstall (triggers Grub2 installation)

Network:

  • API to get next available IP (can be called manually) /config/network/_nextfreeip

  • Renumbering will not be done if:

  • the new group has the same network interfaces and networks

  • the IP is still valid in the new group

NTP configuration (cluster/network):

  • Can be configured cluster wide

  • Override possible on network level

BMC setup

  • Added gateway configuration (taken from network configuration)

  • Added NTP configuration (taken from network configuration)

Secrets

  • Secrets can be configured on group or node level. These are placed inside the OSimage, preventing placement of sensitive information in images.

OSimage:

  • Changing kernel can be done with (/config/osimage/{osimage}/kernel) automatic packing or without (/config/osimage/{osimage}

  • Cloning includes copying of the files, done by ZFS so it should be very quick

  • Distribution flag (default redhat) which should trigger different dracut/packing in future releases

Monitor

  • Added monitoring endpoints for nodes

  • Self-monitoring daemon (/monitor/service/luna2)

Service control via daemon API

  • Monitoring & control of dhcp and dns

Rest resources

Note: There is no cluster configuration. This is to be done by the ini files to prevent breaking installations

Examples

http://host:port/config/node/{node}

Structure of the URI

  • host and port define the host and port where the application lives

  • config is the context for updating or deleting the node at {node}

All POST Method(s) requires a valid token to get the response. Except /token

All Get Method will get the minimal response if the token isn’t set in the headers.

the ** key will hold the token against the apis.

Initially, Tokens are sha256 encoded.

URI Structure

See Luna2 REST API URI Structure

Fields

See Luna2 REST API Fields

API Usage

Authenticate against the API (POST /token)

When talking to the API, a token is required. The token can be obtained from the token endpoint.

Request

POST /token

Request header


Request body

{
  "username": "luna",
  "password": "luna"
}

Response body

{
  "token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"
}

Response header

HTTP 201 Created will be expected to be returned.

HTTP 401 Unauthorized is mandatory if the credentials are invalid

HTTP 400 Bad request when the request is invalid (field definitions)

HTTP 503 Service unavailable is returned when the backend is unavailable.

Version

A very simple endpoint. No auth required and no modifications allowed.

Returned:

  • Luna version

  • API version it supports (this document)

  • Commit (from Git)

Get version (GET /version)

Request

GET /version

Response body

{
  "version": {
    "luna": "2.0.0001",
    "api": 1,
    "commit": "hex(commit)"
  }
}

Request header


Response header

HTTP 200 OK will be expected to be returned.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Booting

The boot menu entry will give out one of several templates (see the Boot process page):

  • templ_boot_ipxe.cfg (default)

  • templ_boot_disk.cfg

  • templ_boot_ipxe_short.cfg

The controller writes out the DHCP configuration. The normal iPXE menu is served when the bootmenu and netboot flags have been set to True.

Node is known

Bootmenu

Netboot

Template

1

Yes

False

True

Short

2

Yes

True

True

Normal

3

Yes

Any

False

Disk

4

No

-

-

Normal

The DHCP configuration is changed to reflect booting off different templates.

2 + 4:

host node001  {
    hardware ethernet 18:c0:4d:45:00:eb;
    fixed-address 10.141.0.1;
}

1:

host node001  {
    hardware ethernet 18:c0:4d:45:00:eb;
    fixed-address 10.141.0.1;
    filename "http://10.141.255.254:7050/boot/short"
}

3:

host node001  {
    hardware ethernet 18:c0:4d:45:00:eb;
    fixed-address 10.141.0.1;
    filename "http://10.141.255.254:7050/boot/disk"
}

Boot by MAC (or port detection)

The node will do a discovery (auto menu selection)

Request

GET /boot/search/18:c0:4d:45:00:eb

Response

The response is an iPXE script which can be booted from.

#!ipxe

imgfetch -n kernel http://10.141.255.254:7050/boot/compute-vmlinuz-4.18.0-372.26.1.el8_6.x86_64
imgload kernel
imgargs kernel root=luna luna.bootproto=static luna.mac=18:c0:4d:45:00:eb luna.ip=10.141.0.1/16 luna.url=http://10.141.255.254:7050/luna luna.node=node001 luna.hostname=node001.cluster luna.service=0  initrd=initrd.img
imgfetch --name initrd.img http://10.141.255.254:7050/boot/compute-initramfs-4.18.0-372.26.1.el8_6.x86_64
imgexec kernel

Manual boot

Request

GET /boot/manual/hostname/node002

Response

The controller will immediately change the hostname in the backend to reflect the change, removing the previous settings for the entry.

The response will allow booting from an alternative hostname. Note the changed luna.node and luna.hostname parameter.

#!ipxe

imgfetch -n kernel http://10.141.255.254:7050/boot/compute-vmlinuz-4.18.0-372.26.1.el8_6.x86_64
imgload kernel
imgargs kernel root=luna luna.bootproto=static luna.mac=18:c0:4d:45:00:eb luna.ip=10.141.0.1/16 luna.url=http://10.141.255.254:7050/luna luna.node=node002 luna.hostname=node002.cluster luna.service=0  initrd=initrd.img
imgfetch --name initrd.img http://10.141.255.254:7050/boot/compute-initramfs-4.18.0-372.26.1.el8_6.x86_64
imgexec kernel

iPXE boot menu (GET /boot)

This endpoint is requested by the node's iPXE bootloader and is served without a token.

Request

GET /boot

Response body A rendered iPXE script (the main boot menu) is returned. The Luna controller fills in the available nodes, groups and controller details before serving it.

#!ipxe
[...]

Response header

HTTP 200 OK will be expected to be returned.

Shortened iPXE boot menu (GET /boot/short)

This endpoint is requested by the node's iPXE bootloader and is served without a token.

Request

GET /boot/short

Response body A rendered iPXE script is returned. This is a shortened variant of the main boot menu that omits the per-node and per-group listings.

#!ipxe
[...]

Response header

HTTP 200 OK will be expected to be returned.

Boot from local disk (GET /boot/disk)

This endpoint is requested by the node's iPXE bootloader and is served without a token.

Request

GET /boot/disk

Response body A rendered iPXE script that instructs the node to boot from its local disk is returned.

#!ipxe
[...]
sanboot --no-describe --drive 0x80
[...]

Response header

HTTP 200 OK will be expected to be returned.

Boot lookup by MAC address (GET /boot/search/mac/{macaddress})

This endpoint is requested by the node's iPXE bootloader and is served without a token.

Request

GET /boot/search/mac/aa:bb:cc:dd:ee:ff

Response body The server performs discovery on the supplied MAC address (looking the MAC up via SNMP port-detection if that has been enabled) and returns a rendered iPXE script populated with the matched node's image, kernel, initrd, kernel options and network details.

#!ipxe
[...]

Response header

HTTP 200 OK will be expected to be returned.

Manual boot by group (GET /boot/manual/group/{groupname}/{macaddress})

This endpoint is requested by the node's iPXE bootloader and is served without a token.

Request

GET /boot/manual/group/compute/aa:bb:cc:dd:ee:ff

Response body The server picks the first available node in the chosen group (creating one if none is available), assigns the supplied MAC address to it, and returns a rendered iPXE script populated with that node's image, kernel, initrd, kernel options and network details.

#!ipxe
[...]

Response header

HTTP 200 OK will be expected to be returned.

Manual boot by hostname (GET /boot/manual/hostname/{hostname}/{macaddress})

This endpoint is requested by the node's iPXE bootloader and is served without a token.

Request

GET /boot/manual/hostname/node001/aa:bb:cc:dd:ee:ff

Response body The server performs discovery on the supplied hostname (looking the MAC up via SNMP port-detection if that has been enabled), assigns the supplied MAC address to the matched node, and returns a rendered iPXE script populated with that node's image, kernel, initrd, kernel options and network details.

#!ipxe
[...]

Response header

HTTP 200 OK will be expected to be returned.

Boot role (GET /boot/roles/{role})

Request

GET /boot/roles/<role>

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body Unlike the other boot endpoints, this returns a JSON payload containing the role's target and its base64-encoded script data.

{
    "target": "[...]",
    "script": "[...]"
}

Response header

HTTP 200 OK will be expected to be returned.

Boot script (GET /boot/scripts/{script})

Request

GET /boot/scripts/<script>

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body Like the role endpoint, this returns a JSON payload containing the script's target and its base64-encoded script data.

{
    "target": "[...]",
    "script": "[...]"
}

Response header

HTTP 200 OK will be expected to be returned.

Kickstart installation template (GET /kickstart/install/{node})

This endpoint is requested by the node during provisioning and is served without a token.

Request

GET /kickstart/install/node001

Response body A rendered kickstart installation template for the named node is returned, populated with the node's group, OS image, distribution, partitioning, BMC setup, interfaces, pre/part/post scripts, provisioning method and related values.

[...]
%post
[...]
%end

Response header

HTTP 200 OK will be expected to be returned.

Luna installation template (GET boot/install/{node})

The luna.node and luna.hostname are passed through the boot parameters and are used to retrieve the installation template. Note that the API must verify that the request is originating from the node itself by checking the IP address (i.e. 10.141.0.1 can only request a template belonging to node001).

Request

GET /boot/install/node001

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response

The response would be a tailored installation script for this node (See #pre, #part, #postscripts) in plain text.

export LUNA_IMAGEFILE=''
export LUNA_OSIMAGE=''
export LUNA_TOKEN="eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpZCI6MCwiZXhwIjoxNzM5MjcxNzA2fQ.2HUmy8sL5oFtzayjWBfUeK0huezEk6rA9qt41_VixCU"
export DECODE=""
## ----------- useful variable exports -----------
export _HOSTNAME="node001"
export _SYSTEMROOT="/sysroot"
export _BOOTIF=${LUNA_BOOTIF}
## -----------------------------------------------

export INSECURE='--insecure'

if [ -n "${LUNA_BOOTIF}" ]; then
    export INTERFACE="--interface ${LUNA_BOOTIF}"
fi
if [ "$(echo LUNA_API_PROTOCOL | grep ':')" ]; then
    export LUNA_URL="http://[10.141.255.254]:7050"
else
    export LUNA_URL="http://10.141.255.254:7050"
fi

base64 --help &> /dev/null
if [ "$?" == "0" ]; then
    DECODE=1
fi
if [ ! "$DECODE" ]; then
    echo "Luna2: --WARNING-- base64 decoder not available. This will impair the installer"
fi

function update_status {
    json='{"monitor": { "status": { "node001": { "state": "'$1'" } } } }'
    curl $INTERFACE $INSECURE -X POST -H "x-access-tokens: $LUNA_TOKEN" -H "Content-Type: application/json" -d "$json" -s "${LUNA_URL}/monitor/node/node001"
}

function update_system_info {
    dmidecode --help &> /dev/null
    ret=$?
    if [ "$ret" == "0" ]; then
        vendor=$(dmidecode -s system-manufacturer)
        assettag=$(dmidecode -s system-serial-number)
        json='{"config": {"node": { "node001": { "vendor": "'$vendor'", "assettag": "'$assettag'" } } } }'
        curl $INTERFACE $INSECURE -X POST -H "x-access-tokens: $LUNA_TOKEN" -H "Content-Type: application/json" -d "$json" -s "${LUNA_URL}/config/node/node001"
    else
        echo "Luna2: dmidecode not found and could therefor not update system information"
    fi
}

function update_node_ip {
    json='{"config": {"node": {"node001": {"name": "node001", "interfaces": [{"interface": "BOOTIF", "force": true, "ipaddress": "'$1'"}]}}}}'
    curl $INTERFACE $INSECURE -X POST -H "x-access-tokens: $LUNA_TOKEN" -H "Content-Type: application/json" -d "$json" -s "${LUNA_URL}/config/node/node001"
}

function lunainit {
    if [ ! -d /lunatmp ]; then
        mkdir /lunatmp
    fi
    if [ ! -d //sysroot ]; then
        echo "Luna2: Warning! /sysroot did not exist! it's unexpected. I will create it and try to continue"
        mkdir //sysroot
    fi
}

function dynamic_ip_check {
    if [ "${LUNA_BOOTPROTO}" == "dhcp" ]; then
        echo "Luna2: I need to update luna to reflect my dynamic IP address"
        if [ "${LUNA_BOOTIF}" ]; then
            MY_IP=$(ip a show dev ${LUNA_BOOTIF}|grep -oE "inet [0-9\.]+"|grep -oE "[0-9\.]+")
            if [ "${MY_IP}" ]; then
                update_node_ip $MY_IP
            else
                echo "Luna2: Could not figure out my IP address"
            fi
        else
            echo "Luna2: BOOTIF is not defined"
        fi
    fi
}
...
...
...

Group configuration

Get a list of groups (GET /config/group)

Request

GET /config/group

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "group": {
      "compute": {
        "bmcsetup": true,
        "bmcsetupname": "gigabyte",
        "domain": "cluster",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ],
        "osimage": "compute",
        "osimagetag": "versionx",
        "partscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "postscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "prescript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "provision_interface": null,
        "netboot": true,
        "bootmenu": false,
        "comment": "Default group",
        "provision_method": "torrent",
        "provision_fallback": "http"
      },
      "compute-ib": {
        "bmcsetup": true,
        "bmcsetupname": "gigabyte",
        "domain": "cluster",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ],
        "osimage": "compute",
        "partscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "postscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "prescript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "provision_interface": null,
        "netboot": true,
        "bootmenu": false,
        "comment": "Default group",
        "provision_method": "torrent",
        "provision_fallback": "http",
        "_override": False
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get group information (GET /config/group/{group})

Request

GET /config/group/compute

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "group": {
      "compute": {
        "bmcsetup": true,
        "bmcsetupname": "gigabyte",
        "domain": "cluster",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ],
        "osimage": "compute",
        "osimagetag": "versionx",
        "partscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "postscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "prescript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "provision_interface": null,
        "netboot": true,
        "bootmenu": false,
        "comment": "Default group",
        "provision_method": "torrent",
        "provision_fallback": "http",
        "_override": False
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a list members of the groups (GET /config/group/{group}/_member)

Request

GET /config/group/{group}/_member

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "group": {
      "compute": {
        "members": [
          "node001",
          "node002",
          "node003",
          "node004"
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update & Rename(By newgroupname) group information (POST /config/group/{group})

Request

POST /config/group/compute

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "group": {
      "compute": {
        "newgroupname": "compute-gpu",
        "bmcsetup": true,
        "bmcsetupname": "gigabyte",
        "domain": "cluster",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ],
        "osimage": "compute",
        "osimagetag": "versionx",
        "partscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "postscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "prescript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "provision_interface": null,
        "netboot": true,
        "bootmenu": false,
        "comment": "Default group",
        "provision_method": "torrent",
        "provision_fallback": "http",
        "_override": False
      }
    }
  }
}

Response header

HTTP 204 No content will be expected to be returned.

HTTP 201 Created will be expected to be returned when a new object is created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Clone (By newgroupname) a group (POST /config/group/{group}/_clone)

Request

POST /config/group/compute/_clone

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "group": {
      "compute": {
        "newgroupname": "compute-gpu",
        "bmcsetup": true,
        "bmcsetupname": "gigabyte",
        "domain": "cluster",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ],
        "osimage": "compute",
        "osimagetag": "versionx",
        "partscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "postscript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "prescript": "IyEvYmluL2Jhc2gKZXhpdCAw",
        "provision_interface": null,
        "netboot": true,
        "bootmenu": false,
        "comment": "Default group",
        "provision_method": "torrent",
        "provision_fallback": "http"
      }
    }
  }
}

Response header

HTTP 204 No content will be expected to be returned.

HTTP 201 Created will be expected to be returned when a new object is created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Deleting a group (GET /config/group/{group}/_delete)

Request

POST /config/group/compute/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get group interface information (GET /config/group/{group}/interfaces)

Request

GET /config/group/compute

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "group": {
      "compute": {
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update group interface information (POST /config/group/{group}/interfaces)

The interfaces can accept updates to one or more interfaces.

Request

POST /config/group/compute/interfaces

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "group": {
      "compute": {
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ]
      }
    }
  }
}

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 201 Created will be expected to be returned when created

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist (group)

HTTP 503 Service unavailable is returned when the backend is unavailable.

Retrieve group interface information (GET /config/group/{group}/interfaces/{interface})

Request

GET /config/group/compute/interfaces/BOOTIF

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "group": {
      "compute": {
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          }
        ]
      }
    }
  }
}

Response body


Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist (group)

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete group interface (GET /config/group/{group}/interfaces/{interface}/_delete)

Request

GET /config/group/compute/interfaces/BOOTIF/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body


Response body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist (group)

HTTP 503 Service unavailable is returned when the backend is unavailable.

Push the osimage to all nodes in the group (POST /config/group/{name}/_ospush)

Request

POST /config/group/compute/_ospush

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "group": {
      "compute": {
        "osimage": "compute-image"
      }
    }
  }
}

Response body

This is an asynchronous operation. The push is queued and a request_id is returned that can be polled for progress (see Tracking asynchronous requests).

{
  "message": "queued",
  "request_id": "8125"
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the push could not be started.

Node configuration

Get a list of nodes (GET /config/node)

Request

GET /config/node

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "node": {
      "node001": {
        "group": "compute",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          },
          {
            "interface": "BMC",
            "network": "ipmi",
            "ipaddress": "10.148.0.1"
          },
          {
            "interface": "ib0",
            "network": "ib",
            "ipaddress": "10.149.0.1"
          }
        ],
        "switch": "switch01",
        "switchport": 1,
        "service": false,
        "setupbmc": true,
        "status": "installer.completed",
        "comment": null,
        "osimage": null,
        "osimagetag": null,
        "prescript": null,
        "postscript": null,
        "partscript": null,
        "netboot": true,
        "bootmenu": false,
        "provision_interface": null,
        "provision_method": null,
        "provision_fallback": null,
        "tpm_uuid": null,
        "tpm_pubkey": null,
        "tpm_sha256": null,
        "_override": False
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get node information (GET /config/node/{node})

Request

GET /config/node

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "node": {
      "node001": {
        "group": "compute",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          },
          {
            "interface": "BMC",
            "network": "ipmi",
            "ipaddress": "10.148.0.1"
          },
          {
            "interface": "ib0",
            "network": "ib",
            "ipaddress": "10.149.0.1"
          }
        ],
        "switch": "switch01",
        "switchport": 1,
        "service": false,
        "setupbmc": true,
        "status": "installer.completed",
        "comment": null,
        "osimage": null,
        "osimagetag": null,
        "prescript": null,
        "postscript": null,
        "partscript": null,
        "netboot": true,
        "bootmenu": false,
        "provision_interface": null,
        "provision_method": null,
        "provision_fallback": null,
        "tpm_uuid": null,
        "tpm_pubkey": null,
        "tpm_sha256": null
        "_override": False
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update node information (POST /config/node/{node})

Renaming a node is done by setting the newhostname field

Interfaces can be updated in bulk via the {node}, or single items via the {node}/interfaces

Request

POST /config/node/{node}

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "node": {
      "node001": {
        "group": "compute",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          },
          {
            "interface": "BMC",
            "network": "ipmi",
            "ipaddress": "10.148.0.1"
          },
          {
            "interface": "ib0",
            "network": "ib",
            "ipaddress": "10.149.0.1"
          }
        ],
        "switch": "switch01",
        "switchport": 1,
        "service": false,
        "setupbmc": true,
        "status": "installer.completed",
        "comment": null,
        "osimage": null,
        "osimagetag": null,
        "prescript": null,
        "postscript": null,
        "partscript": null,
        "netboot": true,
        "bootmenu": false,
        "provision_interface": null,
        "provision_method": null,
        "provision_fallback": null,
        "tpm_uuid": null,
        "tpm_pubkey": null,
        "tpm_sha256": null
      }
    }
  }
}

Response body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 201 Created will be expected to be returned when a new object has been created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Clone a node (POST /config/node/{node}/_clone)

Renaming a node is done by setting the newhostname field

Interfaces can be updated in bulk via the {node}, or single items via the {node}/interfaces

Request

POST /config/node/{node}/_clone

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "node": {
      "node001": {
        "group": "compute",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          },
          {
            "interface": "BMC",
            "network": "ipmi",
            "ipaddress": "10.148.0.1"
          },
          {
            "interface": "ib0",
            "network": "ib",
            "ipaddress": "10.149.0.1"
          }
        ],
        "switch": "switch01",
        "switchport": 1,
        "service": false,
        "setupbmc": true,
        "status": "installer.completed",
        "comment": null,
        "osimage": null,
        "osimagetag": null,
        "prescript": null,
        "postscript": null,
        "partscript": null,
        "netboot": true,
        "bootmenu": false,
        "provision_interface": null,
        "provision_method": null,
        "provision_fallback": null,
        "tpm_uuid": null,
        "tpm_pubkey": null,
        "tpm_sha256": null
      }
    }
  }
}

Response body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 201 Created will be expected to be returned when a new object has been created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Deleting a node (GET /config/node/{node}/_delete)

Request

GET /config/node/node001/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 401 Not Found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Listing node interfaces (GET /config/node/{node}/interfaces)

Request

GET /config/node/node001/interfaces

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "node": {
      "node001": {
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          },
          {
            "interface": "BMC",
            "network": "ipmi",
            "ipaddress": "10.148.0.1"
          },
          {
            "interface": "ib0",
            "network": "ib",
            "ipaddress": "10.149.0.1"
          }
        ]
      }
    }
  }
}

Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 401 Not Found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Updating node interfaces (POST /config/node/{node}/interfaces)

Request

POST /config/node/node001/interfaces

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "node": {
      "node001": {
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          },
          {
            "interface": "BMC",
            "network": "ipmi",
            "ipaddress": "10.148.0.1"
          },
          {
            "interface": "ib0",
            "network": "ib",
            "ipaddress": "10.149.0.1"
          }
        ]
      }
    }
  }
}

Response body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Showing node interfaces (GET /config/node/{node}/interfaces/{interface})

Request

GET /config/node/node001/interfaces/BOOTIF

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "node": {
      "node001": {
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          }
        ]
      }
    }
  }
}

Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete node interfaces (GET /config/node/{node}/interfaces/{interface}/_delete)

Request

GET /config/node/node001/interfaces/BOOTIF/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Grab an osimage from a node (POST /config/node/{name}/_osgrab)

Request

POST /config/node/node001/_osgrab

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "node": {
      "node001": {
        "osimage": "compute-image",
        "dryrun": false
      }
    }
  }
}

Response body

This is an asynchronous operation. The grab is queued and a request_id is returned that can be polled for progress (see Tracking asynchronous requests). On a high-availability setup where this controller is not the master, the request is forwarded and the message reflects that.

{
  "message": "queued",
  "request_id": "8126"
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the grab could not be started.

Push an osimage to a node (POST /config/node/{name}/_ospush)

Request

POST /config/node/node001/_ospush

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "node": {
      "node001": {
        "osimage": "compute-image"
      }
    }
  }
}

Response body

This is an asynchronous operation. The push is queued and a request_id is returned that can be polled for progress (see Tracking asynchronous requests).

{
  "message": "queued",
  "request_id": "8127"
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the push could not be started.

Cluster information

The cluster endpoint mostly read-only, and can not be used to modify the configuration. All the configuration is done via the ini and will require restarting the daemon.

Only configurable items are:

  • ntp_server

  • technical_contacts

  • provisioning_method

  • provision_fallback

  • debug

Get cluster information (GET /config/cluster)

Request

GET /config/cluster

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "cluster": {
      "controller1": {
        "status": "primary",
        "ipaddr": "10.141.255.254",
        "serverport": 7050,
        "luna_config": "/trinity/local/luna/config/luna-daemon.ini"
      },
      "controller2": {
        "status": "standby",
        "ipaddr": "10.141.255.253",
        "serverport": 7050,
        "luna_config": "/trinity/local/luna/config/luna-daemon.ini"
      },
      "ntp_server": "10.141.255.252",
      "debug": false,
      "technical_contacts": "root@localhost",
      "provision_method": "torrent",
      "provision_fallback": "http"
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Update cluster information (POST /config/cluster)

Request

POST /config/cluster

Request body

{
  "config": {
    "cluster": {
      "ntp_server": "10.141.255.252",
      "debug": false,
      "technical_contacts": "root@localhost",
      "provision_method": "torrent",
      "provision_fallback": "http"
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 400 Bad request is mandatory if the controller objects are attempted to be modified

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Export the cluster configuration (GET /config/cluster/export)

Request

GET /config/cluster/export

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "cluster": { "...": "..." },
    "network": { "...": "..." },
    "group": { "...": "..." },
    "node": { "...": "..." },
    "osimage": { "...": "..." },
    "[...]": "[...]"
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the configuration could not be exported.

Import a cluster configuration (POST /config/cluster/import)

Request

POST /config/cluster/import

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "cluster": { "...": "..." },
    "network": { "...": "..." },
    "group": { "...": "..." },
    "node": { "...": "..." },
    "[...]": "[...]"
  }
}

Response body

{
  "message": "Configuration imported"
}

Response header

HTTP 201 Created will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the configuration could not be imported.

Network Management

Network management covers the network configuration section of the configuration management database. It does not configure the network equipment.

Get the list of networks (GET /config/network)

Request

GET /config/network

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "network": {
      "cluster": {
        "network": "10.141.0.0/16",
        "nameserver_ip": "10.141.255.254",
        "ntp_server": "10.141.255.254",
        "gateway": "10.141.255.254",
        "comment": "Default cluster network",
        "dhcp": true,
        "dhcp_range_begin": "10.141.0.200",
        "dhcp_range_end": "10.141.0.253"
      },
      "ipmi": {
        "network": "10.148.0.0/16",
        "nameserver_ip": "10.148.255.254",
        "ntp_server": "10.148.255.254",
        "gateway": "10.148.255.254",
        "comment": "Default OOB network",
        "dhcp": false
      },
      "ib": {
        "network": "10.149.0.0/16",
        "nameserver_ip": "10.149.255.254",
        "ntp_server": "10.149.255.254",
        "gateway": "10.149.255.254",
        "comment": "Default highspeed interconnect network",
        "dhcp": false
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get network information (GET /config/network/{networkname})

Request

GET /config/network/cluster

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "network": {
      "cluster": {
        "name": "cluster",
        "network": "10.141.0.0/16",
        "gateway": "10.141.255.254",
        "nameserver_ip": "10.141.255.254",
        "ntp_server": "10.141.255.254",
        "comment": "Default cluster network",
        "dhcp": true,
        "dhcp_range_begin": "10.141.0.200",
        "dhcp_range_end": "10.141.0.253"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Update network information (POST /config/network/{networkname})

Request

POST /config/network/cluster

Request body

{
  "config": {
    "network": {
      "cluster": {
        "newnetname": "cluster2",
        "network": "10.141.0.0/16",
        "gateway": "10.141.255.254",
        "nameserver_ip": "10.141.255.254",
        "ntp_server": "10.141.255.254",
        "comment": "Default cluster network",
        "dhcp": true,
        "dhcp_range_begin": "10.141.0.200",
        "dhcp_range_end": "10.141.0.253"
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 200 OK will be expected to be returned.

HTTP 201 Created will be expected to be returned when a new object is created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Deleting network information (GET /config/network/{networkname}/_delete)

Request

GET /config/network/cluster/_delete

Request body


Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 201 Created will be expected to be returned when a new object is created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get IP Address information (GET /config/network/{ipaddr})

Request

GET /config/network/cluster/10.141.0.3

Request header


Response body

{
  "config": {
    "network": {
      "10.141.0.1": {
        "status": "free"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned when the query executes. The client is responsible for handling the response

HTTP 404 Not found when the IP is not in the network range (out-of-scope)

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get all taken IP address with device name (GET /config/network/{networkname}/_member)

This API will fetch all the taken IP address with there device names.

Request

GET /config/network/cluster/_member

Request header


Response body

{
  "config": {
    "network": {
      "cluster": {
        "taken": [
            {"ipaddress": "10.141.255.254", "device": "controller"},
            {"ipaddress": "10.141.0.1", "device": "node001"},
            {"ipaddress": "10.141.0.2", "device": "node003"},
            {"ipaddress": "10.141.0.3", "device": "switch001"},
            {"ipaddress": "10.141.0.4", "device": "otherdevice003"}
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned when the query executes. The client is responsible for handling the response

HTTP 404 Not found when the IP is not in the network range (out-of-scope)

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get next available IP address (GET /config/network/{networkname}/_nextfreeip)

The Next IP will search the database for the next available IP address:

  • check database for occupied nodes, otherdev addresses,

  • removing the gateway and network addresses

  • returning the first available address in the range

The client is responsible for processing this, no reservation is made.

Request

GET /config/network/cluster/_nextfreeip

Request header


Response body

{
  "config": {
    "network": {
      "cluster": {
        "nextip": "10.141.0.2"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned when the query executes. The client is responsible for handling the response

HTTP 404 Not found when the IP is not in the network range (out-of-scope)

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get the status of a single IP address (GET /config/network/{name}/{ipaddress})

Request

GET /config/network/cluster/10.141.0.10

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "network": {
      "10.141.0.10": {
        "status": "taken"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned. The reported status is either taken or free.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the network does not exist or the IP address is not within its range.

BMC Management

BMC management entails the ipmi settings. The actual trigger to setup the BMC is done in the group or node configuration using the setupbmc boolean.

Get the list of BMC settings (GET /config/bmcsetup)

Request

GET /config/bmcsetup

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "bmcsetup": {
      "dell": {
        "mgmtchannel": 1,
        "netchannel": 1,
        "password": "calvin",
        "username": "root",
        "userid": 2,
        "comment": "Default DELL"
      },
      "gigabyte": {
        "mgmtchannel": 1,
        "netchannel": 1,
        "password": "password",
        "username": "admin",
        "userid": 2,
        "comment": "Default Gigabyte"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get the list of nodes in BMC setup (GET /config/bmcsetup/{name}/_member)

Request

GET /config/bmcsetup/dell/_member

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "bmcsetup": {
      "ipmi": {
        "members": [
          "node001",
          "node002",
          "node003",
          "node004"
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Show BMC setup (GET /config/bmcsetup/{bmcname})

Request

GET /config/bmcsetup/dell

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "bmcsetup": {
      "dell": {
        "mgmtchannel": 1,
        "netchannel": 1,
        "password": "calvin",
        "username": "root",
        "userid": 2,
        "comment": "Default DELL"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create, configure or rename BMC setup (POST /config/bmcsetup/{bmcname})

Renaming is done by setting the newbmcname field.

Request

POST /config/bmcsetup/dell

Request body

{
  "config": {
    "bmcsetup": {
      "dell": {
        "newbmcname": "dell2"
        "mgmtchannel": 1,
        "netchannel": 1,
        "password": "calvin",
        "username": "root",
        "userid": 2,
        "comment": "Default DELL"
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 200 OK will be expected to be returned when updating fields

HTTP 201 Created will be expected when the BMC setup is created

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Clone BMC setup (POST /config/bmcsetup/{bmcname}/_clone)

Cloning is done by setting the newbmcname field. In this example the dell bmcsetup is cloned to dell2 .

Request

POST /config/bmcsetup/dell/_clone

Request body

{
  "config": {
    "bmcsetup": {
      "dell": {
        "newbmcname": "dell2"
        "mgmtchannel": 1,
        "netchannel": 1,
        "password": "calvin",
        "username": "root",
        "userid": 2,
        "comment": "Default DELL"
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 201 Created will be expected when the BMC setup is created

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete BMC setup (GET /config/bmcsetup/{bmcname}/_delete)

Removing an object is done by calling the _delete on the object.

Request

GET /config/bmcsetup/dell/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected when the object is successfully deleted

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Image management

Image management is mostly token based, as it made introduce breaking changes to the system.

Get a list of images (GET /config/osimage):

Request

GET /config/osimage

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osimage": {
      "compute": {
        "grab_exclude": [
          "/dev",
          "/proc",
          "/sys"
        ],
        "grab_filesystems": [
          "/",
          "/boot"
        ],
        "initrdfile": "compute-initramfs-`uname -r`",
        "kernelfile": "compute-kernel-`uname -r`",
        "kernelmodules": "ipmi_devinft, ipmi_si, ipmi_msghandler",
        "kerneloptions": "mitigations=off nosmt noht",
        "kernelversion": "`uname -r`",
        "path": "/trinity/images/compute",
        "imagefile": "compute.tar.bz2",
        "comment": "Default image"
      },
      "compute-ib": {
        "grab_exclude": [
          "/dev",
          "/proc",
          "/sys"
        ],
        "grab_filesystems": [
          "/",
          "/boot"
        ],
        "initrdfile": "compute-initramfs-`uname -r`",
        "kernelfile": "compute-kernel-`uname -r`",
        "kernelmodules": "ipmi_devinft, ipmi_si, ipmi_msghandler",
        "kerneloptions": "mitigations=off nosmt noht",
        "kernelversion": "`uname -r`",
        "path": "/trinity/images/compute-ib",
        "imagefile": "compute.tar.bz2",
        "comment": "Default image with updated drivers"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a list members of the osimage (GET /config/osimage/{osimage}/_member)

Request

GET /config/osimage/{osimage}/_member

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osimage": {
      "compute-b": {
        "members": [
          "node001",
          "node002",
          "node003",
          "node004"
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get osimage information (GET /config/osimage/{osimage})

Request

GET /config/osimage/compute

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osimage": {
      "compute": {
        "grab_exclude": [
          "/dev",
          "/proc",
          "/sys"
        ],
        "grab_filesystems": [
          "/",
          "/boot"
        ],
        "initrdfile": "compute-initramfs-`uname -r`",
        "kernelfile": "compute-kernel-`uname -r`",
        "kernelmodules": "ipmi_devinft, ipmi_si, ipmi_msghandler",
        "kerneloptions": "mitigations=off nosmt noht",
        "kernelversion": "`uname -r`",
        "path": "/trinity/images/compute",
        "imagefile": "compute.tar.bz2",
        "comment": "Default image"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Updating or creating osimage information (POST /config/osimage/{osimage})

Note that when posting to a non-existing osimage name, it will create the image with the settings submitted.

Request

POST /config/osimage/compute

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "osimage": {
      "compute": {
        "comment": "Default image",
        "distribution": "redhat",
        "grab_exclude": [
          "/dev",
          "/proc",
          "/sys"
        ],
        "grab_filesystems": [
          "/",
          "/boot"
        ],
        "initrdfile": "compute-initramfs-`uname -r`",
        "kernelfile": "compute-kernel-`uname -r`",
        "kernelmodules": "ipmi_devinft, ipmi_si, ipmi_msghandler",
        "kerneloptions": "mitigations=off nosmt noht",
        "kernelversion": "`uname -r`",
        "path": "/trinity/images/compute",
        "imagefile": "compute.tar.bz2"
      }
    }
  }
}

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 201 Created will be expected when a new object is created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete osimage (GET /config/osimage/{osimage}/_delete)

Request

GET /config/osimage/compute/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Renaming osimage (POST /config/osimage/{osimage})

This example will rename the image compute to compute-ib.

Request

POST /config/osimage/compute/

Request body

{
  "config": {
    "osimage": {
      "compute": {
        "newosimage": "compute-ib"
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the newosimage field is not set.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Cloning osimage (POST /config/osimage/{osimage}/_clone)

This example will clone the image compute to compute-ib.

Request

POST /config/osimage/compute/_clone

Request body

{
  "config": {
    "osimage": {
      "compute": {
        "newosimage": "compute-ib"
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response header

HTTP 201 Created will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the newosimage field is not set.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Packing osimage (GET /config/osimage/{osimage}/_pack)

This example will pack the osimage compute.

Request

GET /config/osimage/compute/_pack

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Changing kernel version in osimage (incl. pack) (POST /config/osimage/{osimage}/kernel)

This example will pack the osimage compute, as well as triggering a pack afterwards.

Request

POST /config/osimage/compute/kernel

Request body

{
  "config": {
    "osimage": {
      "compute": {
        "initrdfile": "compute-initramfs-`uname -r`",
        "kernelfile": "compute-kernel-`uname -r`",
        "kernelversion": "`uname -r`"
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get osimage+osimage tag information (GET /config/osimagetag)

Request

GET /config/osimagetag

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osimagetag": {[
       "versionx": {
          "name": "versionx",
          "osimage": "compute",
          "initrdfile": "compute-initramfs-`uname -r`",
          "kernelfile": "compute-kernel-`uname -r`",
          "imagefile": "uuid"
        }
     ]}
   }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get osimage+osimage tag information (GET /config/osimagetag/{osimage})

Request

GET /config/osimagetag/compute

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osimagetag": {[
       "versionx": {
          "name": "versionx",
          "osimage": "compute",
          "initrdfile": "compute-initramfs-`uname -r`",
          "kernelfile": "compute-kernel-`uname -r`",
          "imagefile": "uuid"
        }
     ]}
   }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Changing/creating tag in osimage (POST /config/osimage/{osimage}/tag)

Request

POST /config/osimage/compute/tag

Request body

{
  "config": {
    "osimage": {
      "compute": {
        "tag": "version1"
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned for change, create or update.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a list members of the osimage+osimagetag (GET /config/osimagetag/{osimage}/_member)

Request

GET /config/osimagetag/{osimage}/_member

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osimage": {
      "compute-b": {
        "members": [
          "node001",
          "node002",
          "node003",
          "node004"
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete osimagetag (GET /config/osimage/{osimage}/osimagetag/{tagname}/_delete) ← should we rename osimagetag to just tag to be consistent with the POST request?

Request

GET /config/osimage/compute/osimagetag/versionx/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Secret management

Secrets (encrypted data) may not be revealed without a valid token. The secrets endpoint is token only.

Secrets are stored on node and group level, proper resolving of the hierarchy is the responsibility of the API.

Secrets can be requested on different levels:

  • Global (list)

  • Overview of node (incl. group)

  • Overview of group

  • Single item from node

  • Single item from group

Get a list of secrets (GET /config/secrets):

Request

GET /config/secrets

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "secrets": {
      "node": {
        "node001": [
          {
            "secretname": "shared secret",
            "content": "<ENC>",
            "path": "/etc/keys.crt"
          },
          {
            "secretname": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          },
          {
            "secretname": "shared secret",
            "content": "<ENC>",
            "path": "/etc/keys.crt"
          }
        ],
        "node002": [
          {
            "secretname": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          }
        ]
      },
      "group": {
        "compute": [
          {
            "secretname": "Proprietary key",
            "content": "<ENC>",
            "path": "/var/lib/key.pem"
          }
        ],
        "compute-ib": [
          {
            "secretname": "Infiniband",
            "content": "<ENC>",
            "path": "/etc/rdma/license.lic"
          }
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a list of secrets, any auth (POST /config/secrets):

Request

POST /config/secrets

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 400 Bad request since it is an unsupported request

Retrieve all secrets for a node (GET /config/secrets/node/{node})

Token is required. Note that the secrets from the group membership must also be resolved and provided.

Request

GET /config/secrets/node/node002

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "secrets": {
      "node": {
        "node002": [
          {
            "secretname": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          }
        ]
      },
      "group": {
        "compute-ib": [
          {
            "secretname": "Infiniband",
            "content": "<ENC>",
            "path": "/etc/rdma/license.lic"
          }
        ]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Update all secrets for a node (POST /config/secrets/node/{node})

Request

POST /config/secrets/node/node001

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "secrets": {
      "node": {
        "node001": [
          {
            "secretname": "shared secret",
            "content": "<ENC>",
            "path": "/etc/keys.crt"
          },
          {
            "secretname": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          },
          {
            "secretname": "shared secret",
            "content": "<ENC>",
            "path": "/etc/keys.crt"
          }
        ]
      }
    }
  }
}

Response body


Response header

HTTP 200 OK will be expected to be returned when no updates have occurred

HTTP 201 Created is expected when one or more creations have occurred

HTTP 204 No content is expected when one or more updates have occurred

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Retrieve a single secret from a node (GET /config/secrets/node/{node}/{secret})

Token is required.

Request

GET /config/secrets/node/node002/software%20license

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "secrets": {
      "node": {
        "node002": [
          {
            "secretname": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          }
        ]
      }
    }
  }
}

Response header

HTTP 204 No content will be expected to be returned when the query executed successfully.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Updating a single secret from a node (POST /config/secrets/node/{node}/{secret})

In this example, a node and secret name must be specified.

Request

POST /config/secrets/node/node002/software%20license

Request body

{
  "config": {
    "secrets": {
      "node": {
        "node001": [
          {
            "secretname:": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          }
        ]
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

A HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not Found is mandatory if the object is not found

HTTP 503 Service unavailable is returned when the backend is unavailable.

Cloning a secret from a node (POST /config/secrets/node/{node}/{secret}/_clone)

In this example, a nodeand secret name must be specified.

Token is required.

Request

POST /config/secrets/node/node001/software%20license/_clone

Request body

{
  "config": {
    "secrets": {
      "node": {
        "node001": [
          {
            "secretname": "software license",
            "newsecretname": "software license2",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          }
        ]
      }
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response header

HTTP 201 Created will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the newsecret field is not set.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Deleting a secret from a node (GET /config/secrets/node/{node}/{secret}/_delete)

In this example, a node and secret name must be specified.

Token is required.

Request

GET /config/secrets/node/node002/software%20license/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

A HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not Found is mandatory if the object is not found

HTTP 503 Service unavailable is returned when the backend is unavailable.

Retrieve all secrets for a group (GET /config/secrets/group/{group})

Token is required.

Request

GET /config/secrets/group/compute

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "secrets": {
    "group": {
      "compute": [
        {
          "secretname": "Proprietary key",
          "content": "<ENC>",
          "path": "/var/lib/key.pem"
        }
      ]
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Updating all secrets for a group (POST /config/secrets/group/{group})

Request

POST /config/secrets/group/compute

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "secrets": {
      "group": {
        "compute": [
          {
            "secretname": "Proprietary key",
            "content": "<ENC>",
            "path": "/var/lib/key.pem"
          }
        ]
      }
    }
  }
}

Response body


Response header

HTTP 200 OK will be expected to be returned when no updates have occurred

HTTP 201 Created is expected when one or more creations have occurred

HTTP 204 No content is expected when one or more updates have occurred

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Retrieve a single secret from a group (GET /config/secrets/group /{group }/{secret})

Token is required.

Request

GET /config/secrets/group/compute-ib/Infiniband

Request body

{
  "secrets": {
    "group": {
      "compute": null,
      "compute-ib": [
        {
          "secretname": "Infiniband",
          "content": "<ENC>",
          "path": "/etc/rdma/license.lic"
        }
      ]
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned when the query executed successfully.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Retrieve all secrets for a group (POST /config/secrets/group/{group})

Request

POST /config/secrets/group/compute-ib

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 400 Bad request since it is an unsupported request

Updating a single secret from a group (POST /config/secrets/group /{group }/{secret})

In this example, a group and secret name must be specified.

Request

POST /config/secrets/group/compute-ib/Infiniband
{
  "secrets": {
    "group": {
      "compute-ib": [
        {
          "secretname": "Infiniband",
          "content": "<ENC>",
          "path": "/etc/rdma/license.lic"
        }
      ]
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

A HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not Found is mandatory if the object is not found

HTTP 503 Service unavailable is returned when the backend is unavailable.

Cloning a secret from a group (POST /config/secrets/group /{group }/{secret}/_clone)

In this example, a group and secret name must be specified.

Token is required.

Request

POST /config/secrets/group/compute-ib/Infiniband/_clone

Request body

{
  "secrets": {
    "group": {
      "compute-ib": [
        {
          "secretname": "Infiniband",
          "newsecretname": "Infiniband2"
          "content": "<ENC>",
          "path": "/etc/rdma/license.lic"
        }
      ]
    }
  }
}

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response header

HTTP 201 Created will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the newsecret field is not set.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Deleting a secret from a group (GET /config/secrets/group /{group }/{secret}/_delete)

In this example, a group and secret name must be specified.

Token is required.

Request

GET /config/secrets/group/compute-ib/Infiniband/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

A HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not Found is mandatory if the object is not found

HTTP 503 Service unavailable is returned when the backend is unavailable.

Switch management

Switches are used for identifying nodes. Also creating them and assigning them an IP address will create an entry into the CMDB.

Get a list of switches (GET /config/switch):

Request

GET /config/switch

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "switch": {
      "switch01": {
        "network": "cluster",
        "ipaddress": "10.141.253.1",
        "oid": ".1.3.6.1.2.1.17.7.1.2.2.1.2",
        "read": "public",
        "rw": "private",
        "comments": "Bootswitch"
      },
      "switch02": {
        "network": "ipmi",
        "ipaddress": "10.148.253.1",
        "oid": ".1.3.6.1.2.1.17.7.1.2.2.1.2",
        "read": "public",
        "rw": "private",
        "comments": "Bootswitch"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get switch information (GET /config/switch/{switch}):

Request

GET /config/switch/switch01

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "switch": {
      "switch01": {
        "network": "cluster",
        "ipaddress": "10.141.253.1",
        "oid": ".1.3.6.1.2.1.17.7.1.2.2.1.2",
        "read": "public",
        "rw": "private",
        "comments": "Bootswitch"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not found is mandatory if object doesn’t exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update switch information (POST /config/switch/{switch}):

Renaming the switch is done by passing the newswitchname field.

Note that a switch with the network and ipaddress configured will create an entry in the CMDB.

Request

POST /config/switch/switch01

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "switch": {
      "switch01": {
        "network": "cluster",
        "ipaddress": "10.141.253.1",
        "oid": ".1.3.6.1.2.1.17.7.1.2.2.1.2",
        "read": "public",
        "rw": "private",
        "comments": "Bootswitch"
      }
    }
  }
}

Response body


Response header

HTTP 201 Created will be expected to be returned when a switch is created

HTTP 204 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Clone switch (POST /config/switch/{switch}/_clone):

Cloning is done by passing the newswitchname field.

Request

POST /config/switch/switch01

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "switch": {
      "switch01": {
        "network": "cluster",
        "newswitchname": "mgmsw01",
        "ipaddress": "10.141.253.1",
        "oid": ".1.3.6.1.2.1.17.7.1.2.2.1.2",
        "read": "public",
        "rw": "private",
        "comments": "Bootswitch"
      }
    }
  }
}

Response body


Response header

HTTP 201 Created will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not found is mandatory if object doesn’t exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete switch (GET /config/switch/{switch}/_delete):

Request

GET /config/switch/switch01/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Other devices management

The otherdev section is used to create entries in the CMDB, for non-bootable devices and switches. These objects are usually PDU, UPS or other externally managed devices.

Get a list of otherdev devices (GET /config/otherdev):

Request

GET /config/otherdev

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "otherdev": {
      "apc01": {
        "network": "cluster",
        "ipaddress": "10.141.250.1",
        "comments": "APC for rack01a"
      },
      "ups01": {
        "network": "ipmi",
        "ipaddress": "10.148.250.1",
        "comments": "UPS for the head node"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get otherdev information (GET /config/otherdev/{device}):

Request

GET /config/otherdev/apc01

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "otherdev": {
      "apc01": {
        "network": "cluster",
        "ipaddress": "10.141.250.1",
        "comments": "APC for rack01a"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not found is mandatory if object doesn’t exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update otherdev information (POST/config/otherdev/{device}):

Renaming is done by passing the newotherdevname field.

Request

POST /config/otherdev/apc01

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "otherdev": {
      "apc01": {
        "network": "cluster",
        "ipaddress": "10.141.250.1",
        "comments": "APC for rack01a"
      }
    }
  }
}

Response body


Response header

HTTP 201 Created will be expected to be returned when a new device is created

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Clone otherdev information (POST/config/otherdev/{device}/_clone):

Cloning is done by passing the newotherdevname field.

Request

POST /config/otherdev/apc01/_clone

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "otherdev": {
      "apc01": {
        "network": "cluster",
        "newotherdevname": "apc01b",
        "ipaddress": "10.141.250.1",
        "comments": "APC for rack01a"
      }
    }
  }
}

Response body


Response header

HTTP 201 Created will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Deleting otherdev device (GET /config/otherdev/{device}/_delete):

Request

GET /config/otherdev/apc01/_delete

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body


Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Service management

Reload DNS

Note that Luna2 will automatically schedule a reload once changes have been made to objects which have changed the network and/or ipaddress field.

Request

GET /service/dns/reload

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 200 OK will be expected to be returned.

HTTP 204 No Content will be returned when the service is in cooldown

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Reload DHCP

Request

GET /service/dhcp/reload

Request body



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 200 OK will be expected to be returned.

HTTP 204 No Content will be returned when the service is in cooldown

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Reload Luna2

This is required when templates on the filesystem have manually changed.

Request

GET /service/luna2/reload

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 200 OK will be expected to be returned.

HTTP 204 No Content will be returned when the service is in cooldown

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 503 Service unavailable is returned when the backend is unavailable.

Poll the result of a service action (GET /service/status/{request_id})

Request

GET /service/status/8129

Response body

{
  "message": "2026-06-10 12:00:00 :: restarting dhcp;;2026-06-10 12:00:02 :: dhcp restarted",
  "status": 200
}

Response header

HTTP 200 OK will be expected to be returned while results are available. Poll again until the request is complete.

HTTP 404 Not Found is returned when there is no data for this request id.

Monitoring handles

Monitoring DNS service

Request

GET /monitor/service/dns

Request header


Response body

{
  "monitor": {
    "service": {
      "dns": "OK, running"
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 204 No Content will be returned when the service is in cooldown

HTTP 500 Internal Server Error is returned when the service is unavailable.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Monitoring DHCP service

Request

GET /monitor/service/dhcp

Request header


Response body

{
  "monitor": {
    "service": {
      "dns": "OK, reloaded"
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 204 No Content will be returned when the service is in cooldown

HTTP 500 Internal Server Error is returned when the service is unavailable.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Monitoring Luna2 service

Request

GET /monitor/service/luna2

Request header


Response body

{
  "monitor": {
    "service": {
      "luna2": "OK"
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 204 No Content will be returned when the service is in cooldown

HTTP 500 Internal Server Error is returned when the service is unavailable.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Node monitoring (GET /monitor/node/{node})

Request

GET /monitor/node/node001

Request header


Response body

{
  "monitor": {
    "status": {
      "node001": {
        "status": "Luna installer: No errors",
        "state": "installer.ok"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned when the node is OK

HTTP 500 Internal Server Error is when the node is not OK

HTTP 503 Service unavailable is returned when the backend is unavailable.

Node monitoring (POST /monitor/node/{node})

Meant to be called from the LUNA installer only. Once the node is only, a monitoring stack will be available.

Request

POST /monitor/node/node001

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "monitor": {
    "status": {
      "node001": {
        "status": "Luna installer: No errors",
        "state": "installer.ok"
      }
    }
  }
}

Response body


Response header

HTTP 204 No Content will be expected when the node contents have been successfully updated

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not Found is to be returned when the node does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Cluster monitoring status (GET /monitor/status)

Request

GET /monitor/status

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": [
      {
        "request_id": "a1b2c3d4",
        "username_initiator": "admin",
        "created": "2026-06-10 09:15:42",
        "read": 0,
        "message": "osimage compute build started"
      }
    ]
  }
}

The handler returns every message still held in the status table, ordered by creation time; each entry carries request_id, username_initiator, created, read and message. When the table is empty the list is returned empty.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Push cluster monitoring status (POST /monitor/status)

Request

POST /monitor/status

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "monitor": {
    "status": {
      "request_id": "a1b2c3d4",
      "messages": [
        { "message": "osimage compute sync finished" }
      ]
    }
  }
}

This route receives remote status messages and appends them to the local status table; it is not tied to a node. The payload must contain monitor.status.request_id. Either a list of messages (each with a message, and optionally remote_request_id/remote_host) or a single remote reference (remote_request_id plus remote_host) is accepted.

Response body

{
  "message": "success"
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Node monitoring state (GET /monitor/node)

Request

GET /monitor/node

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "node": {
        "node001": {
          "state": "node001 ok",
          "status": "ready"
        }
      }
    }
  }
}

Each node is keyed by name and reports a state string (the node name followed by its state) and an interpreted status.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

HA monitoring summary (GET /monitor/ha)

Request

GET /monitor/ha

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "ha": {
        "controller": {
          "state": "controller ok",
          "status": "active"
        }
      }
    }
  }
}

Every HA reference entry is returned, keyed by its name, with a state string and a status.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

HA monitoring for one controller (GET /monitor/ha/{name})

Request

GET /monitor/ha/controller

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "controller": {
        "status": "active",
        "state": "controller ok"
      }
    }
  }
}

The single HA entry is keyed by the requested name; if no monitor row exists for it the endpoint responds with HTTP 404 Not Found.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Mother monitoring summary (GET /monitor/mother)

Request

GET /monitor/mother

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "mother": {
        "controller": {
          "state": "controller ok",
          "status": "running"
        }
      }
    }
  }
}

Every mother/core reference entry is returned, keyed by its name, with a state string and a status.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Mother monitoring for one entry (GET /monitor/mother/{name})

Request

GET /monitor/mother/controller

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "controller": {
        "status": "running",
        "state": "controller ok"
      }
    }
  }
}

The single mother entry is keyed by the requested name; if no monitor row exists for it the endpoint responds with HTTP 404 Not Found.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

OS image monitoring summary (GET /monitor/osimage)

Request

GET /monitor/osimage

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "osimage": {
        "compute": {
          "state": "compute ok",
          "status": "built"
        }
      }
    }
  }
}

Every OS image is returned, keyed by image name, with its build/sync state string and a status.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

OS image monitoring for one image (GET /monitor/osimage/{name})

Request

GET /monitor/osimage/compute

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "compute": {
        "status": "built",
        "state": "compute ok"
      }
    }
  }
}

The single image is keyed by the requested name and reports the recorded status and state; if no monitor row exists for it the endpoint responds with HTTP 404 Not Found.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Task queue status (GET /monitor/queue)

Request

GET /monitor/queue

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "queue": [
      {
        "level": "maintask",
        "queue_id": 12,
        "request_id": "a1b2c3d4",
        "username_initiator": "admin",
        "created": "2026-06-10 09:15:42",
        "subsystem": "osimage",
        "task": "pack_n_build compute",
        "status": "queued"
      }
    ]
  }
}

Each queued task is reported with a level of maintask or subtask, a queue_id, and its request_id, username_initiator, created, subsystem, task (with any parameter appended) and status.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Sync monitoring summary (GET /monitor/sync)

Request

GET /monitor/sync

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "sync": {
        "compute": {
          "state": "compute ok",
          "status": "synced"
        }
      }
    }
  }
}

Sync state is derived from the OS image entries; each is keyed by image name and reports a state string and a status.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Sync monitoring for one entry (GET /monitor/sync/{name})

Request

GET /monitor/sync/compute

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "monitor": {
    "status": {
      "compute": {
        "status": "synced",
        "state": "compute ok"
      }
    }
  }
}

The single sync entry is keyed by the requested name and reports the recorded status and state; if no monitor row exists for it the endpoint responds with HTTP 404 Not Found.

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Control API

The control API is used by the Luna tools such as lpower or any scripts to control nodes.

Currently implemented:

  • power control (on, off, reset, identify, noidentify,status)

Control API (GET /control/action/{command}/{hostname}/_{action})

The control GET API supports a single hostname

Request

GET /control/action/power/node001/_on
GET /control/action/power/node001/_off
GET /control/action/power/node001/_status


GET /control/action/sel/node001/_list
GET /control/action/sel/node001/_clear

GET /control/action/chassis/node001/_identify
GET /control/action/chassis/node001/_noidentify

POST /control/action/redfish/node001/_upload -> connect naar BMC address -> uploads json
POST /control/action/redfish/node001/_setting -> connect naar BMC address -> set "uri /redfish/v1/Systems/{system}/BootOptions"

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body


Response body

No body is expected for on, off, reset, identify, noidentify

{
control: {
    (command){
        # This only commands / fire forget
        ok: { "command issued" } (returned with sel/identify only) <- catch exit 0 for fire and forget stuff
        # status
        on: {
             node001: None,
             node002: None,
        },(returned with power)
        off: {
            node002: None,
        } (returned with power)
    }
    failed: {
        node005: None,
        node003: "blabla"  <- ipmitool stacktrace / command failed / connection lost / time out / command does not exist <- exit not 0
    }
}

A body is expected for the status

Only for the status command, return status, e.g. on, off. For all other commands empty return with the corresponding HTTP code


Response header

HTTP 204 No Content will be expected when the command executed

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not Found is to be returned when the node does not exist

HTTP 500 Internal Server error is to be returned when the command failed

HTTP 503 Service unavailable is returned when the backend is unavailable.

Control API (POST /control/action/power/_on)

{
control: {
    power: {
        "on":{
             hostlist: "node[001-004]"
             }
    }
}

Control API (POST /control/action/chassis/_identify)

{
control: {
    chassis: {
        "identify":{
             hostlist: "node[001-004]"
             }
    }

}

Control API (POST /control/action/{command}/_{action})

The control POST API supports multiple hostnames (specified as python hostlists)

Currently implemented:

  • power control (on, off, reset, identify, noidentify,status)

After a success, the hostname and action need to be returned. On a partial or failure, the hosts need to be sorted under that action.

Request

POST /control/action/sel/_list

Request header



x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "control": {
    "power": {
      "on": {
        "hostlist": "node[001-004]"
      }
    }
  }
}

Response body

In this example output, node002 has failed, while node001,003 and 004 are successful:

{
  "control": {
    "power": {
      "on": {
        "hostlist": "node[001,node003-004]"
      },
      "failed": {
        "hostlist": "node[002]"
      }
    }
  }
}

Another example when the status command is issued; the status may differ

{
  "control": {
    "power": {
      "on": {
        "hostlist": "node[001,node004]"
      },
      "off": {
        "hostlist": "node[003]"
      },
      "failed": {
        "hostlist": "node[002]"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected when the control command(s) have been carried out (incl. failed results)

HTTP 401 Unauthorized is mandatory if there is no valid token

HTTP 404 Not Found is to be returned when the hostlist is invalid

HTTP 503 Service unavailable is returned when the backend is unavailable.

Poll the result of a control action (GET /control/status/{request_id})

Request

GET /control/status/8128

Response body

{
  "request_id": "8128",
  "control": {
    "power": {
      "ok": {
        "node001": "power on"
      },
      "on": {},
      "off": {}
    },
    "failed": {}
  }
}

Response header

HTTP 200 OK will be expected to be returned while results are available. Poll again until the request is complete.

HTTP 404 Not Found is returned when there is no data for this request id.

Rack View

Get all the racks in detailed view

Request

GET /config/rack

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "config": {
        "rack": {
            "rack001": {
                "size": 52,
                "order": "ascending",
                "room": "Basement",
                "site": "ClusterVision Amsterdam",
                "name": "rack001",
                "devices": [
                    {"name": "controller", "type": "controller", "vendor": "Supermicro", "orientation": "front", "height": 1, "position": 5},
                    {"name": "node001", "type": "node", "vendor": "Dell", "orientation": "front", "height": 2, "position": 8}
                ]
            },
            "rack002": {
                "size": 52,
                "order": "descending",
                "room": "Basement",
                "site": "ClusterVision Amsterdam",
                "name": "rack002",
                "devices": [
                    {"name": "node002", "type": "node", "vendor": "GigaByte", "orientation": "front", "height": 4, "position": 27}
                ]
            },
            "rack006": {
                "size": 42,
                "order": "descending",
                "room": "1st Floor",
                "site": "ClusterVision Schiphol",
                "name": "rack006",
                "devices": []
            }
        }
    }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a single rack with detailed view

Request

GET /config/rack/{RACK-NAME}

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "config": {
        "rack": {
            "rack001": {
                "size": 52,
                "order": "ascending",
                "room": "Basement",
                "site": "ClusterVision Amsterdam",
                "name": "rack001",
                "devices": [
                    {"name": "node001", "type": "node", "vendor": "HP", "orientation": "front", "height": 1, "position": 5},
                    {"name": "node002", "type": "node", "vendor": "Lenovo", "orientation": "front", "height": 2, "position": 8}
                ]
            }
        }
    }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create a new or update a rack

Request

POST /config/rack/{RACK-NAME}

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "config": {
        "rack": {
            "rack001": {
                "size": 52,
                "order": "ascending",
                "room": "Basement",
                "site": "ClusterVision Amsterdam",
                "name": "rack001",
                "devices": [
                    {"name": "node001", "type": "node", "vendor": "HP", "orientation": "front", "height": 1, "position": 5},
                    {"name": "node002", "type": "node", "vendor": "Lenovo", "orientation": "front", "height": 2, "position": 8}
                ]
            }
        }
    }
}

Response header

HTTP 204 No content will be expected to be returned.

HTTP 201 Created will be expected when a new object is created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get all the inventories in detailed view

Request

GET /config/rack/inventory

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "config": {
        "rack": {
            "inventory": [
                {"name": "node001", "type": "node", "vendor": "Dell", "height": 1, "orientation": "front"},
                {"name": "node002", "type": "node", "vendor": "Dell",  "height": 2, "orientation": "front"}
            ]
        }
    }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get all the configured or unconfigured inventories in detailed view

Request

GET /config/rack/inventory/{SUBSET}

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "config": {
        "rack": {
            "inventory": [
                {"name": "node001", "type": "node", "vendor": "Dell", "height": 1, "orientation": "front"},
                {"name": "node002", "type": "node", "vendor": "Dell",  "height": 2, "orientation": "front"}
            ]
        }
    }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Update a Inventory

Request

POST /config/rack/inventory

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "config": {
        "rack": {
            "inventory": [
                {"name": "node001", "type": "node", "vendor": "Dell", "height": 1, "orientation": "front"},
                {"name": "node002", "type": "node", "vendor": "Dell",  "height": 2, "orientation": "front"}
            ]
        }
    }
}

Response header

HTTP 204 No content will be expected to be returned.

HTTP 201 Created will be expected when a new object is created.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete a Rack

Request

GET /config/rack/{RACK-NAME}/_delete 

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body


Response header

HTTP 204 No content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete a Inventory [Remove it from the Rack]

Request

GET /config/rack/inventory/{DEVICE_NAME}/type/{DEVICE_TYPE}/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "message": "Inventory cleared"
}

Response header

HTTP 201 With content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Journal

Get all the journal entries for a controller

Request

GET /journal/{controller}

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "journal": [
        {"function": "node_update", "object": "node001", "param": None, "payload": "IyBUaGlzIGZpbGUgd2FzIGdlbmVyYXRlZCBieSB3Zy1xdWljayg4KSBmb3IgdXNlIHdpdGgKIyB0", "masteronly": "0", "misc": None, "sendfor": "controller2", "sendby": "controller1", "created": "1713520340"},
        {"function": "osimage_pack", "object": "compute", "param": None, "payload": None, "masteronly": "1", "misc": "1703678426.721102268962463531", "sendfor": "controller2", "sendby": "controller1", "created": "1713520344"},
    ]
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Update journal with entries on controller

Request

POST /journal

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
    "journal": [
        {"function": "node_update", "object": "node001", "param": None, "payload": "IyBUaGlzIGZpbGUgd2FzIGdlbmVyYXRlZCBieSB3Zy1xdWljayg4KSBmb3IgdXNlIHdpdGgKIyB0", "masteronly": "0", "misc": None, "sendfor": "controller2", "sendby": "controller1", "created": "1713520340"},
        {"function": "osimage_pack", "object": "compute", "param": None, "payload": None, "masteronly": "1", "misc": "1703678426.721102268962463531", "sendfor": "controller2", "sendby": "controller1", "created": "1713520344"},
    ]
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is mandatory if the object does not exist

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get journal entries for a host (GET /journal/{name})

Request

GET /journal/controller

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "journal": [
    {
      "function": "Node.update_node",
      "object": "node001",
      "payload": "[...]"
    },
    { "...": "..." }
  ]
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when there are no journal entries for the host.

Clear journal entries for a host (GET /journal/{name}/_delete)

Request

GET /journal/controller/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

Response header

HTTP 204 No Content will be expected to be returned when the host's journal entries are deleted.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when there are no journal entries to delete.

Cloud management

Get a list of clouds (GET /config/cloud)

Request

GET /config/cloud

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "cloud": {
      "aws1": {
        "name": "aws1",
        "type": "aws",
        "comment": "Production AWS account"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a cloud (GET /config/cloud/{name})

Request

GET /config/cloud/aws1

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "cloud": {
      "aws1": {
        "name": "aws1",
        "type": "aws",
        "comment": "Production AWS account"
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the requested cloud does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update a cloud (POST /config/cloud/{name})

Request

POST /config/cloud/aws1

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "cloud": {
      "aws1": {
        "type": "aws",
        "comment": "Production AWS account"
      }
    }
  }
}

To rename an existing cloud, include the newcloudname field in the body. The cloud addressed by the URI is then renamed to this value:

{
  "config": {
    "cloud": {
      "aws1": {
        "newcloudname": "aws-prod",
        "type": "aws",
        "comment": "Production AWS account"
      }
    }
  }
}

Response body

{
  "message": "Cloud aws1 created successfully"
}

Response header

HTTP 201 Created is returned when a new cloud is created.

HTTP 204 No Content is returned when an existing cloud is updated.

HTTP 400 Bad Request is returned when the request contains no data or unknown columns.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete a cloud (GET /config/cloud/{name}/_delete)

Request

GET /config/cloud/aws1/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "message": "Cloud aws1 removed successfully"
}

Response header

HTTP 204 No Content is returned when the cloud is removed.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the requested cloud does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

DNS management

Get DNS record(s) for a network (GET /config/dns/{name})

The {name} URI parameter is the name of the network. All additional DNS host entries belonging to that network are returned.

Request

GET /config/dns/cluster

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "dns": {
      "cluster": [
        {
          "host": "mirror",
          "ipaddress": "10.141.0.5"
        },
        {
          "host": "license",
          "ipaddress": "10.141.0.6"
        }
      ]
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the network does not exist or has no additional DNS entries.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update DNS records for a network (POST /config/dns/{name})

The {name} URI parameter is the name of the network. The body carries a list of host entries; each entry must provide both a host and an ipaddress. Existing hosts on the network are updated, new hosts are inserted.

Request

POST /config/dns/cluster

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "dns": {
      "cluster": [
        {
          "host": "mirror",
          "ipaddress": "10.141.0.5"
        },
        {
          "host": "license",
          "ipaddress": "10.141.0.6"
        }
      ]
    }
  }
}

Response body

{
  "message": "DNS entries added or changed"
}

Response header

HTTP 201 Created is returned when the DNS entries are added or changed.

HTTP 400 Bad Request is returned when the request contains no data.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the network is not present in the database.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Delete a DNS record from a network (GET /config/dns/{network}/{name}/_delete)

The {network} URI parameter is the name of the network and {name} is the host entry to remove from it.

Request

GET /config/dns/cluster/mirror/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "message": "Entry removed"
}

Response header

HTTP 204 No Content is returned when the host entry is removed.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the host entry does not exist for the given network.

HTTP 503 Service unavailable is returned when the backend is unavailable.

OS user group management

Get a list of OS groups (GET /config/osgroup)

Request

GET /config/osgroup

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osgroup": {
      "users": {
        "gidNumber": 100,
        "member": ["alice", "bob"]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a single OS group (GET /config/osgroup/{name})

Request

GET /config/osgroup/users

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osgroup": {
      "users": {
        "gidNumber": 100,
        "member": ["alice", "bob"]
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the requested OS group does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update an OS group (POST /config/osgroup/{name})

Request

POST /config/osgroup/users

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "osgroup": {
      "users": {
        "gidNumber": 100,
        "member": ["alice", "bob"]
      }
    }
  }
}

Response body

{
  "message": "[obol: group users created]"
}

Response header

HTTP 201 Created will be expected to be returned when a new OS group is created.

HTTP 204 No content will be expected to be returned when an existing OS group is updated.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the request data is missing or the backend is unavailable.

Delete an OS group (GET /config/osgroup/{name}/_delete)

Request

GET /config/osgroup/users/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "message": "[obol: group users deleted]"
}

Response header

HTTP 204 No content will be expected to be returned when the OS group is deleted.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the requested OS group does not exist.

OS user management

Get a list of OS users (GET /config/osuser)

Request

GET /config/osuser

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osuser": {
      "alice": {
        "uidNumber": 1050,
        "gidNumber": 100,
        "cn": "Alice Anderson",
        "sn": "Anderson",
        "givenName": "Alice",
        "mail": "alice@controller",
        "telephoneNumber": "555-0100",
        "loginShell": "/bin/bash",
        "homeDirectory": "/home/alice",
        "memberOf": ["users"],
        "shadowExpire": -1
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get a single OS user (GET /config/osuser/{name})

Request

GET /config/osuser/alice

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "config": {
    "osuser": {
      "alice": {
        "uidNumber": 1050,
        "gidNumber": 100,
        "cn": "Alice Anderson",
        "sn": "Anderson",
        "givenName": "Alice",
        "mail": "alice@controller",
        "telephoneNumber": "555-0100",
        "loginShell": "/bin/bash",
        "homeDirectory": "/home/alice",
        "memberOf": ["users"],
        "shadowExpire": -1
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the requested OS user does not exist.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Create or update an OS user (POST /config/osuser/{name})

Request

POST /config/osuser/alice

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "config": {
    "osuser": {
      "alice": {
        "uidNumber": 1050,
        "gidNumber": 100,
        "userPassword": "s3cr3t",
        "cn": "Alice Anderson",
        "sn": "Anderson",
        "givenName": "Alice",
        "mail": "alice@controller",
        "telephoneNumber": "555-0100",
        "loginShell": "/bin/bash",
        "homeDirectory": "/home/alice",
        "memberOf": ["users"],
        "shadowExpire": -1
      }
    }
  }
}

Response body

{
  "message": "[obol: user alice created]"
}

Response header

HTTP 201 Created will be expected to be returned when a new OS user is created.

HTTP 204 No content will be expected to be returned when an existing OS user is updated.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the request data is missing or the backend is unavailable.

Delete an OS user (GET /config/osuser/{name}/_delete)

Request

GET /config/osuser/alice/_delete

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "message": "[obol: user alice deleted]"
}

Response header

HTTP 204 No content will be expected to be returned when the OS user is deleted.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not found is returned when the requested OS user does not exist.

High Availability

HA liveness check (GET /ping)

Request

GET /ping

This endpoint requires no token; it always replies with a small JSON acknowledgement and updates the controller's internal ping timestamp.

Response body

{
  "message": "pong"
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 503 Service unavailable is returned when the backend is unavailable.

HA state (GET /ha/state)

Request

GET /ha/state

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Returns the full HA record of this controller. The boolean flags (master, syncimages, enabled, insync, overrule) are normalised to true/false; updated holds the timestamp of the last state change.

Response body

{
  "ha": {
    "enabled": true,
    "syncimages": true,
    "insync": true,
    "sharedip": false,
    "overrule": false,
    "master": true,
    "updated": "2025-01-01 00:00:00"
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when HA is not available; the body is then {"message": "HA not available"}.

HA master role (GET /ha/master)

Request

GET /ha/master

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Returns whether this controller currently holds the master role (the boolean value of the master flag).

Response body

{
  "message": true
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the controller does not hold the master role.

Become HA master (GET /ha/master/_set)

Request

GET /ha/master/_set

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Sets the current controller as master. It first forces the insync flag to true, then records the role-change request and sets the master role. The body is a single message describing the outcome.

Response body

{
  "message": "current role set to master"
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the role could not be set to master (for example when insync could not be set, or the role change failed). The message then describes the reason.

Set HA overrule flag (GET /ha/overrule/_set)

Request

GET /ha/overrule/_set

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Sets the overrule flag, allowing this controller to proceed even when it is out of sync. Intended only for the case where all controllers are down and a single one is brought back up; use with caution. The body carries the boolean result of setting the flag.

Response body

{
  "message": true
}

Response header

HTTP 204 No Content will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

List HA controllers (GET /ha/controllers)

Request

GET /ha/controllers

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Returns the HA state and configuration for every known controller. The local controller reports its own HA record directly; every other controller is queried over /ha/state. Each entry also carries a config block with its shadow/beacon settings, and an explanatory comment when a controller could not be reached.

Response body

{
  "message": {
    "controller": {
      "ha": {
        "enabled": true,
        "master": true,
        "insync": true,
        "syncimages": true,
        "sharedip": false,
        "overrule": false,
        "updated": "2025-01-01 00:00:00"
      },
      "config": {
        "shadow": false,
        "beacon": false
      }
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when no controller data is available.

Sync image to controller (GET /ha/syncimage/{name})

Request

GET /ha/syncimage/image001

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

This endpoint is deprecated. Image synchronisation is now handled inline by the daemon, so the handler no longer triggers a sync and always reports that the operation is unavailable. The {name} path segment is validated as a name but is otherwise unused.

Response body

{
  "message": "sync not available for images"
}

Response header

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned, as image sync is no longer offered through this endpoint.

File downloads

List downloadable files (GET /files)

Request

GET /files

Response body

[
  "compute-image-20240101.tar.bz2",
  "compute-image-20240101.torrent"
]

Response header

HTTP 200 OK will be expected to be returned.

HTTP 503 Service unavailable is returned when no files are present or the backend is unavailable.

Download a file (GET /files/{filename})

This endpoint streams the requested file from the configured image-files directory. Authentication is enforced inside the handler only for image and torrent extensions (.gz, .tar, .bz, .bz2, .torrent); for those a valid token must be supplied in the x-access-tokens header. Other extensions are served without a token, since some files are fetched during early boot (PXE, kernel, ramdisk) before a token is available.

Request

GET /files/compute-image-20240101.tar.bz2

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

[... binary file stream ...]

Response header

HTTP 200 OK will be expected to be returned, with the file delivered as a binary stream.

HTTP 401 Unauthorized is returned for image/torrent files when the token is missing or invalid.

HTTP 503 Service unavailable is returned when the file cannot be served.

Authenticated file-access check (GET /filesauth)

This endpoint performs an authentication subrequest (for example, an nginx auth_request). It inspects the X-Original-URI header to determine the requested file and enforces a token only for image and torrent extensions (.gz, .tar, .bz, .bz2, .torrent). For all other URIs it returns a "go" without a token. When authentication is required, a valid token must be present in the x-access-tokens header.

Request

GET /filesauth

Request header

X-Original-URI: /files/compute-image-20240101.tar.bz2
x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "message": "Go"
}

Response header

HTTP 200 OK will be expected to be returned when access is granted.

HTTP 401 Unauthorized is returned when authentication is required but the token is missing or invalid.

Database tables

Get hashes of all tables (GET /table/hashes)

Request

GET /table/hashes

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "table": {
    "hashes": {
      "node": "8f14e45fceea167a5a36dedd4bea2543",
      "group": "c9f0f895fb98ab9159f51fd0297e236d",
      "...": "..."
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Get raw data for one table (GET /table/data/{name})

Request

GET /table/data/node

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Response body

{
  "table": {
    "data": {
      "node": [
        {
          "id": 1,
          "name": "node001",
          "...": "..."
        }
      ]
    }
  }
}

Response header

HTTP 200 OK will be expected to be returned.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 503 Service unavailable is returned when the backend is unavailable.

Provisioning tracker

The provisioning tracker is the built-in BitTorrent tracker used for torrent-based image provisioning. It is queried by the aria2 clients running on nodes during deployment. These endpoints return a bencoded, plain-text (text/plain) tracker response, not JSON, and are unauthenticated (no token header is required).

BitTorrent announce (GET /announce)

The announce endpoint registers a peer for a torrent and returns the current peer list. The client passes the standard BitTorrent query parameters, including info_hash and peer_id.

Request

GET /announce?info_hash=%12%34...&peer_id=-aria2-...&port=6881&uploaded=0&downloaded=0&left=0&compact=1

Response body

d8:intervali1800e5:peers[... bencoded peer data ...]e

Response header

HTTP 200 OK will be expected to be returned, with Content-Type: text/plain.

HTTP 400 Bad Request is returned when info_hash or peer_id is missing or invalid.

HTTP 500 Internal Server Error is returned when the response cannot be generated.

BitTorrent scrape (GET /scrape)

The scrape endpoint returns the state (seeders, leechers, completed) of the torrents the tracker manages. One or more info_hash parameters may be supplied; when none are given, all currently active torrents are reported.

Request

GET /scrape?info_hash=%12%34...

Response body

d5:filesd20:[... info_hash ...]d8:completei3e10:downloadedi0e10:incompletei1eeee

Response header

HTTP 200 OK will be expected to be returned, with Content-Type: text/plain.

HTTP 500 Internal Server Error is returned when the response cannot be generated.

Plugin import and export

Import data via an import plugin (POST /import/{name})

This endpoint forwards a request to the named import plugin (for example, prometheus rules). The request body is forwarded as-is to the plugin: if it is valid JSON it is parsed and passed as an object, otherwise the raw body is passed through unchanged.

Request

POST /import/prometheus

Request header

x-access-tokens: "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MSwiZXhwIjoxNjY4ODQyMTQwfQ"

Request body

{
  "rules": [
    {
      "alert": "NodeDown",
      "expr": "up == 0",
      "...": "..."
    }
  ]
}

Response body

[... plugin-defined response ...]

Response header

HTTP 200 OK will be expected to be returned when the plugin accepts the data.

HTTP 401 Unauthorized is mandatory if there is no valid token.

HTTP 404 Not Found is returned when the plugin does not exist or rejects the request.

Export data via an export plugin (GET /export/{name})

This endpoint calls the named export plugin and returns its data as-is. Any query-string parameters are passed through to the plugin. This route is unauthenticated; no token header is required.

Request

GET /export/prometheus

Response body

[... plugin-defined response ...]

Response header

HTTP 200 OK will be expected to be returned when the plugin produces data.

HTTP 404 Not Found is returned when the plugin does not exist or has no data to return.

TPM authentication

Obtain a node token via TPM attestation (POST /tpm/{nodename})

This endpoint issues a node token after validating the supplied TPM attestation against the named node. When cluster security is enabled, the request body must contain the node's tpm_sha256 value, which is matched against the value stored for the node. When cluster security is not enabled, the TPM value is stored and a token is returned (a username/password pair may be supplied instead and is forwarded to the standard token flow). On success the response contains a JWT valid for the configured expiry time. This route is unauthenticated; no token header is required to call it.

Request

POST /tpm/node001

Request body

{
  "tpm_sha256": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08"
}

Response body

{
  "token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpZCI6MCwiZXhwIjoxNjY4ODQyMTQwfQ"
}

Response header

HTTP 200 OK will be expected to be returned, with the node token in the body.

HTTP 401 Unauthorized is returned when the TPM information is missing, the node is invalid, or the attestation does not match.

Asynchronous requests

Some operations do not complete within the lifetime of the HTTP request. When a state-changing POST operation is queued for background processing — for example pushing or grabbing an osimage, or a bulk control or service action — the daemon responds immediately with a request_id alongside the message:

{
  "message": "queued",
  "request_id": "8125"
}

The result is then retrieved by polling the matching status endpoint until the operation finishes:

  • GET /config/status/{request_id} — for configuration operations such as osimage push and grab.
  • GET /control/status/{request_id} — for control (power) actions.
  • GET /service/status/{request_id} — for service (DHCP/DNS) actions.

Each poll returns the status messages collected so far and marks them as read, so successive calls return only new output. Continue polling until the operation is reported complete.

Poll the result of a configuration operation (GET /config/status/{request_id})

Request

GET /config/status/8125

Response body

The status messages collected for the request so far are returned, keyed by the request id. Each poll marks the returned messages as read, so a subsequent call returns only newer output.

{
  "8125": [
    {
      "created": "2026-06-10 09:15:42",
      "message": "osimage compute: packing started"
    },
    {
      "created": "2026-06-10 09:18:10",
      "message": "osimage compute: build finished"
    }
  ]
}

Response header

HTTP 200 OK will be expected to be returned while results are available. Poll again until the request is complete.

HTTP 404 Not Found is returned when there is no data for this request id.

Error handling

Status code

Description

Content

(tick) 200 OK

Indicates the request has succeeded

Return response required, if just a confirmation, send a 204

(tick) 201 Created

Indicates the request has succeeded and a new resource has been created

The new id

(tick) 204 No Content

The server has fulfilled the request but there is no response body

None

(error) 400 Bad Request

The request could not be understood.

The faulty fields may be indicated by the server

(error) 401 Unauthorized

The request requires user authentication

None

(error) 403 Forbidden

The client does not have access rights to the content

None

(minus) 404 Not Found

The server can not find the resource

The faulty fields may be indicated by the server

(error) 500 Internal Server Error

The server encountered an unexpected condition.

Send feedback

(error) 503 Service Unavailable

The server is not ready to handle the request.

Send feedback

Note there are no 300 codes: Either the system is in fault (500), it doesn’t exist (400), but there is no (300) redirection to any other endpoint.

Full spec JSON

JSON

{
  "config": {
    "node": {
      "node001": {
        "newhostname": "gpu001",
        "group": "compute",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet",
            "ipaddress": "10.141.0.1"
          },
          {
            "interface": "BMC",
            "network": "ipmi",
            "ipaddress": "10.148.0.1"
          },
          {
            "interface": "ib0",
            "network": "ib",
            "ipaddress": "10.149.0.1"
          }
        ],
        "switch": "switch01",
        "switchport": 1,
        "service": false,
        "setupbmc": true,
        "status": "installer.completed",
        "comment": null,
        "osimage": "compute",
        "prescript": "#!/bin/bash \n exit 0;",
        "partscript": "#!/bin/bash \n exit 0;",
        "postscript": "#!/bin/bash \n exit 0;",
        "netboot": true,
        "bootmenu": false,
        "provision_interface": null,
        "provision_method": null,
        "provision_fallback": null,
        "tpm_uuid": null,
        "tpm_pubkey": null,
        "tpm_sha256": null
      }
    },
    "group": {
      "compute": {
        "newgroupname": "compute-gpu",
        "bmcsetup": true,
        "domain": "cluster",
        "interfaces": [
          {
            "interface": "BOOTIF",
            "network": "clusternet"
          },
          {
            "interface": "BMC",
            "network": "ipmi"
          },
          {
            "interface": "ib0",
            "network": "ib"
          }
        ],
        "osimage": "compute",
        "partscript": "#!/bin/bash \n exit 0",
        "postscript": "#!/bin/bash \n exit 0",
        "prescript": "#!/bin/bash \n exit 0",
        "provision_interface": null,
        "netboot": true,
        "bootmenu": false,
        "comment": "Default group",
        "provision_method": "torrent",
        "provision_fallback": "http"
        "members": [
          "node001",
          "node002",
          "node003",
          "node004"
        ]
      }
    },
    "cluster": {
      "controller1": {
        "status": "primary",
        "ipaddr": "10.141.255.254",
        "serverport": 7050,
        "luna_config": "/trinity/local/luna/config/luna-daemon.ini"
      },
      "controller2": {
        "status": "standby",
        "ipaddr": "10.141.255.253",
        "serverport": 7050,
        "luna_config": "/trinity/local/luna/config/luna-daemon.ini"
      },
      "ntp_server": "10.141.255.252",
      "debug": false,
      "technical_contacts": "root@localhost",
      "provision_method": "torrent",
      "provision_fallback": "http"
    },
    "network": {
      "cluster": {
        "newnetname": "cluster2",
        "network": "10.141.0.0/16",
        "nameserver_ip": "10.141.255.254",
        "ntp_server": "10.141.255.254",
        "gateway": "10.141.255.254",
        "comment": "Default cluster network",
        "dhcp": true,
        "dhcp_range_begin": "10.141.0.200",
        "dhcp_range_end": "10.141.0.253"
      },
      "ipmi": {
        "newnetname": "ipmi2",
        "network": "10.148.0.0/16",
        "nameserver_ip": "10.148.255.254",
        "ntp_server": "10.148.255.254",
        "gateway": "10.148.255.254",
        "comment": "Default OOB network",
        "dhcp": false
      },
      "ib": {
        "newnetname": "ib2",
        "network": "10.149.0.0/16",
        "nameserver_ip": "10.149.255.254",
        "ntp_server": "10.149.255.254",
        "gateway": "10.149.255.254",
        "comment": "Default highspeed interconnect network",
        "dhcp": false
      }
    },
    "bmcsetup": {
      "dell": {
        "newbmcname": "newname",
        "mgmtchannel": 1,
        "netchannel": 1,
        "password": "calvin",
        "username": "root",
        "userid": 2,
        "comment": "Default DELL",
        "unmanaged_bmc_users": "skip",
        "members": [
          "node003",
          "node004"
        ]        
      },
      "gigabyte": {
        "newbmcname": "newname2",
        "mgmtchannel": 1,
        "netchannel": 1,
        "password": "password",
        "username": "admin",
        "userid": 2,
        "comment": "Default Gigabyte",
        "unmanaged_bmc_users": "disable",
        "members": [
          "node001",
          "node002"
        ]        
      }
    },
    "switch": {
      "switch01": {
        "network": "cluster",
        "newswitchname": "mgmsw01",
        "ipaddress": "10.141.253.1",
        "oid": ".1.3.6.1.2.1.17.7.1.2.2.1.2",
        "readcommunity": "public",
        "rwcommunity": "private",
        "comment": "Bootswitch"
      },
      "switch02": {
        "network": "ipmi",
        "newswitchname": "mgmsw02",
        "ipaddress": "10.148.253.1",
        "oid": ".1.3.6.1.2.1.17.7.1.2.2.1.2",
        "readcommunity": "public",
        "rwcommunity": "private",
        "comment": "Bootswitch"
      }
    },
    "otherdev": {
      "apc01": {
        "network": "cluster",
        "newotherdevname": "apc01a",
        "ipaddress": "10.141.250.1",
        "comment": "APC for rack01a"
      },
      "ups01": {
        "network": "ipmi",
        "newotherdevname": "ups-01",
        "ipaddress": "10.148.250.1",
        "comment": "UPS for the head node"
      }
    },
    "osimage": {
      "compute": {
        "grab_exclude": [
          "/dev",
          "/proc",
          "/sys"
        ],
        "grab_filesystems": [
          "/",
          "/boot"
        ],
        "initrdfile": "compute-initramfs-`uname -r`",
        "kernelfile": "compute-kernel-`uname -r`",
        "kernelmodules": "ipmi_devinft, ipmi_si, ipmi_msghandler",
        "kerneloptions": "mitigations=off nosmt noht",
        "kernelversion": "`uname -r`",
        "path": "/trinity/images/compute",
        "imagefile": "compute.tar.bz2",
        "comment": "Default image"
        "members": [
          "node003",
          "node004"
        ]        
      },
      "compute-ib": {
        "grab_exclude": [
          "/dev",
          "/proc",
          "/sys"
        ],
        "grab_filesystems": [
          "/",
          "/boot"
        ],
        "initrdfile": "compute-initramfs-`uname -r`",
        "kernelfile": "compute-kernel-`uname -r`",
        "kernelmodules": "ipmi_devinft, ipmi_si, ipmi_msghandler",
        "kerneloptions": "mitigations=off nosmt noht",
        "kernelversion": "`uname -r`",
        "path": "/trinity/images/compute-ib",
        "imagefile": "compute.tar.bz2",
        "comment": "Default image with updated drivers"
        "members": [
          "node001",
          "node002"
        ]        
      }
    },
    "secrets": {
      "node": {
        "node001": [
          {
            "secretname": "shared secret",
            "content": "<ENC>",
            "path": "/etc/keys.crt"
          },
          {
            "secretname": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          },
          {
            "secretname": "shared secret",
            "content": "<ENC>",
            "path": "/etc/keys.crt"
          }
        ],
        "node002": [
          {
            "name": "software license",
            "content": "<ENC>",
            "path": "/etc/app/license.lic"
          }
        ]
      },
      "group": {
        "compute": [
          {
            "secretname": "Proprietary key",
            "content": "<ENC>",
            "path": "/var/lib/key.pem"
          }
        ],
        "compute-ib": [
          {
            "secretname": "Infiniband",
            "content": "<ENC>",
            "path": "/etc/rdma/license.lic"
          }
        ]
      }
    }
  },
  "version": {
    "luna": "2.0-001",
    "api": 1,
    "commit": "hex(commit)"
  },
  "monitor": {
    "service": {
      "dns": "OK, running",
      "dhcp": "OK, reloaded",
      "luna2": "OK"
    },
    "status": {
      "node001": {
        "status": "Luna installer: No errors",
        "state": "installer.ok"
      },
      "node002": {
        "status": "Luna installer: No errors",
        "state": "installer.ok"
      },
      "beegfs01": {
        "status": "Luna installer: No errors",
        "state": "installer.ok"
      },
      "login01": {
        "status": "Luna installer: Error in partscript",
        "state": "installer.error"
      }
    }
  },
  "control": {
    "power": {
      "on": {
        "hostlist": "node[001,node003-004]"
      },
      "fail": {
        "hostlist": "node[002]"
      }
    }
  }
}

YAML

---
config:
  node:
    node001:
      newhostname: gpu001
      group: compute
      interfaces:
      - interface: BOOTIF
        network: clusternet
        ipaddress: 10.141.0.1
      - interface: BMC
        network: ipmi
        ipaddress: 10.148.0.1
      - interface: ib0
        network: ib
        ipaddress: 10.149.0.1
      macaddr: aa:bb:cc:dd:ee:ff
      switch: switch01
      switchport: 1
      service: False
      setupbmc: True
      status: installer.completed
      comment:
      osimage: compute
      prescript: "#!/bin/bash \n exit 0;"
      partscript: "#!/bin/bash \n exit 0;"
      postscript: "#!/bin/bash \n exit 0;"
      netboot: True
      bootmenu: False
      provision_interface:
      provision_method:
      provision_fallback:
      tpm_uuid:
      tpm_pubkey:
      tpm_sha256:
  group:
    compute:
      newgroupname: compute-gpu
      bmcsetup: True
      domain: cluster
      interfaces:
      - interface: BOOTIF
        network: clusternet
      - interface: BMC
        network: ipmi
      - interface: ib0
        network: ib
      osimage: compute
      partscript: "#!/bin/bash \n exit 0"
      postscript: "#!/bin/bash \n exit 0"
      prescript: "#!/bin/bash \n exit 0"
      provision_interface:
      netboot: True
      bootmenu: False
      comment: "Default group"
      provision_method: torrent
      provision_fallback: http
      members:
      - node001
      - node002
      - node003
      - node004
  cluster:
    controller1:
      status: primary
      ipaddr: 10.141.255.254
      serverport: 7050
      luna_config: /trinity/local/luna/config/luna-daemon.ini
    controller2:
      status: standby
      ipaddr: 10.141.255.253
      serverport: 7050
      luna_config: /trinity/local/luna/config/luna-daemon.ini
    ntp_server: 10.141.255.252 
    debug: False
    technical_contacts: root@localhost
    provision_method: torrent
    provision_fallback: http
  network:
    cluster:
      newnetname: cluster2
      network: 10.141.0.0/16
      nameserver_ip: 10.141.255.254
      ntp_server: 10.141.255.254
      gateway: 10.141.255.254
      comment: "Default cluster network"
      dhcp: True
      dhcp_range_begin: 10.141.0.200
      dhcp_range_end: 10.141.0.253
    ipmi:
      newnetname: ipmi2
      network: 10.148.0.0/16
      nameserver_ip: 10.148.255.254
      ntp_server: 10.148.255.254
      gateway: 10.148.255.254
      comment: "Default OOB network"
      dhcp: False
    ib:
      newnetname: ib2
      network: 10.149.0.0/16
      nameserver_ip: 10.149.255.254
      ntp_server: 10.149.255.254
      gateway: 10.149.255.254
      comment: "Default highspeed interconnect network"
      dhcp: False
  bmcsetup:
    dell:
      newbmcname: newname
      mgmtchannel: 1
      netchannel: 1
      password: calvin
      username: root
      userid: 2
      comment: "Default DELL"
      unmanaged_bmc_users: "skip"
      members:
      - node003
      - node004      
    gigabyte:
      newbmcname: newname2
      mgmtchannel: 1
      netchannel: 1
      password: password
      username: admin
      userid: 2
      comment: "Default Gigabyte"
      unmanaged_bmc_users: "disable"
      members:
      - node001
      - node002      
  switch:
    switch01:
       network: cluster
       newswitchname: mgmsw01
       ipaddress: 10.141.253.1
       oid: ".1.3.6.1.2.1.17.7.1.2.2.1.2"
       readcommunity: public
       rwcommunity: private
       comment: Bootswitch
    switch02:
       network: ipmi
       newswitchname: mgmsw02
       ipaddress: 10.148.253.1
       oid: ".1.3.6.1.2.1.17.7.1.2.2.1.2"
       readcommunity: public
       rwcommunity: private
       comment: Bootswitch    
  otherdev:
    apc01:
       network: cluster
       newotherdevname: apc01a
       ipaddress: 10.141.250.1
       comment: APC for rack01a
    ups01:
       network: ipmi
       newotherdevname: ups-01
       ipaddress: 10.148.250.1
       comment: UPS for the head node
  osimage:
    compute:
      grab_exclude:
        - /dev
        - /proc
        - /sys
      grab_filesystems:
        - /
        - /boot
      initrdfile: "compute-initramfs-`uname -r`"
      kernelfile: "compute-kernel-`uname -r`"
      kernelmodules: "ipmi_devinft, ipmi_si, ipmi_msghandler"
      kerneloptions: "mitigations=off nosmt noht"
      kernelversion: "`uname -r`"
      path: /trinity/images/compute
      imagefile: compute.tar.bz2
      comment: "Default image"
      members:
      - node003
      - node004      
    compute-ib:
      grab_exclude:
        - /dev
        - /proc
        - /sys
      grab_filesystems:
        - /
        - /boot
      initrdfile: "compute-initramfs-`uname -r`"
      kernelfile: "compute-kernel-`uname -r`"
      kernelmodules: "ipmi_devinft, ipmi_si, ipmi_msghandler"
      kerneloptions: "mitigations=off nosmt noht"
      kernelversion: "`uname -r`"
      path: /trinity/images/compute-ib
      imagefile: compute.tar.bz2
      comment: "Default image with updated drivers"
      members:
      - node001
      - node002  
  secrets:
    node:
      node001:
        - secretname: shared secret
          content: <ENC>
          path: /etc/keys.crt
        - secretname: software license
          content: <ENC>
          path: /etc/app/license.lic
        - secretname: shared secret
          content: <ENC>
          path: /etc/keys.crt
      node002:
        - name: software license
          content: <ENC>
          path: /etc/app/license.lic
    group:
      compute:
        - secretname: Proprietary key
          content: <ENC>
          path: /var/lib/key.pem
      compute-ib:
        - secretname: Infiniband
          content: <ENC>
          path: /etc/rdma/license.lic
version:
  luna: 2.0-001
  api: 1.0
  commit: hex(commit)          
monitor:
  service:
    dns: "OK, running"
    dhcp: "OK, reloaded"
    luna2: "OK"
  status:
    node001:
      status: "Luna installer: No errors"
      state: "installer.ok"
    node002:
      status: "Luna installer: No errors"
      state: "installer.ok"
    beegfs01:
      status: "Luna installer: No errors"
      state: "installer.ok"
    login01:
      status: "Luna installer: Error in partscript"
      state: "installer.error"
control:
  power:
    on:
      hostlist: node[001,node003-004]
    fail:
      hostlist: node[002]