<?xml version="1.0" encoding="UTF-8"?>
  <?xml-stylesheet type="text/xsl" href="rfc2629.xslt" ?>
  <!-- generated by https://github.com/cabo/kramdown-rfc version 1.7.1 (Ruby 2.6.10) -->


<!DOCTYPE rfc  [
  <!ENTITY nbsp    "&#160;">
  <!ENTITY zwsp   "&#8203;">
  <!ENTITY nbhy   "&#8209;">
  <!ENTITY wj     "&#8288;">

<!ENTITY RFC7644 SYSTEM "https://bib.ietf.org/public/rfc/bibxml/reference.RFC.7644.xml">
<!ENTITY I-D.ietf-scim-device-model SYSTEM "https://bib.ietf.org/public/rfc/bibxml3/reference.I-D.ietf-scim-device-model.xml">
<!ENTITY RFC2119 SYSTEM "https://bib.ietf.org/public/rfc/bibxml/reference.RFC.2119.xml">
<!ENTITY RFC8174 SYSTEM "https://bib.ietf.org/public/rfc/bibxml/reference.RFC.8174.xml">
<!ENTITY I-D.ietf-asdf-sdf SYSTEM "https://bib.ietf.org/public/rfc/bibxml3/reference.I-D.ietf-asdf-sdf.xml">
<!ENTITY RFC9114 SYSTEM "https://bib.ietf.org/public/rfc/bibxml/reference.RFC.9114.xml">
<!ENTITY RFC8949 SYSTEM "https://bib.ietf.org/public/rfc/bibxml/reference.RFC.8949.xml">
<!ENTITY RFC8610 SYSTEM "https://bib.ietf.org/public/rfc/bibxml/reference.RFC.8610.xml">
<!ENTITY RFC5226 SYSTEM "https://bib.ietf.org/public/rfc/bibxml/reference.RFC.5226.xml">
]>


<rfc ipr="trust200902" docName="draft-ietf-asdf-nipc-02" category="std" consensus="true" submissionType="IETF" tocInclude="true" sortRefs="true" symRefs="true">
  <front>
    <title abbrev="NIPC">An Application Layer Interface for Non-IP device control (NIPC)</title>

    <author initials="B." surname="Brinckman" fullname="Bart Brinckman">
      <organization>Cisco Systems</organization>
      <address>
        <postal>
          <city>Brussels</city>
          <country>Belgium</country>
        </postal>
        <email>bbrinckm@cisco.com</email>
      </address>
    </author>
    <author initials="R." surname="Mohan" fullname="Rohit Mohan">
      <organization>Cisco Systems</organization>
      <address>
        <postal>
          <street>170 West Tasman Drive</street>
          <city>San Jose</city>
          <code>95134</code>
          <country>USA</country>
        </postal>
        <email>rohitmo@cisco.com</email>
      </address>
    </author>
    <author initials="B." surname="Sanford" fullname="Braeden Sanford">
      <organization>Philips</organization>
      <address>
        <postal>
          <city>Cambridge</city>
          <country>USA</country>
        </postal>
        <email>braeden.sanford@philips.com</email>
      </address>
    </author>

    <date year="2024" month="October" day="21"/>

    
    
    <keyword>Internet-Draft</keyword>

    <abstract>


<?line 54?>

<t>This memo specifies RESTful application layer interface for gateways 
providing operations against non-IP devices. The described interface is
extensible. This memo initially describes Bluetooth Low Energy and 
Zigbee as they are the most commonly deployed.</t>



    </abstract>



  </front>

  <middle>


<?line 61?>

<section anchor="introduction"><name>Introduction</name>

<section anchor="scope"><name>Scope</name>

<t>Low-power sensors, actuators and other connected devices introduced in
environments and use cases such as building management, healthcare, workplaces,
manufacturing, logistics and hospitality are often battery-powered. Often they
do not support wireless of wired interfaces that support the IP protocol.
Most of these environments however mainly support IP-based networking
infrastructure. Therefore, applications on the IP network that aim to
communicate or receive telemetry from these non-IP low-power devices must do
so through a gateway function on the IP network. This gateway functions then 
translates the communication to the non-IP protocol that the low-power device 
supports. Promiment examples of such protocols are <xref target="BLE53"/> and <xref target="Zigbee22"/>.</t>

<figure title="Gateway for non-IP Devices" anchor="gw"><artwork><![CDATA[
                                                               
    +-------------+              +---------+              +--------+
    | Application |<------------>| Gateway |<------------>| Non-IP |                     
    |    app      |   IP-based   |         |    Non-IP    | Device |
    +-------------+   Operation  +---------+   Operation  +--------+                 

]]></artwork></figure>

<t>There have been efforts to define Gateway functions for devices that support
a particular protocol, such as a BLE GATT REST API for BLE Gateways
<eref target="https://www.bluetooth.com/bluetooth-resources/gatt-rest-api/"/>, however 
they have been limited to a single protocol or a particular use case. In
abscence of an open standard describing how applications on an IP network
communicate with non-IP devices, bespoke and vendors specifia implementations
have proliferated. This results in parallel infrastructure of both gateways 
and non-IP networks being deployed on a case by case basis, each connecting
separately into the IP network, with a distinct set of APIs. At the same time,
wireless access points supporting IP-based wireless connectivity are deployed
ubiquitiouslyr. Many of these wireless access points are equipped with multiple
wireless radios, of different types. These radios can transmit and receive
different frame types, such as <xref target="BLE53"/> and <xref target="Zigbee22"/>. This specification
aims to define a Gateway API for these Non-IP protocols that can be leveraged
by this wireless infrastructure in order to connect Non-IP devices into IP
networks.</t>

<t>A standardized Non-IP Gateway interface has following benefits:
 - Avoid the need for parallel Non-IP infrastructure.
 - Avoid the need for Applications to perform bespoke integrations for
   different environments.
 - Faster and more cost-effective adoption of Non-IP devices in IP network
   environments.</t>

</section>
<section anchor="non-ip-gateway-functions"><name>Non-IP Gateway functions</name>

<t>A non-IP gateway MUST provide at least following functions:
 - Authentication and authorization of application clients that
   will leverage the gateway API to communicate with  Non-IP devices.
 - The ability to onboard Non-IP devices on the Non-IP Gateway. Onboarding 
   ensures that the Non-IP Gateway can identify a device and has sufficient
   context about the device to service gateway API requests. It also ensures
   segmentation of devices that were onboarded by particular applications.
 - A persistent inventory of onboarded devices  mapping to the application
   that onboarded them and the access point/radio that is serving them.
 - An API that allows for bi-directional communication to non-IP devices.
 - One or more channels to process requests, responses, and asymmetric
   communications with the non-IP radio resources (Access Points)
   in its inventory.
 - The ability to stream telemetry received from non-IP devices in real-time
   to applications on the IP network.</t>

<t>The onboarding function is out of scope of this document, but can be provided
by a provisioning interface such as <xref target="RFC7644"/> leveraging 
<xref target="I-D.ietf-scim-device-model"/>. All other defined functions are
supported by Non IP-Control (NIPC).</t>

<t>The Application gateway is a network functions, so its goal is to proxy payloads 
between Non-IP and IP networks. It is not intended to be a middleware functioni
that interprets, decodes or modifies these payloads.</t>

<figure title="Basic Architecture" anchor="arch"><artwork><![CDATA[
                            +-----------------------------------+
                            |                                   |
    +-----------+   Request |  +---------+                      |
    | onboarding|------------->|  SCIM   |                      |
    |    app    |<-------------| Server  |                      |
    +-----------+  Ctrl Endpt  +---------+                      |
                            |                                   |
    +-----------+           |  +------------+  +-------+  +--+  |
    |  Control  |>...REST...|.>|            |..|  AP   |..|D |  |
    |     &     |           |  |   Gateway  |  +-------+  +--+  |
    | Telemetry |<...MQTT...|.<|            |                   |
    |    Apps   |           |  +------------+                   |
    +-----------+           |                                   |
                            |       Network Deployment          |
                            +-----------------------------------+

]]></artwork></figure>

<t><xref target="arch"/> shows us applications, the application layer gateway (ALG),
an access point (AP), and a device (D). The applications, application layer
gateway and access point are deployed on an IP-Network. The AP also has a
Non-IP interface, which it uses to communicate with the device.
The Application is deployed in a different administrative domain than the
network elements (ALG &amp; AP).
The role of the ALG is to provide a gateway function to applications wishing
to communicate with non-IP devices in the network domain served by the ALG.
Applications implementing Non-IP Control can leverage RESTful interfaces
to communicate with Non-IP devices in the network domain and subscribe to
events levering MQTT.</t>

</section>
<section anchor="interaction-flow"><name>Interaction flow</name>

<t>In order to enable a network wishing to offer NIPC ALG functions, the network
administrator authorizes application(s) to perform operations on the Gateway.
This happens out of band and may be accomplished by means of exchanging tokens
or public keys.
Authorization can be role-based. The 3 primary roles are:<br />
1. Onboarding: Authorize an onboarding application against a SCIM server
   co-located with the gateway.<br />
2. Control: Authorize applications that may control devices.
3. Data: Authorize applications that may receive telemetry.<br />
It is possible to further refine roles down to an API basis.</t>

<t>Applications can perform the API requests they were authorized for.
In order for application to perform a NIPC operation on a device, the device
must be first onboarded, for example by means of SCIM.</t>

<t>Previous steps are prerequisites and not within the scope of this specification, 
but are provided for context.i Subsequent operations are defined by NIPC.</t>

<t><list style="numbers">
  <t>An application authorized for Control can perform NIPC calls to the
gateway in order to establish bi-directional communication to one or more
devices. Optionally, also set up a publish/subcribe topic to receive
streaming data from a device (telemetry interface).</t>
  <t>An application authorized can receive streaming data on a pub/sub 
topic configured by the control interface (telemetry interface).</t>
</list></t>

</section>
<section anchor="terminology"><name>Terminology</name>

<t>The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT",
"SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and
"OPTIONAL" in this document are to be interpreted as described in BCP
14 <xref target="RFC2119"/> <xref target="RFC8174"/> when, and only when, they appear in all
capitals, as shown here.</t>

</section>
</section>
<section anchor="architecture"><name>Architecture</name>

<section anchor="overview"><name>Overview</name>

<t>Non-IP protocols, such as BLE or Zigbee, typically define a number of basic
operations that are similar across protocols. Examples of this are read and 
write data. NIPC leverages a unified API to support those operations.</t>

<t>NIPC defines actions, which are implemented as REST over HTTP request-response
APIs. NIPC Also defines events, which are implemented as MQTT topics.</t>

<t>In case NIPC is not leveraged in combination with a data model such as ASDF
<xref target="I-D.ietf-asdf-sdf"/>, which can define the properties of a devices,
NIPC also support registrationsr. REgistrations perform mapping of 
properties to protocol-specific attributes.</t>

<t>All operations pertain to a devices or a group of devices, which are addressed
by UUIDs. These UUID's were generated at time of onboarding and returned to 
the application, for example in a SCIM response.</t>

</section>
<section anchor="nipc-operations"><name>NIPC Operations</name>

<t>NIPC adheres to nomenclature defined by Semantic Definition Format (SDF) for
Data and Interactions of Things <xref target="I-D.ietf-asdf-sdf"/>. Therefore NIPC
defines actions and events on properties.</t>

<section anchor="actions"><name>Actions</name>
<t>NIPC supports 3 types of action:
 - connection: Allows an application to establish to manage connections with
   a device (if so required by the technology).
 - property: Allows applications to read or write device properties. In case
   the property supports streaming data, a subscription property can be
   managed.
 - broadcast: This allows the application to send a broadcast message to a
   device or group of devices.</t>

</section>
<section anchor="registrations"><name>Registrations</name>

<t>In absence of a model such as SDF that defines device properties, NIPC allows
an application to register them. NIPC defines 2 types of registrations:
 - property: Manage registrations of properties and their protocol mappings.
   For example, a property called temperature can be mapped to a BLE Service
   Characteristic.
 - event: Manage registrations of events and their MQTT properties such as 
   MQTT topic definition.</t>

</section>
<section anchor="extensions"><name>Extensions</name>

<t>The final set of operations are not fundamental NIPC operations, but are
extensions. Extensions are compound API's. They leverage basic NIPC operations
but combine multiple operations in to one API call for efficiency.
An example of this is the the bulk operation, allowing to send multiple
operations is one operation. extension allows for extensions, either generic
extensions that anre IANA registered, or vendor specific extensions</t>

</section>
<section anchor="events"><name>Events</name>

<t>Events are published over MQTT. Events can be normal sreaming data, but also
broadcasts or connection events.</t>

</section>
</section>
<section anchor="protocols"><name>Protocols</name>

<t>NIPC actions, registrations and extensions are request/response APIs. They makes
use of a JSON schema over RESTful HTTP<xref target="RFC9114"/>.</t>

<t>NIPC events are encoded in CBOR (<xref target="RFC8949"/>) and delivered over MQTT.</t>

</section>
<section anchor="schema"><name>Schema</name>

<section anchor="device-schema"><name>Device schema</name>

<t>Most operations (except registations) are executed against a device or a group.
NIPC operations refer to either of these as "Object" with an ID as an
identifier. The common schema for Object is defined as follows:</t>

<texttable title="Definition of an Object" anchor="objectdef">
      <ttcol align='left'>Attribute</ttcol>
      <ttcol align='left'>Req</ttcol>
      <ttcol align='left'>Type</ttcol>
      <ttcol align='left'>Example</ttcol>
      <c>id</c>
      <c>T</c>
      <c>uuid</c>
      <c>12345678-1234-5678-1234-56789abcdef4</c>
      <c>type</c>
      <c>T</c>
      <c>enum</c>
      <c>device, group</c>
      <c>technology</c>
      <c>F</c>
      <c>enum</c>
      <c>ble, zigbee</c>
</texttable>

<t>where-
 - id is the unique uuid of the device. This is generated when registering
   the device, for example against a SCIM server. As such this ID is known
   both to the application as well as the NIPC Server. 
 - type is either "group" or "device".
 - technology is the radio technology supported by the device. The mappings
   defined in this spec are "ble" or "zigbee". Mappings are extendable to 
   new technologies.</t>

<t>Example device object:</t>

<figure title="Example device object" anchor="exdevobj"><artwork><![CDATA[
{
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "technology": "ble",
}
]]></artwork></figure>

</section>
<section anchor="propertymap"><name>Property mapping</name>

<t>An object can support one or more communications protocols. Even though Non-IP
communications protocols all perform operations on properties, implementations
differ between protocols. For example BLE will address a property as a service
characteristic, while a property in Zigbee is addressed as a property in a 
cluster of an endpoint.</t>

<t>In order for NIPC to support protocol-agnostic APIs, a property mapping is
required between a NIPC property and a protocol-specific property. A property
mapping can be done by means of a property registration API.</t>

<t>Property mapping allows for integration of new protocols in NIPC, new mappings 
can be created without the need to update the base schema.</t>

<figure title="Property Mapping" anchor="propmap"><artwork><![CDATA[
     - property
        |
        |> BLE
        |     - BLE property
        |
        |> Zigbee
              - Zigbee property

]]></artwork></figure>

<t>As shown in <xref target="propmap"/>, protocol-specific properties must be described in a
protocol object, for example a "ble" or a "zigbee" object.</t>

<texttable title="Protocol objects" anchor="proobj">
      <ttcol align='left'>Attribute</ttcol>
      <ttcol align='left'>Req</ttcol>
      <ttcol align='left'>Type</ttcol>
      <ttcol align='left'>Example</ttcol>
      <c>ble</c>
      <c>T</c>
      <c>object</c>
      <c>an object with BLE-specific attributes</c>
      <c>zigbee</c>
      <c>T</c>
      <c>object</c>
      <c>an object with Zigbee-specific attributes</c>
</texttable>

<t>where-</t>

<t><list style="symbols">
  <t>"ble" is an object containing properties that are specific to the BLE
protocol.</t>
  <t>"zigbee" is an object containing properties that are specific to the
Zigbee protocol.</t>
  <t>Other protocol mapping objects can be added by creating a new protocol
object</t>
</list></t>

<t>Example property mapping:</t>

<figure title="Example property mapping" anchor="expropmap"><artwork><![CDATA[
{
  "propertyID": "temperature",
  "ble": {
    "serviceID": "12345678-1234-5678-1234-56789abcdef4",
    "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
    "long": false
  }
}
]]></artwork></figure>

<t>Protocol mapping allows applications to perform a one-time registration to
a propertyID for a property, and leverage the propertyID in all API calls 
that perform an operation on this property. It might be useful for applications
to directly use protocol objects in action API's as well, therefore there are 
a limited set of API's avaialbe that have protocol objects directly embedded 
in the API, in ordur to perform operations on properties without having to 
first register them.</t>

</section>
<section anchor="response"><name>Response</name>

<t>As most operations have a common base schema, based on a device ID and a
property, so do responses. Every NIPC API returns a status in the response, as
well as a requestID, which allows for tracking and logging of requests and 
responses. If the operation was performed on a device or group, the ID is also
returned. If the operation is to read or write a property, the resulting value
is also returned.</t>

<t>Success response:</t>

<texttable title="Success response" anchor="success">
      <ttcol align='left'>Attribute</ttcol>
      <ttcol align='left'>Req</ttcol>
      <ttcol align='left'>Type</ttcol>
      <ttcol align='left'>Example</ttcol>
      <c>status</c>
      <c>T</c>
      <c>enum</c>
      <c>SUCCESS</c>
      <c>id</c>
      <c>F</c>
      <c>uuid</c>
      <c>12345678-1234-5678-1234-56789abcdef4</c>
      <c>requestID</c>
      <c>F</c>
      <c>uuid</c>
      <c>abcd0987-1234-5678-1234-56789abcdef4</c>
</texttable>

<t>Example success response:</t>

<figure title="Example success response" anchor="exsuccess"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "id": "12345678-1234-5678-1234-56789abcdef4",
}
]]></artwork></figure>

<t>Failure responses additionally include an error code and optionally a reason,
which contains a textual explanation of the error.</t>

<t>Failure response:</t>

<texttable title="Failure response" anchor="failure">
      <ttcol align='left'>Attribute</ttcol>
      <ttcol align='left'>Req</ttcol>
      <ttcol align='left'>Type</ttcol>
      <ttcol align='left'>Example</ttcol>
      <c>status</c>
      <c>T</c>
      <c>enum</c>
      <c>SUCCESS</c>
      <c>id</c>
      <c>F</c>
      <c>uuid</c>
      <c>12345678-1234-5678-1234-56789abcdef4</c>
      <c>requestID</c>
      <c>F</c>
      <c>uuid</c>
      <c>abcd0987-1234-5678-1234-56789abcdef4</c>
      <c>errorCode</c>
      <c>T</c>
      <c>int</c>
      <c>12</c>
      <c>reason</c>
      <c>T</c>
      <c>string</c>
      <c>"Not Found"</c>
</texttable>

<t>where-</t>

<t><list style="symbols">
  <t>status is the status of the request, either "SUCCESS" or "FAILURE". 
In case of failure an error code and reason are added.</t>
  <t>id is the id the operation was executed against, found in the request</t>
  <t>requestID is a correlation ID that can be used for end-to-end 
tracing.</t>
  <t>errorCode is a numerical value representing the error.</t>
  <t>reason is a human readable explanation of why the error occurred.</t>
</list></t>

<t>Example failure response:</t>

<figure title="Example failure response" anchor="exfail"><artwork><![CDATA[
{
  "status": "FAILURE",
  "reason": "Not Found",
  "errorCode": 12,
  "requestID": "12345678-5678-1234-5578-abcdef1234"
}
]]></artwork></figure>

</section>
</section>
</section>
<section anchor="nipc-actions"><name>NIPC Actions</name>

<t>The primary goal of NIPC actions is to exchange data with a Non-IP device, by
means of reading, writing or streaming NIPC properties to applications. An
explicit connection may be required, which is also an action. An application
may also want to transmit a broadcast.</t>

<section anchor="connections"><name>Connections</name>

<t>A connection is an operation that establishes or tears down an association or
connection with a device. Optionally during connection setup properties 
supported by a device can be discovered.</t>

<t>/action/connection</t>

<t>The connection API allows an application to request to connect to 
a device.</t>

<t>Operations:</t>

<t><list style="symbols">
  <t>Connect to a device: POST</t>
  <t>Return active connections: GET</t>
  <t>Disconnect a device: DELETE</t>
</list></t>

<section anchor="connection-api"><name>Connection API</name>

<section anchor="connect"><name>Connect to a device</name>

<t>Method: POST /action/connection</t>

<t>Description: Connect to a device</t>

<t>Parameters: None</t>

<t>Request Body: 
 - an Object, as defined in <xref target="objectdef"/> 
 - optionally a set of properties to be discovered. These are supplied
   in protocol objects, as defined in <xref target="proobj"/>.
   In the case of BLE, if no protocol object is included, service discovery is 
   performed to discover all supported properties when connecting to
   a device. Optionally, service discovery may be limited to properties 
   defined in the "ble" protocol extension. The services to be 
   discovered can be added in an array. Property discover can be buffered
   across connections, so the API also supports caching parameters. 
 - Connection retry parameters</t>

<t>Example body of a connection without specific discovery of properties:</t>

<figure title="Example Connection" anchor="exconn"><artwork><![CDATA[
{
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "technology": "ble",
  "retries": 3,
  "retryMultipleAPs": true
}
]]></artwork></figure>

<t>where-</t>

<t><list style="symbols">
  <t>"id", "type" and "technology" are part of the object definition (device
or group), as defined in <xref target="objectdef"/>.</t>
  <t>"retries" defines the number of retries in case the operations does not 
succeed</t>
  <t>"retryMultipleAPs" can be used in case there is an infrastructure with 
multiple access points or radios that can reach the device. If set to "true"
a different access point may be used for retries.</t>
</list></t>

<t>In case the application would like to discover specific properties of a device,
a protocol object can be added that defines what properties should be
discovered.</t>

<t>Example body of a BLE connection with specific discovery of properties:</t>

<figure title="Example Connection with explicit discovery of connections" anchor="exconnprp"><artwork><![CDATA[
{
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "technology": "ble",
  "ble": {
    "services": [
      {
        "serviceID": "12345678-1234-5678-1234-56789abcdef4"
      }
    ],
    "cached": false,
    "cacheIdlePurge": 3600,
    "autoUpdate": true,
    "bonding": "default"
  },
  "retries": 3,
  "retryMultipleAPs": true
}
]]></artwork></figure>

<t>where in the BLE protocol object:</t>

<t><list style="symbols">
  <t>"services" is an array of services defined by their serviceIDs.</t>
  <t>"cached" refers to whether the services need to be cached for 
subsequent connects, in order not to perform service discovery on
each request.</t>
  <t>"cacheIdlepurge" defines how long the cache should be maintained 
before purging</t>
  <t>some devices support notifications on changes in services, 
"autoUpdate" allows the network to update services based on 
notification (on by default)</t>
  <t>"bonding" allows you to override the bonding method configured when 
onboarding the device</t>
</list></t>

<t>Response: 
Success responses include standard success response properties
as defined in <xref target="success"/> as well as a protocol object with an array of 
discovered properties, as defined in the specific protocol.
For example, for BLE, this is an array of supported services, which in turn
contains an array of charateristics, which in turn contains an array of
descriptors, as shown in <xref target="BLEservices"/>.</t>

<figure title="BLE Services" anchor="BLEservices"><artwork><![CDATA[
    services
     - serviceID
        |
        |> characteristics
            - charactericID
            - flags
               |
               |> Descriptors
                   - descriptorID
]]></artwork></figure>

<t>Example of a BLE connection response with BLE discovered properties:</t>

<figure title="Example Connection response" anchor="exconnresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "ble": [
    {
      "serviceID": "12345678-1234-5678-1234-56789abcdef4",
      "characteristics": [
        {
          "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
          "flags": [
            "read",
            "write"
          ],
          "descriptors": [
            {
              "descriptorID": "12345678-1234-5678-1234-56789abcdef4"
            }
          ]
        }
      ]
    }
  ]
}
]]></artwork></figure>

<t>where in the BLE protocol object:</t>

<t><list style="symbols">
  <t>"id", "requestID" and "technology" are part of hte standard <xref target="success"/> definition</t>
  <t>"ble" protocol object conatins an Array of BLE services as shown in
<xref target="BLEservices"/></t>
</list></t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="return-active-connections"><name>Return active connections</name>

<t>Method: GET /action/connection</t>

<t>Description: Returns one or more active connections, based on ids 
provided in parameters (none = return all connections).</t>

<t>Parameters, in query: 
One of following options:
 - None: return all active connections for this application 
 - single id: return connection status for this id
 - comma separated ids: return connection status for multiple ids</t>

<t>Response: 
A standard success (<xref target="exsuccess"/>)i or failure (<xref target="exfail"/>) response, including
an array of device objects and their connection status. Success if hte device
is connected, failure if the device is not connected.</t>

<t>Example get connection response:</t>

<figure title="Example Connection response" anchor="exgetresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "connections": [
    {
      "status": "SUCCESS",
      "requestID": "12345678-5678-1234-5578-abcdef1234",
      "id": "12345678-1234-5678-1234-56789abcdef4"
    },
    {
      "status": "FAILURE",
      "reason": "Not Found",
      "errorCode": 12,
      "requestID": "12345678-5678-1234-5578-abcdef1234"
    }
  ]
}
]]></artwork></figure>

<t>In this example, status of 2 connections was requested. The request was
successfully executed, 1 of the 2 connections was found active, the other
one not.</t>

</section>
<section anchor="disconnect-a-device"><name>Disconnect a device</name>

<t>Method: DELETE /action/connection</t>

<t>Description: Disconnect one or more devices, based on ids provided in
parameters</t>

<t>Parameters, in query: 
One of following options:
 - None: Disconnect all devices for connections this application made
 - single id: disconnect device with id
 - comma separated ids: disconnect multiple devices with ids</t>

<t>Response: 
The response for the DELETE function is the same as the response for the GET
function. See <xref target="exsuccess"/> for success response, and <xref target="exconnresp"/> for failed
responses.</t>

</section>
</section>
</section>
<section anchor="properties"><name>Properties</name>

<t>Property APIs allow applictions to read and write property values from/to
devices.</t>

<t>/action/property</t>

<t>Operations:</t>

<t><list style="symbols">
  <t>Write value: POST</t>
  <t>Update value: PUT</t>
  <t>Read value: GET</t>
  <t>Delete value: DELETE</t>
</list></t>

<section anchor="property-api"><name>Property API</name>

<section anchor="write"><name>Writing a value</name>

<t>Method: POST /action/property/</t>

<t>Description: Writes a value to a property</t>

<t>Parameters: None</t>

<t>Request Body: 
 - an Object, as defined in <xref target="objectdef"/>
 - A propertyID to write to
 - A value to be written
 - optional parameters</t>

<t>Example body writing a property:</t>

<figure title="Example writing a property" anchor="exwrite"><artwork><![CDATA[
{
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "technology": "ble",
  "propertyID": "temperature",
  "value": "1",
  "forcedResponse": true
}
]]></artwork></figure>

<t>where-
 - "id", "type" and "technology" are part of the object definition (device
   or group), as defined in <xref target="objectdef"/>
 - "propertyID" is the ID of a previously registered property mapping
 - "value" is the value to be written
 - "forcedresponse" requests a specific response behavior of the device
   that is not the default</t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as the propertyID and the value written.</t>

<t>Example of a write property response:</t>

<figure title="Example write property response" anchor="exwrresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "propertyID": "temperature",
  "value": "1"
}
]]></artwork></figure>

<t>where-</t>

<t><list style="symbols">
  <t>"id", "requestID" and "technology" are part of the standard <xref target="success"/> definition</t>
  <t>"propertyID" is the ID of a previously registered property mapping</t>
  <t>"value" is the value to be written</t>
  <t>"propertyID" is the proper</t>
</list></t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="update"><name>Updating a value</name>

<t>Method: PUT /action/property</t>

<t>Description: Updates a value of a property</t>

<t>Parameters: None</t>

<t>Request Body: 
 - an Object, as defined in <xref target="objectdef"/>
 - A propertyID to write to
 - A value to be written
 - optional parameters</t>

<t>Example body updating a property:</t>

<figure title="Example updating a property" anchor="exupd"><artwork><![CDATA[
{
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "technology": "ble",
  "propertyID": "temperature",
  "value": "1",
  "forcedResponse": true
}
]]></artwork></figure>

<t>where-
 - "id", "type" and "technology" are part of the object definition (device
   or group), as defined in <xref target="objectdef"/>
 - "propertyID" is the ID of a previously registered property mapping
 - "value" is the value to be updated
 - "forcedresponse" requests a specific response behavior of the device
   that is not the default</t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as the propertyID and the value updated.</t>

<t>Example of a write property response:</t>

<figure title="Example update property response" anchor="exupresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "propertyID": "temperature",
  "value": "1"
}
]]></artwork></figure>

<t>where-</t>

<t><list style="symbols">
  <t>"id", "requestID" and "technology" are part of the standard <xref target="success"/> definition</t>
</list></t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="read-a-property"><name>Read a property</name>

<t>Method: GET /action/property/{property}</t>

<t>Description: Read a property from a device</t>

<t>Parameters, in path: 
A propertyID {property} that needs to be read.</t>

<t>Parameters, in query: 
An id of a device on which the property has to be read.</t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as the propertyID and the value read.</t>

<t>Example of a read property response:</t>

<figure title="Example read property response" anchor="exreresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",                   
  "id": "12345678-1234-5678-1234-56789abcdef4",                        
  "propertyID": "temperature",
  "value": "1"
}
]]></artwork></figure>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="delete-a-property-value"><name>Delete a property value</name>

<t>Method: DELETE /action/property/{property}</t>

<t>Description: Delete a property value from a device</t>

<t>Parameters, in path:
A propertyID {property} that needs to be deleted..</t>

<t>Parameters, in query:
An id of a device on which the property has to be deleted.</t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as the propertyID and the value deleted.</t>

<t>Example of a delete property response:</t>

<figure title="Example delete property response" anchor="exdelresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "propertyID": "temperature",
  "value": "1"
}
]]></artwork></figure>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
</section>
</section>
<section anchor="subscriptions"><name>Subscriptions</name>

<t>/action/property/subscription</t>

<t>Subscriptions are properties that deliver a data stream instead of a single
value. The property subscription API allows an application to manage these 
data streams.</t>

<t>Operations:</t>

<t><list style="symbols">
  <t>Start a subscription data stream: POST</t>
  <t>Get status of a subscription data stream: GET</t>
  <t>Stop a subscription data stream: DELETE</t>
</list></t>

<section anchor="property-subscription-api"><name>Property subscription API</name>

<section anchor="starting-a-subscription-data-stream"><name>Starting a subscription data stream</name>

<t>Method: POST /action/property/subscription</t>

<t>Description: Start a subcription data stream pertaining to a specific 
property</t>

<t>Parameters: None</t>

<t>Request Body: 
 - an Object, as defined in <xref target="objectdef"/>
 - A propertyID for which to start the subscription 
 - optional parameters</t>

<t>Example body for starting a subscription of a property:</t>

<figure title="Example starting a subscription for a property" anchor="exstartsub"><artwork><![CDATA[
{
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "technology": "ble",
  "propertyID": "temperature",
  "forcedAck": true
}
]]></artwork></figure>

<t>where-
 - "id", "type" and "technology" are part of the object definition (device
   or group), as defined in <xref target="objectdef"/>
 - "propertyID" is the ID of a previously registered property mapping
 - "forcedAck" requests a specific response behavior of the device
   that is not the default</t>

<t>Response:
Success responses is a standard success response when the
subscription is started, as defined in <xref target="success"/>.</t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="get-status-of-a-subscription-data-stream"><name>Get status of a subscription data stream</name>

<t>Method: GET /action/property/subscription/{property}</t>

<t>Description: Gets the status of a subscription data stream, success if
active, failure if not active</t>

<t>Parameters, in path:
A propertyID {property} for the subscription.</t>

<t>Parameters, in query:
An id of a device on which the subscription has to be started.</t>

<t>Response:
Success responses is a standard success response when the
subscription is started, as defined in <xref target="success"/>.</t>

<t>A failure to find the subscription will generate a standard failed response. 
Please refer to <xref target="failure"/> definition of failed response.</t>

</section>
<section anchor="stop-a-subscription-data-stream"><name>stop a subscription data stream</name>

<t>Method: DELETE /action/property/subscription/{property}</t>

<t>Description: stops a subscription data stream</t>

<t>Parameters, in path:
A propertyID {property} for the subscription.</t>

<t>Parameters, in query:
An id of a device on which the subscription has to be started.</t>

<t>Response:
Success response is a standard success response when the
subscription is deleted, as defined in <xref target="success"/>.</t>

<t>A failure to delete the subscription will generate a standard failed response.
Please refer to <xref target="failure"/> definition of failed response.</t>

</section>
</section>
</section>
</section>
<section anchor="nipc-registrations"><name>NIPC Registrations</name>

<t>NIPC allows an application to register properties to use in action API's. NIPC
supports 2 types of registrations: Registrations for properties and 
registrations for events.</t>

<section anchor="event-registration"><name>Event registration</name>

<t>/registration/event</t>

<t>The event registration API allows an application to register an event for a
data application to a specified property. This event is mapped to an MQTT
pub/sub topic. By activating a subscription on one or more device(s) for that
property, streaming data will get published to the associated pub/sub topic
on MQTT.</t>

<t>Operations:</t>

<t><list style="symbols">
  <t>Register an event: POST</t>
  <t>Update an event: PUT</t>
  <t>Get configuration of one or more events: GET</t>
  <t>Delete an event: DELETE</t>
</list></t>

<section anchor="event-registration-api"><name>Event registration API</name>

<section anchor="registering-an-event"><name>Registering an event</name>

<t>Method: POST /registration/event</t>

<t>Description: Register an event to a property</t>

<t>Parameters: None</t>

<t>Request Body:
 - An event name that matches to an MQTT pub/sub topic
 - The data format the event should be delivered in
 - The device or group id the event is valid for
 - Whether the event needs to be cached for replay
 - the data applications that can consume the events</t>

<t>Example body registering an event:</t>

<figure title="Example registering an event" anchor="exregeve"><artwork><![CDATA[
{
  "event": "enterprise/hospital/pulse_oximeter",
  "eventFormat": "default",
  "replay": false,
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "dataApps": [
    {
      "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
      "mqtt": {
        "brokerURI": "mqtt.broker.com:8883",
        "username": "user1",
        "password": "password1",
        "brokerCACert": "string"
      }
    }
  ],
  "propertyID": "temperature"
}
]]></artwork></figure>

<t>where-
 - "event" is the event identifier, which also maps to the MQTT topic name
 - "eventFormat" is the format the data stream is delivered in, either default
   (decorated with id and property) or just the payload 
 - "replay" defines whether the event should be cached for replay or not
 - "id" is hte id of the device or group the event is valid for
 - "type" is the type if the id, either device or group
 - "dataApps" is an array of data appplications that can subscribe to the event
 - "propertyID" is the propertyID that will be used in action APIs to activate
   this event</t>

<t>The dataApps array consists of following-
 - "dataAppID" is the identity of the data application either configured 
   administratively or through SCIM.
 - "mqtt" optional MQTT broker connection parameters, in case an external MQTT
   needs to be configured</t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as all the attributes that were configured
from the request.</t>

<t>Example of a register event response:</t>

<figure title="Example register event response" anchor="exregeveresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "event": "enterprise/hospital/pulse_oximeter",
  "eventFormat": "default",
  "replay": false,
  "type": "device",
  "dataApps": [
    {
      "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
      "mqtt": {
        "brokerURI": "mqtt.broker.com:8883",
        "username": "user1",
        "password": "password1",
        "brokerCACert": "string"
      }
    }
  ],
  "propertyID": "temperature"
}
]]></artwork></figure>

<t>where-</t>

<t><list style="symbols">
  <t>"id", "requestID" and "technology" are part of the standard <xref target="success"/> definition</t>
  <t>"event" is the event identifier, which also maps to the MQTT topic name</t>
  <t>"eventFormat" is the format the data stream is delivered in, either default 
(decorated with id and property) or just the payload</t>
  <t>"replay" defines whether the event should be cached for replay or not</t>
  <t>"dataApps" is an array of data appplications that can subscribe to the event</t>
  <t>"propertyID" is the propertyID that will be used in action APIs to activate
this event</t>
</list></t>

<t>The dataApps array consists of following-
 - "dataAppID" is the identity of the data application either configured 
   administratively or through SCIM.
 - "mqtt" optional MQTT broker connection parameters, in case an external MQTT
   needs to be configured</t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="updating-a-topic"><name>Updating a topic</name>

<t>Method: PUT /registration/event</t>

<t>Description: Update an existing event</t>

<t>Parameters: None</t>

<t>Request Body:
 - An event name that matches to an MQTT pub/sub topic
 - The data format the event should be delivered in
 - The device or group id the event is valid for
 - Whether the event needs to be cached for replay
 - the data applications that can consume the events</t>

<t>Example body updating an event:</t>

<figure title="Example updating an event" anchor="exupdeve"><artwork><![CDATA[
{
  "event": "enterprise/hospital/pulse_oximeter",
  "eventFormat": "default",
  "replay": false,
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "type": "device",
  "dataApps": [
    {
      "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
      "mqtt": {
        "brokerURI": "mqtt.broker.com:8883",
        "username": "user1",
        "password": "password1",
        "brokerCACert": "string"
      }
    }
  ],
  "propertyID": "temperature"
  "ble": {
    "type": "gatt",
    "serviceID": "12345678-1234-5678-1234-56789abcdef0",
    "characteristicID": "12345678-1234-5678-1234-56789abcdef1"
  }
}
]]></artwork></figure>

<t>where-
 - "event" is the event identifier, which also maps to the MQTT topic name
 - "eventFormat" is the format the data stream is delivered in, either default
   (decorated with id and property) or just the payload
 - "replay" defines whether the event should be cached for replay or not
 - "id" is hte id of the device or group the event is valid for
 - "type" is the type if the id, either device or group
 - "dataApps" is an array of data appplications that can subscribe to the event
 - "propertyID" is the propertyID that will be used in action APIs to activate
   this event</t>

<t>The dataApps array consists of following-
 - "dataAppID" is the identity of the data application either configured
   administratively or through SCIM.
 - "mqtt" optional MQTT broker connection parameters, in case an external MQTT
   needs to be configured</t>

<t>The propertyID gets mapped to a protocol-specific property with a 
property mapping, through a protocol object-</t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as all the attributes that were configured
from the request.</t>

<t>Example of an update register event response:</t>

<figure title="Example update event response" anchor="exupdeveresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "id": "12345678-1234-5678-1234-56789abcdef4",
  "event": "enterprise/hospital/pulse_oximeter",
  "eventFormat": "default",
  "replay": false,
  "type": "device",
  "dataApps": [
    {
      "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
      "mqtt": {
        "brokerURI": "mqtt.broker.com:8883",
        "username": "user1",
        "password": "password1",
        "brokerCACert": "string"
      }
    }
  ],
  "propertyID": "temperature"
  "ble": {
    "type": "gatt",
    "serviceID": "12345678-1234-5678-1234-56789abcdef0",
    "characteristicID": "12345678-1234-5678-1234-56789abcdef1"
  }
}
]]></artwork></figure>

<t>where-</t>

<t><list style="symbols">
  <t>"id", "requestID" and "technology" are part of the standard <xref target="success"/> 
definition</t>
  <t>"event" is the event identifier, which also maps to the MQTT topic name</t>
  <t>"eventFormat" is the format the data stream is delivered in, either default
(decorated with id and property) or just the payload</t>
  <t>"replay" defines whether the event should be cached for replay or not</t>
  <t>"dataApps" is an array of data appplications that can subscribe to the event</t>
  <t>"propertyID" is the propertyID that will be used in action APIs to activate
this event</t>
</list></t>

<t>The dataApps array consists of following-
 - "dataAppID" is the identity of the data application either configured
   administratively or through SCIM.
 - "mqtt" optional MQTT broker connection parameters, in case an external MQTT
   needs to be configured</t>

<t>The propertyID gets mapped to a protocol-specific property with a
property mapping, through a protocol object-</t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="get-configuration-of-one-or-more-events"><name>Get configuration of one or more events</name>

<t>Method: GET /registration/event</t>

<t>Description: Gets the configuration of one or more events</t>

<t>Parameters: An event name. Multiple events can be added by comma-separated
attributes. If no parameters are present, all events are returned.</t>

<t>Response: A success response as in <xref target="success"/> with a "events" object
containing an array of returned event names with attributes defined in
<xref target="exupdeve"/>.</t>

<t>Example of a get event response:</t>

<figure title="Example get event response" anchor="exgeteveresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "events": [
    {
      "ble": {
        "type": "gatt",
        "serviceID": "12345678-1234-5678-1234-56789abcdef0",
        "characteristicID": "12345678-1234-5678-1234-56789abcdef1"
      },
      "event": "enterprise/hospital/pulse_oximeter",
      "propertyID": "temperature",
      "eventFormat": "default",
      "replay": false,
      "id": "12345678-1234-5678-1234-56789abcdef4",
      "type": "device",
      "dataApps": [
        {
          "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
          "mqtt": {
            "brokerURI": "mqtt.broker.com:8883",
            "username": "user1",
            "password": "password1",
            "brokerCACert": "string"
          }
        }
      ],
      "technology": "ble"
    },
    {
      "zigbee": {
        "endpointID": 1,
        "clusterID": 6,
        "propertyID": 16,
        "type": 1
      },
      "event": "enterprise/hospital/pulse_oximeter",
      "propertyID": "temperature",
      "eventFormat": "default",
      "replay": false,
      "id": "12345678-1234-5678-1234-56789abcdef4",
      "type": "device",
      "dataApps": [
        {
          "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
          "mqtt": {
            "brokerURI": "mqtt.broker.com:8883",
            "username": "user1",
            "password": "password1",
            "brokerCACert": "string"
          }
        }
      ],
      "technology": "ble"
    }
  ]
}
]]></artwork></figure>

<t>where-
 - "id", "requestID" and "technology" are part of the standard <xref target="success"/>
   definition
 - "events" is an array of events</t>

<t>where an event-
 - "event" is the event identifier, which also maps to the MQTT topic name
 - "eventFormat" is the format the data stream is delivered in, either default
   (decorated with id and property) or just the payload
 - "replay" defines whether the event should be cached for replay or not
 - "id" is hte id of the device or group the event is valid for
 - "type" is the type if the id, either device or group
 - "dataApps" is an array of data appplications that can subscribe to the event
 - "propertyID" is the propertyID that will be used in action APIs to activate
   this event</t>

<t>The dataApps array consists of following-
 - "dataAppID" is the identity of the data application either configured
   administratively or through SCIM.
 - "mqtt" optional MQTT broker connection parameters, in case an external MQTT
   needs to be configured</t>

<t>The propertyID gets mapped to a protocol-specific property with a
property mapping, through a protocol object-</t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="delete-one-or-more-topics"><name>Delete one or more topics</name>

<t>Method: DELETE /registration/event</t>

<t>Description: Delete one or more events</t>

<t>Parameters: An event name. Multiple events can be added by comma-separated
attributes. If no parameters are present, all events are returned.</t>

<t>Response: A success response as in <xref target="success"/> with a "events" object
containing an array of returned event names with attributes defined in
<xref target="exupdeve"/>.</t>

<t>Example of a delete event response:</t>

<figure title="Example delete event response" anchor="exdeleveresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "events": [
    {
      "ble": {
        "type": "gatt",
        "serviceID": "12345678-1234-5678-1234-56789abcdef0",
        "characteristicID": "12345678-1234-5678-1234-56789abcdef1"
      },
      "event": "enterprise/hospital/pulse_oximeter",
      "propertyID": "temperature",
      "eventFormat": "default",
      "replay": false,
      "id": "12345678-1234-5678-1234-56789abcdef4",
      "type": "device",
      "dataApps": [
        {
          "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
          "mqtt": {
            "brokerURI": "mqtt.broker.com:8883",
            "username": "user1",
            "password": "password1",
            "brokerCACert": "string"
          }
        }
      ],
      "technology": "ble"
    },
    {
      "zigbee": {
        "endpointID": 1,
        "clusterID": 6,
        "propertyID": 16,
        "type": 1
      },
      "event": "enterprise/hospital/pulse_oximeter",
      "propertyID": "temperature",
      "eventFormat": "default",
      "replay": false,
      "id": "12345678-1234-5678-1234-56789abcdef4",
      "type": "device",
      "dataApps": [
        {
          "dataAppID": "12345678-1234-5678-1234-56789abcdef4",
          "mqtt": {
            "brokerURI": "mqtt.broker.com:8883",
            "username": "user1",
            "password": "password1",
            "brokerCACert": "string"
          }
        }
      ],
      "technology": "ble"
    }
  ]
}
]]></artwork></figure>

<t>where-
 - "id", "requestID" and "technology" are part of the standard <xref target="success"/>
   definition
 - "events" is an array of events</t>

<t>where an event-
 - "event" is the event identifier, which also maps to the MQTT topic name
 - "eventFormat" is the format the data stream is delivered in, either default
   (decorated with id and property) or just the payload
 - "replay" defines whether the event should be cached for replay or not
 - "id" is hte id of the device or group the event is valid for
 - "type" is the type if the id, either device or group
 - "dataApps" is an array of data appplications that can subscribe to the event
 - "propertyID" is the propertyID that will be used in action APIs to activate
   this event</t>

<t>The dataApps array consists of following-
 - "dataAppID" is the identity of the data application either configured
   administratively or through SCIM.
 - "mqtt" optional MQTT broker connection parameters, in case an external MQTT
   needs to be configured</t>

<t>The propertyID gets mapped to a protocol-specific property with a
property mapping, through a protocol object-</t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
</section>
</section>
<section anchor="property-registration"><name>Property registration</name>

<t>/registration/property</t>

<t>The property registration API allows an application to register a property
mapping against a protocol-specific property as decribed in <xref target="propertymap"/></t>

<t>Operations:</t>

<t><list style="symbols">
  <t>Register a property: POST</t>
  <t>Update a property: PUT</t>
  <t>Get a property: GET</t>
  <t>Delete a property: DELETE</t>
</list></t>

<section anchor="property-registration-api"><name>Property registration API</name>

<section anchor="registering-a-property"><name>Registering a property</name>

<t>Method: POST /registration/property</t>

<t>Description: Register a property mapping to a protocol-specific property</t>

<t>Parameters: None</t>

<t>Request Body:
 - a property ID
 - a protocol object containing a protocol mapping</t>

<t>Example body registering a property:</t>

<figure title="Example registering a property" anchor="exregprop"><artwork><![CDATA[
{
  "propertyID": "temperature",
  "ble": {
    "serviceID": "12345678-1234-5678-1234-56789abcdef4",
    "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
    "long": false
  }
}
]]></artwork></figure>

<t>where-
 - "propertyID" is the propertyID that will be used in action APIs to refer
   to this property mapping
 - A protocol object with a protocol-specific property map, as decribed in
   <xref target="propertymap"/></t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as all the attributes that were configured
from the request.</t>

<t>Example of a register property response:</t>

<figure title="Example register property response" anchor="exregpropresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "propertyID": "temperature",
  "ble": {
    "serviceID": "12345678-1234-5678-1234-56789abcdef4",
    "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
    "long": false
  }
}
]]></artwork></figure>

<t>where-</t>

<t><list style="symbols">
  <t>"id", "requestID" and "technology" are part of the standard <xref target="success"/>
definition</t>
  <t>"propertyID" is the propertyID that will be used in action APIs to refer
to this property mapping</t>
  <t>A protocol object with a protocol-specific property map, as decribed in
<xref target="propertymap"/></t>
</list></t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="updating-a-property"><name>Updating a property</name>

<t>Method: PUT /registration/property</t>

<t>Description: Update a property mapping to a protocol-specific property</t>

<t>Parameters: None</t>

<t>Request Body:
 - a property ID
 - a protocol object containing a protocol mapping</t>

<t>Example body updating a property:</t>

<figure title="Example registering a property" anchor="exupdprop"><artwork><![CDATA[
{
  "propertyID": "temperature",
  "ble": {
    "serviceID": "12345678-1234-5678-1234-56789abcdef4",
    "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
    "long": false
  }
}
]]></artwork></figure>

<t>where-
 - "propertyID" is the propertyID that will be used in action APIs to refer
   to this property mapping
 - A protocol object with a protocol-specific property map, as decribed in
   <xref target="propertymap"/></t>

<t>Response:
Success responses include standard success response properties
as defined in <xref target="success"/> as well as all the attributes that were configured
from the request.</t>

<t>Example of ain update property response:</t>

<figure title="Example register property response" anchor="exupdpropresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "propertyID": "temperature",
  "ble": {
    "serviceID": "12345678-1234-5678-1234-56789abcdef4",
    "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
    "long": false
  }
}
]]></artwork></figure>

<t>where-</t>

<t><list style="symbols">
  <t>"id", "requestID" and "technology" are part of the standard <xref target="success"/>
definition</t>
  <t>"propertyID" is the propertyID that will be used in action APIs to refer
to this property mapping</t>
  <t>A protocol object with a protocol-specific property map, as decribed in
<xref target="propertymap"/></t>
</list></t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="get-property-mapping-of-one-or-more-properties"><name>Get property mapping of one or more properties</name>

<t>Method: GET /registration/property</t>

<t>Description: Gets the property mapping of one or more properties</t>

<t>Parameters: A property name. Multiple properties can be added by
comma-separated parameters. If no parameters are present, all properties
are returned.</t>

<t>Response: A success response as in <xref target="success"/> with an array of properties,
containing propertyID with protocol object containing a protocol-specific 
property mapping</t>

<t>Example of a get property response:</t>

<figure title="Example get property response" anchor="exgetpropresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "properties": [
    {
      "ble": {
        "serviceID": "12345678-1234-5678-1234-56789abcdef4",
        "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
        "long": false
      },
      "propertyID": "temperature"
    },
    {
      "zigbee": {
        "endpointID": 1,
        "clusterID": 6,
        "propertyID": 16,
        "type": 1
      },
      "propertyID": "temperature"
    }
  ]
}
]]></artwork></figure>

<t>where-
 - "id", "requestID" and "technology" are part of the standard <xref target="success"/>
   definition
 - "properties" is an array of properties</t>

<t>where a property-
 - "id", "requestID" and "technology" are part of the standard <xref target="success"/>
   definition
 - "propertyID" is the propertyID that will be used in action APIs to refer
   to this property mapping
 - A protocol object with a protocol-specific property map, as decribed in
   <xref target="propertymap"/></t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
<section anchor="delete-property-mapping-of-one-or-more-properties"><name>Delete property mapping of one or more properties</name>

<t>Method: DELETE /registration/property</t>

<t>Description: Deletes the property mapping of one or more properties</t>

<t>Parameters: A property name. Multiple properties can be added by 
comma-separated parameters. If no parameters are present, all properties
are deleted.</t>

<t>Response: A success response as in <xref target="success"/> with an array of properties, 
containing propertyID with protocol object containing a protocol-specific <br />
property mapping</t>

<t>Example of a delete property response:</t>

<figure title="Example delete property response" anchor="exdelpropresp"><artwork><![CDATA[
{
  "status": "SUCCESS",
  "requestID": "12345678-5678-1234-5578-abcdef1234",
  "properties": [
    {
      "ble": {
        "serviceID": "12345678-1234-5678-1234-56789abcdef4",
        "characteristicID": "12345678-1234-5678-1234-56789abcdef4",
        "long": false
      },
      "propertyID": "temperature"
    },
    {
      "zigbee": {
        "endpointID": 1,
        "clusterID": 6,
        "propertyID": 16,
        "type": 1
      },
      "propertyID": "temperature"
    }
  ]
}
]]></artwork></figure>

<t>where-
 - "id", "requestID" and "technology" are part of the standard <xref target="success"/>
   definition
 - "properties" is an array of properties</t>

<t>where a property-
 - "id", "requestID" and "technology" are part of the standard <xref target="success"/>
   definition
 - "propertyID" is the propertyID that will be used in action APIs to refer
   to this property mapping
 - A protocol object with a protocol-specific property map, as decribed in
   <xref target="propertymap"/></t>

<t>A failure will generate a standard failed response. Please refer to <xref target="failure"/>
definition of failed response.</t>

</section>
</section>
</section>
</section>
<section anchor="nipc-extensibility"><name>NIPC Extensibility</name>

<t>NIPC is extensible in two ways:</t>

<t><list style="symbols">
  <t>Protocol mapping: New protocol mapping can extend NIPC with support
for new non-IP protocols</t>
  <t>API extensions: API extensions leverage compound statements of basic NIPC
action APIs to simplify common operations for applications.</t>
</list></t>

<section anchor="protocol-extensions"><name>Protocol extensions</name>

<t>As described in <xref target="propertymap"/> NIPC supports mapping protocol specific
mapping to NIPC properties. BLE and Zigbee are used as examples, but protocol
mapping is extensible to other protocols, so noew non-IP protocols can be 
supported by NIPC without a schema change.</t>

<figure title="Extended protocol mapping" anchor="extprotmap"><artwork><![CDATA[
     -  property
        |
        |> BLE
        |     - BLE  properties
        |
        |> Zigbee
        |     - Zigbee properties
        |
        |> New protocol 
        |     -  New protocol properties

]]></artwork></figure>

<t>As shown in <xref target="extprotmap"/>, a protocol mapping can be added by adding
a new technology specific extension to the schema.</t>

<t>This is performed by adding the new protocol to the technology enum in
the base object definition <xref target="objectdef"/></t>

<t>Furthermore, the protocol objects need to be extended with the new
protocol as well. Protocol objects will be extended as follows:</t>

<texttable title="Adding Protocol mappings" anchor="newprotext">
      <ttcol align='left'>Attribute</ttcol>
      <ttcol align='left'>Req</ttcol>
      <ttcol align='left'>Type</ttcol>
      <ttcol align='left'>Example</ttcol>
      <c>ble</c>
      <c>T</c>
      <c>object</c>
      <c>an object with BLE-specific properties</c>
      <c>zigbee</c>
      <c>T</c>
      <c>object</c>
      <c>an object with Zigbee-specific properties</c>
      <c>newProtocol</c>
      <c>T</c>
      <c>object</c>
      <c>an object with newProtocol-specific props</c>
</texttable>

<t>In the new protocol object, protocol specific properties can be added.</t>

<t>Protocol mappings need to be IANA registered.</t>

</section>
<section anchor="api-extensions"><name>API extensions</name>

<t>/extension</t>

<t>The extension APIs allow for extensibility of the APIs, either IANA 
registered extensions or vendor-specific extensions.
Extension APIs must leverage the basic NIPC defined APIs and combine them in 
compound statements in order to streamline application operation against
devices, make operations more expediant and convenient in one API call.
In principle they do not add any basic functionality. In
the OpenAPI model <xref target="openAPI"/> below, we have defined a few example 
extensions.</t>

</section>
</section>
<section anchor="publishsubscribe-interface"><name>Publish/Subscribe Interface</name>

<t>The publish/subscribe interface, or data streaming interface, is an MQTT
publishing interface. Pub/sub topics can be created and managed by means
of the /registration/event NIPC element.</t>

<t>In this memo, we propose the data format to be CBOR <xref target="RFC8949"/>.</t>

<section anchor="cddl-definition"><name>CDDL Definition</name>

<t>We have a CDDL <xref target="RFC8610"/> definition where we define the
DataSubscription struct that will be used by all the messages published 
to the MQTT broker.</t>

<t>The DataSubscription struct is a CBOR map that will contain the raw data
in bytes and a timestamp of the data. Optionally, the message will also
have a deviceId that corresponds to the SCIM ID of the device if the 
payload is associated to a known device.</t>

<t>Other fields in the CDDL such as apMacAddress and rssi can be optionally
included but these fields can expose the underlying network topology.</t>

<t>Each message also has a subscription choice group that will define the
type of data that is being published.</t>

<figure><sourcecode type="CDDL"><![CDATA[
DataSubscription = {
  data: bytes,
  timestamp: float, ; epoch in seconds
  ? deviceId: text,
  ? apMacAddress: text,
  subscription
}

subscription = (
  bleSubscription: BleSubscription //
  bleAdvertisement: BleAdvertisement //
  bleConnectionStatus: BleConnectionStatus //
  zigbeeSubscription: ZigbeeSubscription //
  rawPayload: RawPayload
)

BleSubscription = {
  serviceId: text,
  characteristicId: text
}

BleAdvertisement = {
  macAddress: text,
  ? rssi: nint,
}

BleConnectionStatus = {
  macAddress: text,
  connected: bool,
  ? reason: int
}

ZigbeeSubscription = {
  endpointId: int,
  clusterId: int,
  attributeId: int
  attributeType: int
}

RawPayload = {
  contextId: text
}
]]></sourcecode></figure>

</section>
<section anchor="cbor-examples"><name>CBOR Examples</name>

<t>This section contains a few examples of the DataSubscription struct 
depicted in CBOR diagnostic notation.</t>

<figure title="Onboarded BLE Device Advertisement"><artwork><![CDATA[
{
    "data": h'02011A020A0C16FF4C001007721F41B0392078',
    "deviceId": "75fde96d-886f-4ac0-a1d5-df79f76e7c9c",
    "timestamp": 1727484393,
    "bleAdvertisement": {
        "macAddress": "C1:5C:00:00:00:01",
        "rssi": -25
    }
}
]]></artwork></figure>

<figure title="Non-onboarded BLE Device Advertisement"><artwork><![CDATA[
{
    "data": h'02011A020A0C16FF4C001007721F41B0392078',
    "timestamp": 1727484393,
    "bleAdvertisement": {
        "macAddress": "C1:5C:00:00:00:01",
        "rssi": -25
    }
}
]]></artwork></figure>

<figure title="BLE GATT Notification"><artwork><![CDATA[
{
    "data": h'434630374346303739453036',
    "deviceId": "75fde96d-886f-4ac0-a1d5-df79f76e7c9c",
    "timestamp": 1727484393,
    "bleSubscription": {
        "serviceId": "a4e649f4-4be5-11e5-885d-feff819cdc9f",
        "characteristicId": "c4c1f6e2-4be5-11e5-885d-feff819cdc9f"
    }
}
]]></artwork></figure>

<figure title="BLE Connection status event"><artwork><![CDATA[
{
    "data": h'434630374346303739453036',
    "deviceId": "75fde96d-886f-4ac0-a1d5-df79f76e7c9c",
    "timestamp": 1727484393,
    "bleConnectionStatus": {
        "macAddress": "C1:5C:00:00:00:01",
        "connected": true
    }
}
]]></artwork></figure>

<figure title="Zigbee Attribute Notification"><artwork><![CDATA[
{
    "data": h'434630374346303739453036',
    "deviceId": "75fde96d-886f-4ac0-a1d5-df79f76e7c9c",
    "timestamp": 1727484393,
    "zigbeeSubscription": {
        "endpointId": 1,
        "clusterId": 6,
        "attributeId": 12,
        "type": 1
    }
}
]]></artwork></figure>

</section>
</section>
<section anchor="examples"><name>Examples</name>

<t>This section contains a few examples on how applications can leverage 
NIPC operations to communicate with BLE and Zigbee devices.</t>

<section anchor="ble-advertisement"><name>BLE Advertisement</name>

<t>In this example, we will onboard a device, and setup an advertisement
subscription event for that device.</t>

<t>The sequence of operations for this are:</t>

<t><list style="symbols">
  <t>Onboard a device using the SCIM Interface (out of scope of this
memo)</t>
  <t>Register an eventc with the device id to subscribe to advertisements
POST /register/event</t>
  <t>Subscribe to the topic from the data receiver app 
MQTT subscribe topic</t>
</list></t>

</section>
<section anchor="ble-property-readwrite"><name>BLE Property Read/Write</name>

<t>In this example, we will connect to a BLE device and read and write from a
property.</t>

<t>The sequence of operations for this are:</t>

<t><list style="symbols">
  <t>Onboard a device using the SCIM Interface (out of scope of this
memo)</t>
  <t>Connect to the BLE device
POST /action/connection</t>
  <t>Read a property from the BLE device
GET  /action/property</t>
  <t>Write to a property on the BLE device
POST /action/property</t>
  <t>Disconnect from the BLE device
DELETE /action/connection</t>
</list></t>

</section>
<section anchor="zigbee-property-readwrite"><name>Zigbee Property Read/Write</name>

<t>In this example, we will connect a zigbee device to a Zigbee mesh
and read and write from a property</t>

<t>The sequence of operations for this are:</t>

<t><list style="symbols">
  <t>Onboard a device using the SCIM Interface (out of scope of this
memo)</t>
  <t>Connect the Zigbee device
POST /action/connection</t>
  <t>Read a property from the Zigbee device
GET  /action/property</t>
  <t>Write to a property on the Zigbee device
POST  /action/property</t>
  <t>Disconnect from the Zigbee device
DELETE /action/connection</t>
</list></t>

</section>
</section>
<section anchor="security-considerations"><name>Security Considerations</name>

<t>TBD.</t>

</section>
<section anchor="iana-considerations"><name>IANA Considerations</name>

<t>This section provides guidance to the Internet Assigned Numbers Authority
(IANA) regarding registration of values related to NIPC, in accordancei
with <xref target="RFC5226"/>.</t>

<section anchor="protocol-mapping"><name>Protocol mapping</name>

</section>
<section anchor="api-extensions-1"><name>API extensions</name>

</section>
</section>


  </middle>

  <back>


    <references title='Normative References' anchor="sec-normative-references">

&RFC7644;
&I-D.ietf-scim-device-model;
&RFC2119;
&RFC8174;
&I-D.ietf-asdf-sdf;
&RFC9114;
&RFC8949;
&RFC8610;
&RFC5226;


    </references>

    <references title='Informative References' anchor="sec-informative-references">

<reference anchor="BLE53" >
  <front>
    <title>Bluetooth Core Specification, Version 5.3</title>
    <author >
      <organization>Bluetooth SIG</organization>
    </author>
    <date year="2021"/>
  </front>
</reference>
<reference anchor="Zigbee22" >
  <front>
    <title>zigbee Specification, Version 22 1.0</title>
    <author >
      <organization>Connectivity Standards Alliance</organization>
    </author>
    <date year="2017"/>
  </front>
</reference>


    </references>


<?line 1987?>

<section anchor="openapi-definition"><name>OpenAPI definition</name>

<t>The following non-normative model is provide for convenience of
the implementor.</t>

<figure anchor="openAPI"><artwork><![CDATA[
<CODE BEGINS>
file "openapi.yml"
openapi: 3.0.3
info:
  title: Non IP Device Control (NIPC) API
  description: |-
    There has been a large influx of non-IP devices supporting
    processes in manufacturing, healthcare, hospitality, retail, the
    home, and the office.  At the same time, wireless access points
    have been deployed nearly everywhere, many of which have radios
    that can transmit and receive different frame types, such as BLE,
    Zigbee. To integrate multiple of these use cases leveraging a
    single wireless infrastructure and avoid the need for parallel
    infrastructure, a Non IP device gateway function is necessary.
    The gateway provides the following functions:
       - authentication and authorization of application clients that
         will communicate with devices 
       - APIs that onboard a device on the network (out of scope for
         this specification, but covered in SCIM for devices)
       - APIs that allow an app to set up a connection with a device
       - APIs that allow an app to exchange action with a device
       - APIs that allow a device to create registrations in the
         network for a device 
    These collection of these APIs, in combination with the
    onboarding API (SCIM for devices) will allow an application to
    perform a complete set of operations on Non-IP devices.
  termsOfService: http://swagger.io/terms/
  contact:
    email: bbrinckm@cisco.com
  license:
    name: TBD
    url: TBD
  version: 0.3.5
externalDocs:
  description: NIPC IETF draft
  url: TBD
servers:
  - url: https://{gw_host}/nipc
    variables:
      gw_host:
        default: localhost
        description: Gateway Host
tags:
  - name: action
    description: APIs that allow apps to perform actions on devices. 
  - name: registrations
    description: |-
      APIs that allow apps to register properties of devices.
  - name: extensions
    description: |-
      APIs that simplify application interaction by implementing one
      or more basic API's into a single API call.

paths:
### Action
  /action/connection:
    post:
      tags:
        - action
      summary: |-
        Connect a device to the network, optionally with service
        discovery 
      description: |-
        Connect a device to the network, optionally with service
        discovery 
      operationId: Connect
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Connection'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
    
    get:
      tags:
        - action
      summary: |-
        Get connection state devices for a device or group of
        devices
      description: |-
        Get all connection status for connections made by control ap
        or connection status by object ID, multiple ids can be
        provided with comma separated strings, or a group id can be
        provided  
      operationId: GetConnections
      parameters:
        - name: id
          in: query
          description: device or group ids that need to be filtered
          required: false
          explode: false
          schema:
            type: array
            items:
              type: string
              format: uuid
              example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiConnectionsResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
                
    delete:
      tags:
        - action
      summary: Disconnect a device or group of devices
      description: |-
        Disconnect a device or device group by object ID, Multiple
        ids can be provided with comma separated strings, or a
        group id can be provided 
      operationId: DeleteConnections
      parameters:
        - name: id
          in: query
          description: device or group ids that need to be filtered
          required: false
          explode: false
          schema:
            type: array
            items:
              type: string
              format: uuid
              example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiConnectionsResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 

  /action/connection/id/{id}:
    post:
      tags:
        - action
      summary: |-
        Connect a device by device id (device technology needs to
        support connection) 
      description: |-
        Connect a device by device id, full service discovery 
        will be performed. Will fail if device has multiple 
        technologies defined. Group ids will fail.
      operationId: CreateConnectionbyID
      parameters:
        - name: id
          in: path
          description: device id that need to be filtered
          required: true
          schema:
            type: string
            format: uuid
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
  
    get:
      tags:
        - action
      summary: Get connection by id for a device
      description: |-
        Get connection by id for a device, success when device
        connected, failure when device not connected.
        Group ids will also fail. 
      operationId: GetConnectionbyId
      parameters:
        - name: id
          in: path
          description: device id that need to be filtered
          required: true
          schema:
            type: string
            format: uuid
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
                
    delete:
      tags:
        - action
      summary: Delete connection by id for a device
      description: |-
        Disconnect a device by id, success when device
        is disconnected, failure disconnect fails.
        Group ids will also fail. 
      operationId: DeleteConnectionbyID
      parameters:
        - name: id
          in: path
          description: device id that need to be filtered
          required: true
          schema:
            type: string
            format: uuid
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
  
  /action/services/:            
    get:
      tags:
        - action
      summary: Get all services for a device
      description: |-
        Get all services for a connected device, success
        when service discovery succeeds failure, failure when 
        Service discovery fails. This updates cache for cached
        Services. Fails when using a group id.
      operationId: GetServicesbyId
      parameters:
        - name: id
          in: query
          description: device id that need to be filtered
          required: true
          schema:
            type: string
            format: uuid
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 

  /action/services/discover:
    post:
      tags:
        - action
      summary: |-
        Selectively discover services on a device, limited 
        to services described in the parameters
      description: |-
        Selectively discover services on a device, limited 
        to services described in the parameters.
        Group ids will fail.
      operationId: GetSelectiveServices
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Service'
        required: true    
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /action/property:
    post:
      tags:
        - action
      summary: Write a value to an property on a device
      description: Write a value to an property on a device
      operationId: Write
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyValue'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyValueResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request       
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
    
    put:
      tags:
        - action
      summary: Update a value of an property on a device
      description: Update a value of an property on a device
      operationId: Update
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyValue'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyValueResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request       
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
  
  /action/property/{property}:
    delete:
      tags:
        - action
      summary: Delete a value from an property on a device
      description: Delete a value to an property on a device
      operationId: Delete
      parameters:
      - name: id
        in: query
        description: device id that need to be filtered
        required: true
        schema:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4
      - name: property
        in: path
        description: property that needs to be filtered
        required: true
        schema:
          type: string
          example: "temperature"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyValueResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 
                
    get:
      tags:
        - action
      summary: Read a value from an property on a device
      description: Read a value to an property on a device
      operationId: Read
      parameters:
      - name: id
        in: query
        description: device id that need to be filtered
        required: true
        schema:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4
      - name: property
        in: path
        description: property that needs to be filtered
        required: true
        schema:
          type: string
          example: "temperature"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyValueResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse' 

  /action/property/write:
    post:
      tags:
        - action
      summary: Write a value to an property using technology extensions
      description: |-
        Write a value to an property directly, addressing the property
        with technology-specific extensions, this does not require
        property registration. You cannot write to a group id.
      operationId: AttrWrite
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyValueRaw'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyValueResponseRaw'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'
                
  /action/property/read:
    post:
      tags:
        - action
      summary: Read a value to an property using technology extensions
      description: |-
        Read a value to an property directly, addressing the property
        with technology-specific extensions, this does not require
        property registration. You cannot write to a group id.
      operationId: AttrRead
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyRaw'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyValueResponseRaw'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'
  
  /action/property/subscription:
    post:
      tags:
        - action
      summary: |-
         Subscribe to streaming event action from an property on a device
      description: |-
        Subscribe to streaming event action from an property on a device
      operationId: Subscribe
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Subscription'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request 
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'   
  
  /action/property/subscription/{property}:
    delete:
      tags:
        - action
      summary: |-
        Unsubscribe to streaming event action from an property on a device
      description: |-
        Unsubscribe to streaming event action from an property on a device
      operationId: Unsubscribe
      parameters:
      - name: id
        in: query
        description: device id that need to be filtered
        required: true
        schema:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4
      - name: property
        in: path
        description: property that needs to be filtered
        required: true
        schema:
          type: string
          example: "temperature" 
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'
                
    get:
      tags:
        - action
      summary: Get the status of an event subscription on a device
      description: Get the status of an event subscription on a device
      operationId: GetSubscription
      parameters:
      - name: id
        in: query
        description: device id that need to be filtered
        required: true
        schema:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4
      - name: property
        in: path
        description: property that needs to be filtered
        required: true
        explode: true
        schema:
          type: string
          example: "temperature" 
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /action/property/subscription/event/{event}:    
    delete:
      tags:
        - action
      summary: delete all active subscriptions by event
      description: delete all active subscriptions by event
      operationId: deleteSubscriptionbyEvent
      parameters:
        - name: event
          in: path
          description: event that needs to be filtered
          required: true
          schema:
            type: string
            example: "enterprise/hospital/pulse_oximeter"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref:
                   '#/components/schemas/MultiSubscriptionResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - action
      summary: get all active subscriptions by event
      description: get all active subscriptions by event
      operationId: getSubsciptionsbyEvent
      parameters:
        - name: event
          in: path
          description: event that needs to be filtered
          required: true
          schema:
            type: string
            example: "enterprise/hospital/pulse_oximeter"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref:
                   '#/components/schemas/MultiSubscriptionResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref:
                   '#/components/schemas/MultiSubscriptionResponse'

  /action/property/subscription/id/{id}:
    delete:
      tags:
        - action
      summary: delete all event subscriptions by id
      description: delete all event subscriptions by id
      operationId: deleteSubscriptionbyID
      parameters:
        - name: id
          in: path
          description: object id that needs to be filtered
          required: true
          schema:
            type: string
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref:
                   '#/components/schemas/MultiSubscriptionResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - action
      summary: get all event subscriptions by object id
      description: get all event subscriptions by object id
      operationId: getSubscriptionbyID
      parameters:
        - name: id
          in: path
          description: object id that needs to be filtered
          required: true
          schema:
            type: string
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref:
                   '#/components/schemas/MultiSubscriptionResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /action/property/subscription/start:
    post:
      tags:
        - action
      summary: |-
         Subscribe to streaming action from an property on a device
         by directly addressing hte property (unregistered attr)
      description: |-
        Subscribe to streaming action from an property on a device
        by directly addressing hte property (unregistered attr)
      operationId: SubscriptionStart
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/SubscriptionRaw'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request 
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'  
  
  /action/property/subscription/stop:
    post:
      tags:
        - action
      summary: |-
         Stop streaming action from an property on a device
         by directly addressing hte property (unregistered attr)
      description: |-
        Stop streaming action from an property on a device
        by directly addressing hte property (unregistered attr)
      operationId: SubscriptionStop
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/SubscriptionRaw'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'          
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request 
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'  
 
  /action/broadcast:
    post:
      tags:
        - action
      summary: Broadcast to a device
      description: Broadcast to a device
      operationId: Broadcast
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Broadcast'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

### Registrations
  /registration/event:
    post:
      tags:
        - registrations
      summary: Register a publish/subscribe event
      description: Register a publish/subscribe event
      operationId: registerEvent
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Event'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/EventResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    put:
      tags:
        - registrations
      summary: Update a publish/subscribe event
      description: Update a publish/subscribe event
      operationId: UpdateEvent
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Event'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/EventResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    delete:
      tags:
        - registrations
      summary: unregister a publish/subscribe event
      description: |-
        unregister a publish/subscribe event, single topic,
        multiple events not allowed.
      operationId: unregisterEvent
      parameters:
        - name: event
          in: query
          description: event that need to be filtered
          required: false
          explode: false
          schema:
            type: string
            example: "enterprise/hospital/pulse_oximeter"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/EventResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - registrations
      summary: get one or all publish/subscribe event
      description: |-
        get publish/subscribe event, if no topic is specified
        in query, all events will be returned
      operationId: getEvent
      parameters:
        - name: event
          in: query
          description: event that need to be filtered
          required: false
          explode: false
          schema:
            type: string
            example: "enterprise/hospital/pulse_oximeter"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiEventsResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /registration/event/{event}:
    delete:
      tags:
        - registrations
      summary: delete a publish/subscribe event by name
      description: unregister a publish/subscribe event by Name
      operationId: deleteEventbyName
      parameters:
        - name: event
          in: path
          description: event that needs to be filtered
          required: true
          schema:
            type: string
            example: "enterprise/hospital/pulse_oximeter"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/EventResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - registrations
      summary: get a publish/subscribe event by name
      description: get a publish/subscribe event by name
      operationId: getEventbyName
      parameters:
        - name: event
          in: path
          description: event that needs to be filtered
          required: true
          schema:
            type: string
            example: "enterprise/hospital/pulse_oximeter"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/EventResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /registration/event/data-app/{data-app}:
    delete:
      tags:
        - registrations
      summary: delete all publish/subscribe events by data-app
      description: |-
        unregister all publish/subscribe events by data-app
      operationId: deleteEventbyDataApp
      parameters:
        - name: data-app
          in: path
          description: action app that needs to be filtered
          required: true
          schema:
            type: string
            example: https://data-app-1
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiEventsResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - registrations
      summary: get all publish/subscribe events by data-app
      description: get all publish/subscribe events by data-app
      operationId: getEventbyDataApp
      parameters:
        - name: data-app
          in: path
          description: action app that needs to be filtered
          required: true
          schema:
            type: string
            example: https://data-app-1
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiEventsResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /registration/event/id/{id}:
    delete:
      tags:
        - registrations
      summary: delete all publish/subscribe events by object id
      description: unregister all publish/subscribe events by id
      operationId: deleteEventbyID
      parameters:
        - name: id
          in: path
          description: object id that needs to be filtered
          required: true
          schema:
            type: string
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiEventsResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - registrations
      summary: get all publish/subscribe events by object id
      description: get all publish/subscribe events by object id
      operationId: getEventbyID
      parameters:
        - name: id
          in: path
          description: object id that needs to be filtered
          required: true
          schema:
            type: string
            example: 12345678-1234-5678-1234-56789abcdef4
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiEventsResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /registration/property:
    post:
      tags:
        - registrations
      summary: Register an property
      description: |-
        Register an property for use in action APIs
      operationId: registerProperty
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyRegistration'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyRegistrationResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    put:
      tags:
        - registrations
      summary: Update an property registration
      description: |-
        Update an existing property registration
      operationId: updatePropertyRegistration
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyRegistration'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyRegistrationResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    delete:
      tags:
        - registrations
      summary: Delete an property registration
      description: Delete an property registration
      operationId: deletePropertyRegistration
      parameters:
        - name: propertyname
          in: query
          description: property name that needs to be filtered
          required: false
          explode: false
          schema:
            type: string
            example: "temperature"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyRegistrationResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - registrations
      summary: list registered properties
      description: |-
        get a registered property by name of get all 
        properties if no names supplied.
      operationId: getPropertyRegistration
      parameters:
        - name: propertyname
          in: query
          description: property name that needs to be filtered
          required: false
          explode: true
          schema:
            type: string
            example: "temperature"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/MultiPropertyRegistrationResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /registration/property/{propertyname}:
    delete:
      tags:
        - registrations
      summary: delete an property registration by name
      description: delete an property registration by name
      operationId: deletePropertyRegistrationbyName
      parameters:
        - name: propertyname
          in: path
          description: property that needs to be filtered
          required: true
          schema:
            type: string
            example: "temperature"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyRegistrationResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

    get:
      tags:
        - registrations
      summary: get an property registration by name
      description: get an property registration by name
      operationId: getAttirbuteRegistrationbyName
      parameters:
        - name: propertyname
          in: path
          description: property that needs to be filtered
          required: true
          schema:
            type: string
            example: "temperature"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyRegistrationResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'
                
  /registration/property/file:
    post:
      tags:
        - registrations
      summary: Register and upload a file for later use
      description: Register and upload a file for later use
      operationId: registerFile
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/File'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

### Extensions

  /extension/property/write/file:
    post:
      tags:
        - extensions
      summary: Write a file to an property across multiple writes
      description: |-
        Write a file to an property across multiple writes
      operationId: WriteFile
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyFile'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /extension/property/write/blob:
    post:
      tags:
        - extensions
      summary: |-
        Write a binary blob to an property across multiple writes
      description: |-
        Write a binary blob to an property across multiple writes
      operationId: WriteBlob
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyBlob'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SuccessResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /extension/property/read/conditional:
    post:
      tags:
        - extensions
      summary: |-
        Read a value from property on a device until it matches a
        specific value.
      description: |-
        Read a value from property on a device until it matches a
        specific value.
      operationId: ReadCond
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/PropertyConditional'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PropertyValueResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

  /extension/property/firmware:
    post:
      tags:
        - extensions
      summary: Write firmware to a device
      description: |-
        Write a file to an property across multiple writes
      operationId: WriteFirmware
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Firmware'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FirmwareResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'
                
    get:
      tags:
        - extensions
      summary: get the status of a firmware upgrade
      description: get the status of a firmware upgrade
      operationId: getFirmwareStatus
      parameters:
        - name: id
          in: query
          description: device id that needs to be filtered
          required: true
          schema:
            type: string
            example: "12345678-1234-5678-1234-56789abcdef4"
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FirmwareResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'
                
  /extension/bulk:
    post:
      tags:
        - extensions
      summary: Compound operations on a device
      description: Compound operations on a device
      operationId: Bulk
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Bulk'
        required: true
      responses:
        '200':
          description: Success
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/BulkResponse'
        '400':
          description: Bad request
        '401':
          description: Unauthorized
        '405':
          description: Invalid request
        '500':
          description: Server-side failure
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/FailureResponse'

components:
  schemas:
# BLE objects
##  An array for BLE services
    BLEServiceslist:
      required:
        - services
      type: object
      properties:
        ble:
          type: array
          items:
            $ref: '#/components/schemas/BLEService'

## A BLE service with its characteristics
    BLEService:
      required:
        - serviceID
        - characteristics
      type: object
      properties:
        serviceID:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4
        characteristics:
          type: array
          items:
            $ref: '#/components/schemas/BLECharacteristic'

## A BLE characteristics with its descriptors
    BLECharacteristic:
      required:
        - characteristicID
        - flags
        - descriptors
      type: object
      properties:
        characteristicID:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4
        flags:
          type: array
          example:
          - read
          - write
          items:
            type: string
            enum:
              - read
              - write
              - notify
        descriptors:
          type: array
          items:
            $ref: '#/components/schemas/BLEDescriptor'

## A BLE descriptor
    BLEDescriptor:
      required:
        - descriptorID
      type: object
      properties:
        descriptorID:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4

## BLE service ID only
    BLEServiceID:
      type: object
      properties:
        serviceID:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4

## Properties that define a BLE property
    BLEProperties:
      required:
        - ble
      type: object
      properties:
        ble:
          required:
            - serviceID
            - characteristicID
          type: object
          properties:
            serviceID:
              type: string
              format: uuid
              example: 12345678-1234-5678-1234-56789abcdef4
            characteristicID:
              type: string
              format: uuid
              example: 12345678-1234-5678-1234-56789abcdef4
            long:
              type: boolean
              example: false

## Defines different types of BLE events
    BLEEvent:
      required:
        - ble
      type: object
      properties:
        ble:
          oneOf:
            - $ref: '#/components/schemas/BLESubEvent'
            - $ref: '#/components/schemas/BLEConnEvent'
            - $ref: '#/components/schemas/BLEAdvEvent'

## BLE Gatt Event definition
    BLESubEvent:
      required:
        - type
        - serviceID
        - characteristicID
      type: object
      properties:
        type:
          type: string
          example: gatt
          enum:
            - gatt
        serviceID:
          type: string
          example: 12345678-1234-5678-1234-56789abcdef0
        characteristicID:
          type: string
          example: 12345678-1234-5678-1234-56789abcdef1

## BLE Connection event Event definition
    BLEConnEvent:
      required:
        - type
      type: object
      properties:
        type:
          type: string
          example: connection_events
          enum:
            - connection_events

## BLE Advertisement Event definition
    BLEAdvEvent:
      required:
        - type
      type: object
      properties:
        type:
          type: string
          example: advertisements
          enum:
            - advertisements
        filterType:
          type: string
          example: deny
          enum:
            - deny
            - allow
        filters:
          type: array
          items:
            $ref: '#/components/schemas/BLEAdvertisement'

## BLE Advertisement properties
    BLEAdvertisement:
      type: object
      properties:
        adType:
          type: string
          example: ff
        adData:
          type: string
          example: 4c00*

## Properties that define a BLE broadcast
    BLEBroadcast:
      required:
        - ble
      type: object
      properties:
        ble:
          type: object
          required:
            - advertisement
          properties:
            advertisement:
              type: string
              format: byte
              example: AgEaAgoMFv9MABAHch9BsDkgeA==

# Zigbee objects
## An array for Zigbee Endpoints
    ZigbeeEndpointlist:
      required:
        - zigbee
      type: object
      properties:
        zigbee:
          type: array
          items:
            $ref: '#/components/schemas/ZigbeeEndpoint'

## A Zigbee endpoint with its clusters
    ZigbeeEndpoint:
      required:
        - endpointID
        - clusters
      type: object
      properties:
        endpointID:
          type: integer
          format: int32
          example: 10
        clusters:
          type: array
          items:
            $ref: '#/components/schemas/ZigbeeCluster'

## A Zigbee cluster with its properties
    ZigbeeCluster:
      required:
        - clusterID
        - properties
      type: object
      properties:
        clusterID:
          type: integer
          format: int32
          example: 0
        properties:
          type: array
          items:
            $ref: '#/components/schemas/ZigbeeProperty'

## A Zigbee property
    ZigbeeProperty:
      required:
        - propertyID
        - propertyType
      type: object
      properties:
        propertyID:
          type: integer
          format: int32
          example: 1
        propertyType:
          type: integer
          format: int32
          example: 32

## Properties that define a Zigbee property
    ZigbeeProperties:
      required:
        - zigbee
      type: object
      properties:
        zigbee:
          required:
            - endpointID
            - clusterID
            - propertyID
          type: object
          properties:
            endpointID:
              type: integer
              format: int32
              example: 1
            clusterID:
              type: integer
              format: int32
              example: 6
            propertyID:
              type: integer
              format: int32
              example: 16
            type:
              type: integer
              format: int32
              example: 1

## Properties that define a Zigbee broadcast
    ZigbeeBroadcast:
      required:
        - zigbee
      type: object
      properties:
        zigbee:
          required:
            - endpointID
            - clusterID
            - propertyID
            - value
          type: object
          properties:
            endpointID:
              type: integer
              format: int32
              example: 1
            clusterID:
              type: integer
              format: int32
              example: 6
            propertyID:
              type: integer
              format: int32
              example: 16
            type:
              type: integer
              format: int32
              example: 1
            value:
              type: integer
              format: int32
              example: 15

# Common objects
## A SCIM id, can be a  device or a group
    Id:
      required:
        - id
      type: object
      properties:
        id:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4

## A SCIM object, can be a  device or a group
    Object:
      allOf:
        - $ref: '#/components/schemas/Id'
      type: object
      properties:
        type:
          type: string
          example: device
          enum:
            - device
            - group
        technology:
          type: string
          example: ble
          enum:
            - ble
            - zigbee

## A Service is a device with optional service IDs
    Service:
      allOf:
        - $ref: '#/components/schemas/Object'
      type: object
      properties:
        ble:
          type: object
          properties:
            services:
              type: array
              items:
                $ref: '#/components/schemas/BLEServiceID'
            cached:
              description: |-
                If we can cache information, then device doesn't need
                to be rediscovered before every connected.
              type: boolean
              default: false
            cacheIdlePurge:
              description: cache expiry period, when device allows
              type: integer
              example: 3600 # default 1 hour
            autoUpdate:
              description: |-
                autoupdate services if device supports it (default)
              type: boolean
              example: true
            bonding: #optional, by default defined in SCIM object 
              type: string
              example: default
              enum:
                - default 
                - none
                - justworks
                - passkey
                - oob

## A Connection
    Connection:
      allOf:
        - $ref: '#/components/schemas/Service'
      type: object
      properties:
        retries:
          type: integer
          format: int32
          example: 3
        retryMultipleAPs:
          type: boolean
          example: true

## A specific property of an Device
    PropertyRaw:
      allOf:
        - $ref: '#/components/schemas/Object'
      oneOf:
        - $ref: '#/components/schemas/BLEProperties'
        - $ref: '#/components/schemas/ZigbeeProperties'
      discriminator:
        propertyName: technology
        mapping:
          ble: '#/components/schemas/BLEProperties'
          zigbee: '#/components/schemas/ZigbeeProperties'

## A value of an property of an Device
    PropertyValueRaw:
      allOf:
        - $ref: '#/components/schemas/PropertyRaw'
      required:
        - value
      type: object
      properties:
        value:
          type: string
          format: byte
          example: 0001
        forcedResponse:
          description: do or do not wait for a response?
          type: boolean
          example: true
        
## An property ID
    PropertyID:
      required:
        - propertyID
      type: object
      properties:
        propertyID:
          type: string
          example: "temperature"
          
## A specific property of an Device
    Property:
      allOf:
        - $ref: '#/components/schemas/Object'
        - $ref: '#/components/schemas/PropertyID'

## A value of an property of an Device
    PropertyValue:
      allOf:
        - $ref: '#/components/schemas/Property'
      required:
        - value
      type: object
      properties:
        value:
          type: string
          format: byte
          example: 0001
        forcedResponse:
          description: do or do not wait for a response?
          type: boolean
          example: true
          
## An property registration
    PropertyRegistration:
      allOf:
        - $ref: '#/components/schemas/PropertyID'
      oneOf:
        - $ref: '#/components/schemas/BLEProperties'
        - $ref: '#/components/schemas/ZigbeeProperties'
      discriminator:
        propertyName: technology
        mapping:
          ble: '#/components/schemas/BLEProperties'
          zigbee: '#/components/schemas/ZigbeeProperties'

## A file-based property of an Device
    PropertyFile:
      allOf:
        - $ref: '#/components/schemas/Property'
      type: object
      properties:
        chunksize:
          type: integer
        forcedResponse:
          description: do or do not wait for a response?
          type: boolean
          example: true

## A binary blob-based property of an Device
    PropertyBlob:
      allOf:
        - $ref: '#/components/schemas/Property'
      required:
        - blob
      type: object
      properties:
        blob:
          type: string
          format: binary
        chunksize:
          type: integer
        forcedResponse:
          description: do or do not wait for a response?
          type: boolean
          example: true

## Conditional read of a value (read until specific value is read)
    PropertyConditional:
      allOf:
        - $ref: '#/components/schemas/Property'
      required:
        - value
      type: object
      properties:
        value:
          type: string
          format: byte
          example: 0001
        maxTime:
          description: |-
            maximum time the conditional read should run in seconds
            (default 10 sec, max 60 sec)
          type: integer
        maxRepeat:
          description: |-
           maximum time the conditional read should repeat
           (default 5, max 60)
          type: integer
        frequency:
          description: |-
            time between reads in seconds (default 1, max 60)
          type: integer

## A subscription property of an Device
    SubscriptionRaw:
      allOf:
        - $ref: '#/components/schemas/PropertyRaw'
      type: object
      properties:
        forcedAck:
          description: |-
            When not looking at device/property support MUST we
            ackhnowledge?
          type: boolean
          example: true

## A specific property of an Device
    Subscription:
      allOf:
        - $ref: '#/components/schemas/Object'
        - $ref: '#/components/schemas/PropertyID'
      type: object
      properties:
        forcedAck:
          description: |-
            When not looking at device/property support MUST we
            ackhnowledge?
          type: boolean
          example: true

## A broadcast
    Broadcast:
      allOf:
        - $ref: '#/components/schemas/Object'
      oneOf:
        - $ref: '#/components/schemas/BLEBroadcast'
        - $ref: '#/components/schemas/ZigbeeBroadcast'
      discriminator:
        propertyName: technology
        mapping:
          ble: '#/components/schemas/BLEBroadcast'
          zigbee: '#/components/schemas/ZigbeeBroadcast'
      required:
        - cycle
      type: object
      properties:
        cycle:
          type: string
          example: single
          enum:
            - single
            - repeat
        # broadcast time in ms
        broadcastTime:
          type: integer
          example: 3000
        # interval between broadcasts in ms
        broadcastInterval:
          type: integer
          example: 500
        # optional external broker config
        mqtt:
          type: object

## Event Name
    EventName:
      required:
        - event
      type: object
      properties:
        event:
          type: string
          example: enterprise/hospital/pulse_oximeter

## DataStream Event
    Event:
      allOf:
        - $ref: '#/components/schemas/EventName'  
        - $ref: '#/components/schemas/PropertyID'
      oneOf:
        - $ref: '#/components/schemas/BLEEvent'
        - $ref: '#/components/schemas/ZigbeeProperties'
      discriminator:
        propertyName: technology
        mapping:
          ble: '#/components/schemas/BLEEvent'
          zigbee: '#/components/schemas/ZigbeeProperties'
      type: object
      properties:
        eventFormat:
          description: |-
            How is information decorated?  Default: device
            and property ids.
          type: string
          example: default
          enum:
            - default
            - payload
        replay:
          type: boolean
          example: false
          default: false
        id:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4
        type:
          type: string
          example: device
          enum:
            - device
            - group
        dataApps:
          type: array
          items:
            type: object
            properties:
              dataAppID:
                type: string
                format: uuid
                example: 12345678-1234-5678-1234-56789abcdef4
              mqtt:
                type: object
                properties: 
                  brokerURI: 
                    type: string
                    example: mqtt.broker.com:8883
                  username:
                    type: string
                    example: user1
                  password: 
                    type: string
                    example: password1
                  brokerCACert: 
                    type: string
        technology:
          type: string
          example: ble
          enum:
            - ble
            - zigbee

## FileURL
    FileURL:
      required:
        - fileURL
      type: object
      properties:
        fileURL:
          type: string
          example: "https://domain.com/firmware.dat"
          
## FileBinary        
    FileBin:
      required:
        - fileBin
      type: object
      properties:
        fileBin:
          type: string
          format: binary
          example: "firmware.dat"

## File
    File:
      allOf:
        - $ref: '#/components/schemas/PropertyID'
      oneOf:
        - $ref: '#/components/schemas/FileURL'
        - $ref: '#/components/schemas/FileBin'

## Firmware
    Firmware:
      allOf:
        - $ref: '#/components/schemas/Property'
      type: object
      properties:
        upgradeType:
          type: string
          enum:
            - nordics
            - silabs
            - wiliot

## Defines an operation in a bulk API
    Operation:
      required:
        - operation
      allOf:
        - type: object
          properties:
            path:
              type: string
              enum:
               - /action/connection
               - /action/property
               - /action/property/subscription
               - /extension/property/write/file
               - /extension/property/write/blob
               - /extension/property/read/conditional
            method:
              type: string
              enum:
               - POST
               - DELETE
               - GET
        - oneOf:
            - $ref: '#/components/schemas/Object'
            - $ref: '#/components/schemas/Property'
            - $ref: '#/components/schemas/PropertyValue'
            - $ref: '#/components/schemas/PropertyConditional'
            - $ref: '#/components/schemas/PropertyFile'
            - $ref: '#/components/schemas/PropertyBlob'
            - $ref: '#/components/schemas/Subscription'
          discriminator:
            propertyName: operation
            mapping:
              POST /action/connection:
                '#/components/schemas/Service'
              DELETE /action/connection:
                '#/components/schemas/Object'
              GET /action/connection:
                '#/components/schemas/Object'
              POST /action/property:
                '#/components/schemas/PropertyValue'
              DELETE /action/property:
                '#/components/schemas/Property'
              GET /action/property:
                '#/components/schemas/Property'
              POST /action/property/Subscription:
                '#/components/schemas/Subscription'
              DELETE /action/property/Subscription:
                '#/components/schemas/Subscription'
              GET /action/property/Subscription:
                '#/components/schemas/Subscription'
              POST /extension/property/read/conditional:
                '#/components/schemas/PropertyConditional'
              POST /extension/property/write/file:
                '#/components/schemas/PropertyFile'
              POST /extension/property/write/blob:
                '#/components/schemas/PropertyBlob'

## Bulk schema
    Bulk:
      allOf:
        - $ref: '#/components/schemas/Object'
      type: object
      properties:
        autoDisconnect:
          description: |-
            do we automatically disconnect after a RESTful operation?
          type: boolean
          example: true
          default: true
        operations:
          type: array
          items:
            $ref: '#/components/schemas/Operation'

# responses
## Baseline success reponse
    Success:
      required:
        - status
      type: object
      properties:
        status:
          type: string
          example: SUCCESS
          enum:
            - SUCCESS
        requestID:
          type: string
          example: 12345678-5678-1234-5578-abcdef1234

    SuccessResponse:
      allOf:
        - $ref: '#/components/schemas/Success'
      type: object
      properties:
        id:
          type: string
          format: uuid
          example: 12345678-1234-5678-1234-56789abcdef4

## Error 500 application Failure response
    FailureResponse:
      required:
        - status
        - errorCode
      type: object
      properties:
        status:
          type: string
          example: FAILURE
          enum:
            - FAILURE
        reason:
          type: string
          example: Not Found
        errorCode:
          type: integer
          format: int32
          example: 12
        requestID:
          type: string
          example: 12345678-5678-1234-5578-abcdef1234

## Response, success or failure
    Response:
      oneOf:
        - $ref: '#/components/schemas/SuccessResponse'
        - $ref: '#/components/schemas/FailureResponse'

 ## Returns discovered services
    PropertyResponse:
      allOf:
        - $ref: '#/components/schemas/SuccessResponse'
      oneOf:
        - $ref: '#/components/schemas/BLEServiceslist'
        - $ref: '#/components/schemas/ZigbeeEndpointlist'

## Response to multiple connections
    MultiConnectionsResponse:
      allOf:
        - $ref: '#/components/schemas/Success'
      required:
        - connections
      type: object
      properties:
        connections:
          type: array
          items:
            $ref: '#/components/schemas/Response'

## Returns an property value
    PropertyValueResponseRaw:
      allOf:
        - $ref: '#/components/schemas/SuccessResponse'
      required:
       - value
      type: object
      properties:
        value:
          type: string
          example: 01
          format: byte
          
## Returns an property value with ID
    PropertyValueResponse:
      allOf:
        - $ref: '#/components/schemas/SuccessResponse'
        - $ref: '#/components/schemas/PropertyID'
      required:
       - value
      type: object
      properties:
        value:
          type: string
          example: 01
          format: byte

## Returns an property registration
    PropertyRegistrationResponse:
      allOf:
        - $ref: '#/components/schemas/Success'
        - $ref: '#/components/schemas/PropertyRegistration'
        
## Returning multiple property registrations
    MultiPropertyRegistrationResponse:
      allOf:
        - $ref: '#/components/schemas/Success'
      required:
        - properties
      type: object
      properties:
        properties:
          type: array
          items:
            $ref: '#/components/schemas/PropertyRegistration'

## Returns a event
    EventResponse:
      allOf:
        - $ref: '#/components/schemas/SuccessResponse'
        - $ref: '#/components/schemas/Event'

## Returning multiple events
    MultiEventsResponse:
      allOf:
        - $ref: '#/components/schemas/Success'
      required:
        - events
      type: object
      properties:
        events:
          type: array
          items:
            $ref: '#/components/schemas/Event'

## Returning multiple subscriptions
    MultiSubscriptionResponse:
      allOf:
        - $ref: '#/components/schemas/Success'
      required:
        - subscriptions
      type: object
      properties:
        subscriptions:
          type: array
          items:
            $ref: '#/components/schemas/Subscription'

## Multiple returns for a bulk operation
    BulkResponse:
      allOf:
        - $ref: '#/components/schemas/SuccessResponse'
      type: object
      properties:
        operations:
          type: array
          items:
            $ref: '#/components/schemas/OperationResponse'

## Return ofr a firmware upgrade operation
    FirmwareResponse:
      allOf:
        - $ref: '#/components/schemas/SuccessResponse'
      type: object
      properties:
        upgradeStatus:
          type: string
          enum:
            - completed
            - in-progress
            - rolled-back
            - failed

## Return for an operation
    OperationResponse:
      required:
        - operation
      allOf:
        - type: object
          properties:
            operation:
              type: string
              enum:
               - /action/connection
               - /action/property
               - /action/property/subscription
               - /extension/property/write/file
               - /extension/property/write/blob
               - /extension/property/read/conditional
            type:  
              type: string
              enum:
               - POST
               - DELETE
               - GET
        - oneOf:
            - $ref: '#/components/schemas/SuccessResponse'
            - $ref: '#/components/schemas/PropertyResponse'
            - $ref: '#/components/schemas/PropertyValueResponse'
          discriminator:
            propertyName: operation
            mapping:
              POST /action/connection:
                '#/components/schemas/ServiceResponse'
              DELETE /action/connection:
                '#/components/schemas/SuccessResponse'
              GET /action/connection:
                '#/components/schemas/SuccessResponse'
              POST /action/property:
                '#/components/schemas/PropertyValueResponse'
              DELETE /action/property:
                '#/components/schemas/PropertyValueResponse'
              GET /action/property:
                '#/components/schemas/PropertyValueResponse'
              POST /action/property/Subscription:
                '#/components/schemas/SuccessResponse'
              DELETE /action/property/Subscription:
                '#/components/schemas/SuccessResponse'
              GET /action/property/Subscription:
                '#/components/schemas/SuccessResponse'
              POST /extension/property/read/conditional:
                '#/components/schemas/PropertyValueResponse'
              POST /extension/property/write/file:
                '#/components/schemas/SuccessResponse'
              POST /extension/property/write/blob:
                '#/components/schemas/SuccessResponse'

 # API key authorization
  securitySchemes:
    ApiKeyAuth:
      type: apiKey
      in: header
      name: X-API-KEY
# Apply the API key globally to all operations
security:
  - ApiKeyAuth: []
<CODE ENDS>
]]></artwork></figure>

</section>


  </back>

<!-- ##markdown-source:
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
WgBg4bCscs5Ara2iie2ZMw9N86oB30QelcBedd29aoDFCRt1mx+3TeleUr7O
oxycqw3DqTrJ10O6uhyPL1Tgs7pLQ7d2l4I9xjROTZvK6c1qF7yhPfD+4ojv
4OyK35wdGmqQTojE2Z+Ry0kSzuhMRj2u+i0luG8JVreYjqWFWPUQ8oaF8Z0B
eoTGuuS7DeJCbusb1rcn06SQf82+xIR1tQ0dG/CR5u5GHBWqwIG7O32uxNlA
DOD1XPViPPVmnZrt8d/L0myEoif9PPsk848fjhEYvu7xE7zTee/FixePneLq
LZC/OdIYfou/77ovJ8DgeKUFvtS/ex8w4IP9A6Bs/IjPivC3T1FB3QKvquJA
wXLLz7XqjSYiqDhL/Ey7LIp8zWG39lyiAkMSE31Linv0NeLCglL0oQE6XOXF
SwqPqcxZFdpbASQ8wBsKc3sZUMwlUxojD5H1/obH8lFYju8s1LsriRad3XxV
7rOsXeM9QZeQl9qRxJFiRWv1EFjL+O1cr1xQfR42ncU6VEdmODP2wFE7Q/XV
bTFaIDRJBPfiKzuo+Vl+zljTZa6osZydota6YPHJWlJ5mFrHspbXo1XDRMkU
09nWTjVi152XMwymtHJmkFvV9ApLzp4pHIJ/f1pCi1ae53QKKl9VhN0Rn9tg
CpEss59bVDzxTV7ac4q88qVENudmtBXMldhmODcdg8bCTbIj7IGL9jJeZ1gU
w3dOWqnnfZTK1TbazxaWvm7ttNE2l9Y2zUmzRrpq3nd/hbntn1eXiXWV2dXq
so1OuUU65UfX3rF35FfcLfTiHGf0C25yBEhMoRv3bXX3zZbGbXy3u6dNq4dx
aPSNwKzTRx+vuil555JnLu/SiRr1os0Gt7JGnHfZp9y4lHdd/f9s2v/MR+YI
k4vuJWeT1qsm9EGBQTW53DGTqZ3x0b2lLmyqK2k3ruxG+d5h5TunhvxGfGyc
123ws38O/b7Rs/9EenZFNfvD6qCWSAVXyqAWOvum4mkp2K7/7zn6PaEP6tM3
S9buu8HDBLrmMIHAuX8aT5rEY2jt+TBcsEvHe9Nlo+51leYOCveUgf26ORMW
VdtFGVUsqwp9hZM+gUz5QYbRzSXUdpbqhAPH4LFWUoCHDLCkp5oVL0qPJQQ3
ZdWo2dXsBVdXtunLS+nMS+tN0vz2ZJMVrS22PuZWr1q4zUYZva8bZvR4RWPR
w7Bj0Lmm25xTxtY37poNvJWNvIWGHqN7gbHndNtm8NGiB9Xf/mJxWCtTDhw6
MdStLvbyCFxfJEhY3HWJlO8bpOfPXNvVpZ5d941ayd0NlW6odBUqDRpPVGrx
BupaorEg/rKeQJsjULd1tdrn0/h0kHATG9zEBjc+y8ZnWXqrq+tJEOsX9WL6
hY5KA6yNV3I5r0RV0m8ck41jop5vTL6NY7Kh0n8GKm1wTFAdNDsmjYpi45ts
fJONb7LxTW6jb2LPt5i3A9KcJSGEh5O1dkLaM3HNxfV8o+p8hFIlBvGAvdOP
3gAUvFOgfZOhPTqits3QfWU3GrqPK/sJnTfujsJGLLZtKnQOBZ6zrbDlIMiG
aWnaWkSTS1WtOmDx7pZuwxU6rkNmX+pDH+Zs2ms5w2PBQRtNl3ytbM9c9raS
LbzwSdtyQb2yAeaJ05i7Xa3tdI/LS3BifhLfGUvwpqM49lvuQprHdNC8U+E8
7KbGfLey3qq2Hf0mDrO6Q8Q+d7dM42lZV1/M02Am3wF2+tG7JRoUVG3DRIt+
qmnWn1k7LTyQ+C5wK0xyo5pumWqK09ZTdTeqaQli36imO6Wa0Cmr6ZNKZZ7D
qXMq/1q0lin+W6UXL9tmW1bybbZFNecWVHJu3t3ni3Nurmi6grybE4mykDtu
9s0hVWqylObt1k+krCtjUxp489Iulssk4ta/T/PyIq9J7FHkeolkxU+ViFk0
zOYSoTZx3kguNxWKd4inGsZ1JYQKyZtx3syoNuplveqMdTRMY9VGi5Lhbm5e
z4irVTQNh5VfXs+IK1Q0YqGqufkzzDfa5hZoGyCLNm0z7wz4jcLZKJzlFQ4f
m3r0pZRpEffjJEY9Qc/oulh+nPCV3xeZuAhneOMpouGkEszaE+/kRS3ERdKf
4ETcFeFKHaSKKMB0eAoN0yztHp+Y9gVh+uRYj4EOV/X/FlQWgYf4g0KZ0D2z
KCPlmIr/YLr9sIA1oJNboaPKUhcxcFI85FJDRI9J2PGhqE7iuwcT5qwaT80O
ARYM17RoTQTynM25sRopBkuaUgInLElNLBv16DJz5JE/k+wi7iD6Dc2Fvni3
7bQ0YA00fw0BNl2+a5HcEUUGmG9Av9ba+sxbVt1mBbMpXQMwOJfjUICMT0dI
TSy9WOR1hY2lavH4zf72B5yV/VM1wZm6EqSxIaOh1lZhZ1Frj0hrQPzXrixz
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
EPwP/QRf6YAYmQLo78H/B6AVXYK7IgIA

-->

</rfc>

