Web Thing Protocol

WebSocket Sub-protocol

This document defines a WebSocket sub-protocol called the Web Thing Protocol, for monitoring and controlling connected devices over the World Wide Web. The Web Thing Protocol is intended as a dedicated real-time protocol for the Web of Things, to enable a WoT Consumer to communicate with one or more WoT Things over a WebSocket connection.

Introduction

This document defines a WebSocket [[WEBSOCKETS-PROTOCOL]] sub-protocol for monitoring and controlling connected devices over the Web.

The Web of Things (WoT) is a collection of standardised technology building blocks that help provide interoperability on the Internet of Things (IoT). The WoT Thing Description specification [[wot-thing-description11]] defines a metadata format for describing the capabilities of "Things" (connected devices) on the Web. The WoT Discovery specification [[wot-discovery]] defines mechanisms for discovering Things on the Web. This specification complements those building blocks by defining a dedicated real-time protocol for communicating with Things over the Web.

WebSockets [[WEBSOCKETS-PROTOCOL]] provide a way to upgrade a standard HTTP [[HTTP11]] request to a full-duplex, persistent, real-time communication channel over a single TCP connection. This can be used to create a versatile and efficient two-way channel with which a WoT Consumer can communicate with one or more Things [[wot-architecture11]] to carry out the full set of WoT operations. However, since a WebSocket is essentially just a raw TCP socket with no semantics of its own, a sub-protocol needs to be defined in order for a Consumer and Thing to communicate.

Whilst many other WebSocket sub-protocols exist, what makes the Web Thing Protocol unique is that it is specifically designed around the Web of Things information model and set of operations [[wot-thing-description11]], as well as being targeted specifically at Web of Things use cases [[wot-usecases]]. It can therefore be thought of as being native to the Web of Things.

The sub-protocol defines message payload formats for each of the well-known operation types defined in the WoT interaction model [[wot-architecture11]], and other messages needed for WebSocket communication.

This specification is intended to complement deliverables of the WoT Working Group, including WoT Architecture [[wot-architecture11]], WoT Thing Description [[wot-thing-description11]], WoT Discovery [[wot-discovery]], WoT Binding Templates [[wot-binding-templates]] and WoT Profile [[wot-profile]]. It is intended to implement use cases and requirements defined in the Web Thing Protocol Use Cases & Requirements community report.

Whilst this document is not on a standards track, the Web Thing Protocol is intended to eventually join a standards track at the W3C or another standards body such as the IETF.

Terminology

Fundamental WoT terminology such as Thing or Web Thing, Consumer or WoT Consumer, WoT Thing Description or Thing Description, Interaction Model, Interaction Affordance, Property, Action and Event are defined in the Terminology section of the WoT Architecture specification [[wot-architecture11]].

WebSocket Connection

Protocol Handshake

In order to communicate with a Web Thing, a WoT Consumer [[wot-architecture11]] MUST locate one or more WebSocket [[WEBSOCKETS-PROTOCOL]] endpoints provided by the Thing for a given set of Interaction Affordances [[wot-thing-description11]].

The URL of a WebSocket endpoint to be used for a given interaction MUST be obtained from a Thing Description [[wot-architecture11]] by locating a Form inside the corresponding Interaction Affordance for which:

To open a WebSocket on a Thing, an HTTP GET request [[RFC9110]] MUST be upgraded to a WebSocket connection using a standard WebSocket protocol handshake [[WEBSOCKETS-PROTOCOL]], specifying the "webthingprotocol" sub-protocol.

        GET wss://mythingserver.com/things/robot
        Host: mythingserver.com
        Origin: https://mythingserver.com
        Upgrade: websocket
        Connection: Upgrade
        Sec-WebSocket-Key: x3JJHMbDL1EzLkh9GBhXDw==
        Sec-WebSocket-Protocol: webthingprotocol
        Sec-WebSocket-Version: 13
      
        HTTP/1.1 101 Switching Protocols
        Upgrade: websocket
        Connection: Upgrade
        Sec-WebSocket-Accept: HSmrc0sMlYUkAGmm5OPpG2HaGWk=
        Sec-WebSocket-Protocol: webthingprotocol        
      

Sub-protocol name to be confirmed, see IANA Considerations.

A WebSocket can be opened from a web page using the JavaScript WebSocket API [[WEBSOCKETS-API]] which will take care of the handshake detailed above and allow messages to be sent and received.

        const socket = new WebSocket('wss://mywebthingserver/things/robot', 'webthingprotocol');
      

WebSocket Re-use

A single WebSocket [[WEBSOCKETS-PROTOCOL]] connection from a WoT Consumer MAY be shared between multiple Interaction Affordances of a Thing. A single WebSocket connection from a WoT Consumer MAY also be shared between multiple Things.

Before opening a new WebSocket connection, a WoT Consumer SHOULD check whether it already has an open connection to the same WebSocket endpoint URL.

If an existing connection to the same WebSocket endpoint URL exists, then that connection SHOULD be re-used rather than opening an additional socket.

If an existing connection to the same WebSocket endpoint URL exists but is using a different set of credentials for its given SecurityScheme [[wot-thing-description11]] (e.g. a different Bearer Token), then the WoT Consumer MUST NOT re-use the connection.

WebSocket Messages

All messages MUST be a JSON object [[JSON]].

The top level JSON object MUST contain a thingID member with the value set to a unique identifier of the Web Thing to which the message relates. If the Thing Description of the Web Thing contains an id member then the value of that id member MUST be used as the unique identifier assigned to thingID. If the Thing Description of the Web Thing does not contain an id member then the URL [[URL]] from which the Thing Description was retrieved MAY be used as the thingID value instead. The value of the thingID member MUST be a valid URI [[URI]] serialised as a string.

The top level JSON object MUST contain a messageID member with the value set to a unique identifier for the current message in UUIDv4 format [[rfc9562]].

The top level JSON object MAY contain a correlationID member which provides a unique identifier in UUIDv4 format [[rfc9562]] which is shared between messages corresponding to the same WoT operation (e.g. a property read request and response, or an event subscription request and event notification).

Common members of all messages
Member Type Assignment Description
thingID string Mandatory The ID (URI) of the Thing to which the Property belongs.
messageID string Mandatory A unique identifier (UUID) for the current message.
messageType string Mandatory A string which denotes the type of message, with a value from the WebSocket message types table below.
correlationID string Optional A unique identifer (UUID) which is shared between messages corresponding to the same operation, e.g. a request and a response.

The top level JSON object MUST contain a messageType member, with its value set to one of the message type strings from the following table:

WebSocket message types
Message type Description Entity Direction
readProperty Request a property reading from a Thing PropertyAffordance Consumer ➡ Thing
propertyReading A property reading from a Thing PropertyAffordance Thing ➡ Consumer

All date and time values MUST use the date-time format defined in [[RFC3339]].

      2025-01-15T12:08:00.42Z
    

In order to reduce ambiguity, RFC 3339 only permits an hour with a value between 00 and 23 (not 24), and time zones expressed as a numerical offset relative to UTC. The suffix "Z" when applied to a time denotes a UTC offset of 00:00.

Properties

The following sections define WebSocket message payload formats for reading, writing and observing Properties of Things.

readProperty

To request a property reading from a Thing, a Consumer MUST send a message to the Thing which contains the following members:

Members of a readProperty message
Member Type Assignment Description
messageType string "readProperty" A string which denotes that this message is requesting a readproperty operation.
name string Mandatory The name of the Property to read, as per its key in the properties member of the Thing Description.
          {
            "thingID": "https://mythingserver.com/things/mylamp1",
            "messageID": "c370da58-69ae-4e83-bb5a-ac6cfb2fed54",
            "messageType": "readProperty",
            "name": "on",
            "correlationID": "5afb752f-8be0-4a3c-8108-1327a6009cbd"
          }
        

When a Thing receives a readProperty message from a Consumer, then upon successfully reading the value of the corresponding property it MUST send a propertyReading message in response, containing its current value.

propertyReading

To notify a Consumer of the value of a Property, a Thing MUST send a message to the Consumer which contains the following members:

Members of a propertyReading message
Member Type Assignment Description
messageType string "propertyReading" A string which denotes that this message is notifying a Consumer of the value of a Property.
name string Mandatory The name of the Property being read, as per its key in the properties member of the Thing Description.
value any Mandatory The current value of the Property being read, with a format conforming to the data schema of the corresponding PropertyAffordance in the Thing Description.
timestamp string Optional A timestamp in date-time format [[RFC3339]] set to the time the property reading took place.

If a propertyReading message is sent in response to a readProperty, readAllProperties, observeProperty or observeAllProperties message which contained a correlatonID member, then the response message SHOULD also include a correlationID member with the same value.

          {
            "thingID": "https://mythingserver.com/things/mylamp1",
            "messageID": "79057736-3e0e-4dc3-b139-a33051901ee2",
            "messageType": "propertyReading",
            "name": "on",
            "value": true,
            "timestamp": "2024-01-13T23:20:50.52Z",
            "correlationID": "5afb752f-8be0-4a3c-8108-1327a6009cbd"
          }
        

Actions

Events

Other Messages

Example Thing Descriptions

Privacy Considerations

Security Considerations

Accessibility Considerations

IANA Considerations

This specification proposes the registration of a sub-protocol in the IANA "WebSocket Subprotocol Name Registry". The name of the sub-protocol and the published URL of its definition are to be confirmed, but currently the name "webthingprotocol" and this document are used as a placeholder and draft proposal.

Subprotocol Identifier
webthingprotocol
Subprotocol Common Name
Web Thing Protocol
Subprotocol Definition
This document.