diff --git a/src/constants.ts b/src/constants.ts index aca3f60c5..1d3216b08 100644 --- a/src/constants.ts +++ b/src/constants.ts @@ -82,6 +82,11 @@ export enum LogSeverity { PROMPT = 4, } +export enum WoTOperation { + READ_ALL_PROPERTIES_OP = 'readallproperties', + SUBSCRIBE_ALL_EVENTS_OP = 'subscribeallevents', + UNSUBSCRIBE_ALL_EVENTS_OP = 'unsubscribeallevents', +} export interface LogMessage { severity: LogSeverity; message: string; diff --git a/src/models/thing.ts b/src/models/thing.ts index 38882db91..64522a85e 100644 --- a/src/models/thing.ts +++ b/src/models/thing.ts @@ -141,6 +141,7 @@ export default class Thing extends EventEmitter { this.events = description.events || {}; this.connected = false; this.eventsDispatched = []; + this.forms = []; if (description.properties) { for (const propertyName in description.properties) { @@ -172,14 +173,28 @@ export default class Thing extends EventEmitter { this.properties[propertyName] = property; } + + // If there are properties, add a top level form for them + if (Object.keys(description.properties).length > 0) { + this.forms.push({ + href: `${this.href}/properties`, + op: Constants.WoTOperation.READ_ALL_PROPERTIES_OP, + }); + } + } + + // If there are events, add a top level form for them + if (Object.keys(description.events ?? {}).length > 0) { + this.forms.push({ + href: `${this.href}/events`, + op: [ + Constants.WoTOperation.SUBSCRIBE_ALL_EVENTS_OP, + Constants.WoTOperation.UNSUBSCRIBE_ALL_EVENTS_OP, + ], + subprotocol: 'sse', + }); } - this.forms = [ - { - href: `${this.href}/properties`, - op: ['readallproperties', 'writeallproperties'], - }, - ]; this.floorplanVisibility = description.floorplanVisibility; this.floorplanX = description.floorplanX; this.floorplanY = description.floorplanY; @@ -190,10 +205,6 @@ export default class Thing extends EventEmitter { rel: 'actions', href: `${this.href}/actions`, }, - { - rel: 'events', - href: `${this.href}/events`, - }, ]; const uiLink = { @@ -281,6 +292,7 @@ export default class Thing extends EventEmitter { // Give the event a URL event.forms.push({ href: `${this.href}${Constants.EVENTS_PATH}/${encodeURIComponent(eventName)}`, + subprotocol: 'sse', }); } @@ -668,7 +680,7 @@ export default class Thing extends EventEmitter { // Update description this.description = description.description || ''; - + this.forms = []; // Update properties this.properties = {}; if (description.properties) { @@ -700,6 +712,14 @@ export default class Thing extends EventEmitter { }); this.properties[propertyName] = property; } + + // If there are properties, add a top level form for them + if (Object.keys(description.properties).length > 0) { + this.forms.push({ + href: `${this.href}/properties`, + op: Constants.WoTOperation.READ_ALL_PROPERTIES_OP, + }); + } } // Update actions @@ -756,6 +776,19 @@ export default class Thing extends EventEmitter { // Give the event a URL event.forms.push({ href: `${this.href}${Constants.EVENTS_PATH}/${encodeURIComponent(eventName)}`, + subprotocol: 'sse', + }); + } + + // If there are events, add a top level form for them + if (Object.keys(description.events ?? {}).length > 0) { + this.forms.push({ + href: `${this.href}/events`, + op: [ + Constants.WoTOperation.SUBSCRIBE_ALL_EVENTS_OP, + Constants.WoTOperation.UNSUBSCRIBE_ALL_EVENTS_OP, + ], + subprotocol: 'sse', }); }