Skip to content

Fabric API Service

ETSI HypO uses a dedicated service - titled Fabric API - to integrate with OpenZiti; an open-source secure networking platform that provides both zero-trust security and overlay networking as pure open source software. This service exposes an API that allows ETSI HypO to manage (create, read, update, delete) key OpenZiti entities, such as identities, connections, policies, etc.

The key feature in Fabric API is that it may integrate with multiple OpenZiti instances simultaneously.

API

The Fabric API exposes a set of REST API as shown in the following tables.

Table 1: Fabric API Network Controller Endpoints.
Method Endpoint Description Response Codes Auth Roles Leads to
GET /fabric-api/network/controller Returns all network controllers 200, 401, 403 admin
GET /fabric-api/network/controller/{id} Returns a network controller matching the provided id 200, 401, 403 admin
POST /fabric-api/network/controller Creates a new network controller 201, 401, 403 admin Stores a network object in the database. Sends a message to Registry API in order to store credentials
PATCH /fabric-api/network/controller/{id} Updates a network controller matching the provided id 200, 401, 403 admin Updates the network object in the database.
DELETE /fabric-api/network/controller/{id} Deletes a network controller matching the provided id 204, 401, 403 admin Deletes a network object in the database. Sends a message to Registry API in order to remove credential

A sample POST body request is shown below:

{
  "networkName": "Patras' Controller2",
  "networkOwner": "Patras",
  "networkLocation": "Patras University street address",
  "networkEndpoint": "https://localhost:3333",
  "username": "admin",
  "password": "password"
}

The password is not stored in the Fabric API database. As soon as a network create request is received, a message is published in the Kafka channel fabric-ziti-creds-persist-incoming-channel. Afterwards Registry API reads the message and stores a secret for the triplet (networkControllerId, username, password). NetworkControllerId is a UUID generated by Fabric API at runtime and is unique for each network object.

Table 2: Fabric API Domain Identities Endpoints.
Method Endpoint Description Response Codes Auth Roles Leads to
GET /fabric-api/network/controller/{networkControllerId}/domain/identities Returns all network ids for the provided network controller id 200, 401, 403 admin GET call in the corresponding Ziti Controller
GET /fabric-api/network/controller/{networkControllerId}/domain/identities/{id} Returns an identity based on its id and the managing network controller id 200, 401, 403 admin GET call in the corresponding Ziti Controller
GET /fabric-api/domain/identities Returns all Identities 200, 401, 403 admin GET calls in all corresponding Ziti Controllers
POST /fabric-api/network/controller/{networkControllerId}/domain/identities Creates a new Domain Identity under a specific network controller 201, 401, 403 admin POST call in the corresponding Ziti Controller
PATCH /fabric-api/network/controller/{networkControllerId}/domain/identities Creates a new Domain Identity under a specific network controller 201, 401, 403 admin PATCH call in the corresponding Ziti Controller
DELETE /fabric-api/network/controller/{networkControllerId}/domain/identities/{id} Deletes a Domain Identity matching the provided id and the managing network controller id 204, 401, 403 admin DELETE call in the corresponding Ziti Controller

A sample POST body request is provided below:

{
  "domainIdentity": {
    "name": "test",
    "type": "Device",
    "appData": {},
    "isAdmin": true,
    "roleAttributes": [
      "ACME"
    ],
    "authPolicyId": "default",
    "externalId": "",
    "defaultHostingCost": "0",
    "defaultHostingPrecedence": "default",
    "tags": {},
    "enrollment": {
      "ott": false
    }
  },
  "organizationId": "3b730fdd-fc0b-427a-bb88-63ef6d540d8f",
  "organizationName": "ACME"
}

When Fabric API receives the request, it retrieves the network controller from the path provided id and then a subsequent POST request is performed using the network controller endpoint as the base URL. The body for this request is the domainIdentity value of the request above. If the request is successful some basic data are persisted in the Fabric API database, the most important being the network controller generated domainIdentityId which is used as the unique identifier in Fabric API as well. The organization fields are TMF API related and are used in the end user service flow.

A sample PATCH body request is presented below:

{
  "domainIdentity": {
    "roleAttributes": [
      "ACME","CORP"
    ]
  },
  "organizationId": "3b730fdd-fc0b-427a-bb88-63ef6d540d8f",
  "organizationName": "ACME"
}

The only updates allowed for an identity are on upon its roleAttributes and the related organization.

Table 3: Fabric API Domain Connection Endpoints.
Method Endpoint Description Response Codes Auth Roles Leads to
GET /fabric-api/network/controller/domain/connections Returns all domain connections 200, 401, 403 admin, infrastructure-provider
GET /fabric-api/network/controller/{networkControllerId}/domain/connections Returns all domain connections for a particular network controller id 200, 401, 403 admin, infrastructure-provider
GET /fabric-api/network/controller/{networkControllerId}/domain/connections/{id} Returns a domain connection for a provided id and a network controller id 200, 401, 403 admin, infrastructure-provider
POST /fabric-api/network/controller/{networkControllerId}/domain/connections Creates a new domain connection using a specific network controller id 201, 401, 403 admin, infrastructure-provider Subsequent calls though the managing Controller in order to create Ziti objects tha ensure the domain connection
DELETE /fabric-api/network/controller/{networkControllerId}/domain/connections/{id} Deletes a domain connection for a provided id and a network controller id 204, 401, 403 admin, infrastructure-provider Removes all corresponding objects to Ziti and the Fabric API database objects

A sample POST body request is shown below:

{
  "serviceOrderId": "0ab14a96-4db0-4850-ac63-be653cd558f8",
  "serviceOrderItemId": "f5a465ba-a976-4345-9cf2-496db7069294",
  "serviceId": "ece47dec-16bc-4d45-a624-0729db80d1f4",
  "domainIdentityId": "Acme Corporation",
  "address": "10.20.30.40",
  "port": 80,
  "protocol": "TCP"
}

With the above provided, Fabric API sends additional requests in Ziti in order to create the quintuplet below that materializes a domain connection:

  • a host config for the provided address, protocol and port
  • an intercept config for the provided address, protocol and port
  • a Ziti service
  • a dial policy for the provided domain identity (which corresponds to the provided address and port)
  • a bind policy for the provided domain identity (which corresponds to the provided address and port)

KAFKA Channels

channel name type publisher subscriber action
fabric-ziti-creds-persist-incoming-channel outgoing FABRIC API REGISTRY API Stores Network Credentials
fabric-ziti-creds-delete-incoming-channel outgoing FABRIC API REGISTRY API Deletes Network Credentials
fabric-api-connection incoming SONATA FABRIC API Creates a new domain connection related to a Kubernetes Service
fabric-api-connection-result outgoing FABRIC API SONATA Domain creation result
fabric-api-connection-teardown incoming SONATA FABRIC API Deletes a domain connection related to a Kubernetes Service
fabric-api-connection-teardown-result outgoing FABRIC API SONATA Domain connection deletion result

Sample messages for the channels are show below.

fabric-api-connection channel:

{
  "specversion": "1.0",
  "id": "8963475e-425c-4df1-b6a9-163b0037ac4d",
  "source": "/process/fabricApiConfigurationProcess",
  "type": "fabric-api-connection",
  "time": "2024-02-26T15:07:11.763520617+02:00",
  "kogitoproctype": "BPMN",
  "kogitoprocinstanceid": "7aa45064-f4a7-4a25-a7a2-667afb07c3d1",
  "kogitoprocist": "Active",
  "kogitoprocversion": "1.0",
  "kogitoprocid": "fabricApiConfigurationProcess",
  "data": {
    "serviceOrderId": "2c4fecbc-c436-4f8c-a5db-4a1159ebad2a",
    "serviceId": "56165b84-40e1-4f53-a064-cc9ae6998beb",
    "organizationName": "open-slice-uop",
    "address": "10.0.2.4",
    "ports": [8000, 30180],
    "protocol": "tcp"
  }
}

from the message above, Fabric API will create a domain connection for each of the ports included in the message, with the provided protocol and http address. Through the organization id, Fabric API retrieves the corresponding domain identity and then the managed network controller for this identity. Through this and the data provided in the message, a new domain connection is created.

Upon success or failure of the above operation, a message will be posted in the Kafka channel fabric-api-connection-result in order to inform Sonata:

{
  "specversion": "1.0",
  "id": "21627e26-31eb-43e7-8343-92a696fd96b1",
  "source": "/process/fabricApiServiceConnection",
  "type": "fabric-api-connection-result",
  "kogitoprocrefid": "7aa45064-f4a7-4a25-a7a2-667afb07c3d1",
  "data": {
    "serviceOrderId": "2c4fecbc-c436-4f8c-a5db-4a1159ebad2a",
    "serviceId": "56165b84-40e1-4f53-a064-cc9ae6998beb",
    "organizationName": "open-slice-uop",
    "fabricApiClientStatus": "SUCCESS",
    "fabricApiClientMessage": "everything went as expected"
  }
}

A similar message is published in the topic fabric-api-connection-teardown when the Kubernetes service is terminated:

{
  "specversion": "1.0",
  "id": "383815b8-e92b-447b-96dc-99bc66d7d728",
  "source": "/process/fabricApiServiceConnectionTeardown",
  "type": "fabric-api-connection-teardown",
  "time": "2024-02-26T15:07:11.763520617+02:00",
  "kogitoproctype": "BPMN",
  "kogitoprocinstanceid": "d12d2753-ac8f-4029-9546-5d7cca6db145",
  "kogitoprocist": "Active",
  "kogitoprocversion": "1.0",
  "kogitoprocid": "fabricApiConfigurationProcess",
  "data": {
    "serviceOrderId": "2c4fecbc-c436-4f8c-a5db-4a1159ebad2a",
    "serviceId": "56165b84-40e1-4f53-a064-cc9ae6998beb",
    "organizationName": "open-slice-uop",
    "address": "10.0.2.4",
    "ports": [8000, 30180],
    "protocol": "tcp"
  }
}

The message above will delete or Ziti domain connection objects related to the serviceId, address, ports and protocol provided. The network that will be used is the one that manages the organization with the provided organizationName. Upon finishing the operation, Fabric API posts a callback message towards Sonata in the topic fabric-api-connection-teardown-result:

{
  "specversion": "1.0",
  "id": "966affd3-85f2-4276-8d76-103b314dc32e",
  "source": "/process/fabricApiServiceConnection",
  "type": "fabric-api-connection-result",
  "kogitoprocrefid": "16bd05ff-261b-46c7-8a5e-173ac34eeec3",
  "data": {
    "serviceOrderId": "2c4fecbc-c436-4f8c-a5db-4a1159ebad2a",
    "serviceId": "56165b84-40e1-4f53-a064-cc9ae6998beb",
    "organizationName": "open-slice-uop",
    "fabricApiClientStatus": "SUCCESS",
    "fabricApiClientMessage": "everything went as expected"
  }
}