Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Quickstart Things #1064

Merged
merged 41 commits into from
Sep 5, 2023
Merged
Show file tree
Hide file tree
Changes from 35 commits
Commits
Show all changes
41 commits
Select commit Hold shift + click to select a range
54d67d1
examples: remove unnecessary instructions
egekorkan Aug 27, 2023
b3a7adf
examples: add presence sensor
egekorkan Aug 27, 2023
f7c3849
examples: add presence sensor implementation
egekorkan Aug 27, 2023
d29f9a4
examples: start coffee machine implementation
egekorkan Aug 27, 2023
3144f50
examples: comment out rejects
egekorkan Aug 27, 2023
58ec343
examples: add readme
egekorkan Aug 27, 2023
c34b53a
examples: adjust consumption rates
egekorkan Aug 27, 2023
4446cdf
examples: start smart clock implementation
egekorkan Aug 27, 2023
35b2c62
add intervals to smart clock
egekorkan Aug 29, 2023
d39efad
examples: fix ts errors for coffee machine
egekorkan Aug 30, 2023
d6daae2
examples: apply lint and format
egekorkan Aug 30, 2023
5fa9363
examples: fix readme linting errors
egekorkan Aug 30, 2023
24a8b44
examples: fix coffee machine behavior
egekorkan Aug 30, 2023
1bd4c5e
examples: prettify
egekorkan Aug 30, 2023
511602d
refactor: remove ts-ignore statements and fix code
danielpeintner Aug 31, 2023
04bf916
examples: remove log statements
egekorkan Aug 31, 2023
74250b2
add synchronous statement to action
egekorkan Aug 31, 2023
d8be7e3
refactor: don't return early
danielpeintner Aug 31, 2023
86def41
Merge branch 'ege-quickstart-things' of https://github.com/egekorkan/…
danielpeintner Aug 31, 2023
487b23b
refactor: promisify timeout
danielpeintner Aug 31, 2023
839a044
examples: add property change emission
egekorkan Aug 31, 2023
d5102a0
examples: lint and format
egekorkan Aug 31, 2023
0f5f323
mqtt: fix binding-mqtt readme
egekorkan Aug 31, 2023
9df4a00
examples: add mqtt binding to examples package.json
egekorkan Aug 31, 2023
67f6b32
examples: change http coap for clock
egekorkan Aug 31, 2023
9952928
examples: adapt sensor to MQTT
egekorkan Aug 31, 2023
afcad16
examples: lint and format
egekorkan Aug 31, 2023
9055272
mqtt: format readme
egekorkan Aug 31, 2023
4aff7d1
mqtt: fix readme
egekorkan Sep 1, 2023
3e35d12
Revert "mqtt: fix binding-mqtt readme"
egekorkan Sep 1, 2023
7c00309
Merge pull request #1066 from eclipse-thingweb/egekorkan-mqtt-readme
egekorkan Sep 2, 2023
3e0335b
examples: change mqtt broker
egekorkan Sep 2, 2023
98767c8
Merge branch 'ege-quickstart-things' of https://github.com/egekorkan/…
relu91 Sep 4, 2023
0ba43cd
chore(examples): fix mqtt dep declarations
relu91 Sep 4, 2023
cf0c6fd
chore(examples): use fixed version for mqtt binding
relu91 Sep 4, 2023
ffb156e
chore(examples): remove commented http server
egekorkan Sep 4, 2023
b5fec33
chore(examples): change water tank min to 0
egekorkan Sep 4, 2023
19d0d84
Revert "examples: remove unnecessary instructions"
egekorkan Sep 4, 2023
9de884f
examples: copy js files to root examples folder
egekorkan Sep 4, 2023
83471af
chore(examples): lint root level examples js files
egekorkan Sep 4, 2023
efcf67b
refactor(examples): remove the Object.defineProperty preamble
relu91 Sep 5, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions packages/binding-mqtt/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ W3C Web of Things (WoT) Protocol Binding for [MQTT](https://en.wikipedia.org/wik
This package uses [mqtt](https://www.npmjs.com/package/mqtt) as a low level library for MQTT.
W3C WoT Binding Template for MQTT can be found [here](https://w3c.github.io/wot-binding-templates/bindings/protocols/mqtt/index.html).

Current Maintainer(s): [@egekorkan](https://github.com/egekorkan) [@hasbel](https://github.com/hasbel) [@sebastiankb](https://github.com/sebastiankb) [@hasanheroglu](https://github.com/hasanheroglu)
Current Maintainer(s): [@egekorkan](https://github.com/egekorkan) [@sebastiankb](https://github.com/sebastiankb) [@hasanheroglu](https://github.com/hasanheroglu)

## Protocol specifier

Expand All @@ -31,7 +31,7 @@ MqttBrokerServer = require("@node-wot/binding-mqtt").MqttBrokerServer;

// create Servient add MQTT binding
let servient = new Servient();
servient.addServer(new MqttBrokerServer("mqtt://test.mosquitto.org"));
servient.addServer(new MqttBrokerServer({ uri: "mqtt://test.mosquitto.org" }));
egekorkan marked this conversation as resolved.
Show resolved Hide resolved

servient.start().then((WoT) => {
var counter = 0;
Expand Down
11 changes: 1 addition & 10 deletions packages/examples/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,16 +14,7 @@ see https://github.com/eclipse-thingweb/node-wot/issues/171.
### Workflow

1. Run `npm run build`
2. Remove the following 3/4 lines in JS files of folder `dist/`

```
Object.defineProperty(exports, "__esModule", { value: true });
require("wot-typescript-definitions");
let WoT;
let WoTHelpers;
```

3. Copy the according JS file(s) to
danielpeintner marked this conversation as resolved.
Show resolved Hide resolved
2. Copy the according JS file(s) to

- `<node-wot>/examples/scripts`
- `<node-wot>/examples/testthing`
Expand Down
1 change: 1 addition & 0 deletions packages/examples/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
"@node-wot/binding-coap": "0.8.8",
"@node-wot/binding-file": "0.8.8",
"@node-wot/binding-http": "0.8.8",
"@node-wot/binding-mqtt": "0.8.8",
"@node-wot/binding-opcua": "0.8.8",
"@node-wot/core": "0.8.8",
"@node-wot/td-tools": "0.8.8",
Expand Down
10 changes: 10 additions & 0 deletions packages/examples/src/quickstart/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Quick Start Things

This set of Things can be used to build mashup applications for a smart home scenario.
These Things are:

- Simple coffee machine that can take an order to brew a coffee.
- Presence sensor that emits an event when a person is detected.
- Smart clock that runs 60 times faster than real time, where 1 hour happens in 1 minute.

These Things are hosted on plugfest.thingweb.io but can be also self-hosted.
64 changes: 64 additions & 0 deletions packages/examples/src/quickstart/presence-sensor.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
/********************************************************************************
* Copyright (c) 2023 Contributors to the Eclipse Foundation
*
* See the NOTICE file(s) distributed with this work for additional
* information regarding copyright ownership.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
* http://www.eclipse.org/legal/epl-2.0, or the W3C Software Notice and
* Document License (2015-05-13) which is available at
* https://www.w3.org/Consortium/Legal/2015/copyright-software-and-document.
*
* SPDX-License-Identifier: EPL-2.0 OR W3C-20150513
********************************************************************************/

// This is an example Thing script which is a simple presence detector
// It fires an event when it detects a person (mocked as every 5 second)

import { Servient } from "@node-wot/core";
import { MqttBrokerServer } from "@node-wot/binding-mqtt";

// create Servient add MQTT binding with port configuration
const servient = new Servient();
servient.addServer(new MqttBrokerServer({ uri: "mqtt://test.mosquitto.org" }));

servient.start().then((WoT) => {
WoT.produce({
title: "PresenceSensor",
description: "Thing that can detect presence of human nearby",
support: "https://github.com/eclipse-thingweb/node-wot/",
"@context": "https://www.w3.org/2022/wot/td/v1.1",
events: {
presenceDetected: {
title: "Presence Detected",
description:
"An event that is emitted when a person is detected in the room. It is mocked and emitted every 5 seconds",
data: {
type: "number",
title: "Distance",
minimum: 55,
maximum: 1200,
},
},
},
})
.then((thing) => {
console.log("Produced " + thing.getThingDescription().title);

// expose the thing
thing.expose().then(() => {
console.info(thing.getThingDescription().title + " ready");

// mocking the detection with an event sent every 5 seconds, with a random distance
setInterval(() => {
const distance: number = Math.random() * (1200 - 55) + 55;
thing.emitEvent("presenceDetected", distance);
console.info("Emitted presence with distance ", distance);
}, 5000);
});
})
.catch((e) => {
console.log(e);
});
});
137 changes: 137 additions & 0 deletions packages/examples/src/quickstart/simple-coffee-machine.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,137 @@
/********************************************************************************
* Copyright (c) 2023 Contributors to the Eclipse Foundation
*
* See the NOTICE file(s) distributed with this work for additional
* information regarding copyright ownership.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
* http://www.eclipse.org/legal/epl-2.0, or the W3C Software Notice and
* Document License (2015-05-13) which is available at
* https://www.w3.org/Consortium/Legal/2015/copyright-software-and-document.
*
* SPDX-License-Identifier: EPL-2.0 OR W3C-20150513
********************************************************************************/

// This is an example Thing script which is a simple coffee machine.
// You can order coffee and see the status of the resources

import { Servient } from "@node-wot/core";
import { HttpServer } from "@node-wot/binding-http";

// create Servient add HTTP binding with port configuration
const servient = new Servient();
servient.addServer(
new HttpServer({
port: 8081,
})
);

let waterAmount = 100;
let beansAmount = 100;
let milkAmount = 100;

// promisify timeout since it does not return a promise
function timeout(ms: number) {
return new Promise((resolve) => setTimeout(resolve, ms));
}

servient.start().then((WoT) => {
WoT.produce({
title: "Coffee Machine",
description: "A simple coffee machine that can be interacted over the Internet",
support: "https://github.com/eclipse-thingweb/node-wot/",
"@context": "https://www.w3.org/2022/wot/td/v1.1",
properties: {
resources: {
readOnly: true,
observable: true,
type: "object",
properties: {
water: {
type: "integer",
minimum: 10,
egekorkan marked this conversation as resolved.
Show resolved Hide resolved
maximum: 100,
},
beans: {
type: "integer",
minimum: 0,
maximum: 100,
},
milk: {
type: "integer",
minimum: 0,
maximum: 100,
},
},
},
},
actions: {
brew: {
synchronous: true,
input: {
type: "string",
enum: ["espresso", "cappuccino", "americano"],
},
},
},
})
.then((thing) => {
console.log("Produced " + thing.getThingDescription().title);

thing.setPropertyReadHandler("resources", async () => {
return {
water: waterAmount,
beans: beansAmount,
milk: milkAmount,
};
});

thing.setActionHandler("brew", async (params, options) => {
const coffeeType = await params.value();
console.info("received coffee order of ", coffeeType);
if (coffeeType === "espresso") {
if (waterAmount <= 10 || beansAmount <= 10) {
throw new Error("Not enough water or beans");
} else {
await timeout(1000);
waterAmount = waterAmount - 10;
beansAmount = beansAmount - 10;
thing.emitPropertyChange("resources");
return undefined;
}
} else if (coffeeType === "cappuccino") {
if (waterAmount <= 20 || beansAmount <= 25 || milkAmount <= 15) {
throw new Error("Not enough water or beans");
} else {
await timeout(2000);
waterAmount = waterAmount - 15;
beansAmount = beansAmount - 20;
milkAmount = milkAmount - 10;
thing.emitPropertyChange("resources");
return undefined;
}
} else if (coffeeType === "americano") {
if (waterAmount <= 35 || beansAmount <= 10) {
throw new Error("Not enough water or beans");
} else {
await timeout(2000);
waterAmount = waterAmount - 30;
beansAmount = beansAmount - 10;
thing.emitPropertyChange("resources");
return undefined;
}
} else {
throw new Error("Wrong coffee input");
}
});

// expose the thing
thing.expose().then(() => {
console.info(thing.getThingDescription().title + " ready");
});
})
.catch((e) => {
console.log(e);
});
});
96 changes: 96 additions & 0 deletions packages/examples/src/quickstart/smart-clock.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
/********************************************************************************
* Copyright (c) 2023 Contributors to the Eclipse Foundation
*
* See the NOTICE file(s) distributed with this work for additional
* information regarding copyright ownership.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
* http://www.eclipse.org/legal/epl-2.0, or the W3C Software Notice and
* Document License (2015-05-13) which is available at
* https://www.w3.org/Consortium/Legal/2015/copyright-software-and-document.
*
* SPDX-License-Identifier: EPL-2.0 OR W3C-20150513
********************************************************************************/

// This is an example Thing which is a smart clock that runs 60 times faster than real time, where 1 hour happens in 1 minute.

import { Servient } from "@node-wot/core";
// import { HttpServer } from "@node-wot/binding-http";
egekorkan marked this conversation as resolved.
Show resolved Hide resolved
import { CoapServer } from "@node-wot/binding-coap";

// create Servient add CoAP binding with port configuration
const servient = new Servient();
servient.addServer(new CoapServer(5685));

let minuteCounter = 0;
let hourCounter = 0;

async function timeCount(thing: WoT.ExposedThing) {
for (minuteCounter = 0; minuteCounter < 59; minuteCounter++) {
// if we have <60, we can get a 15:60.
await new Promise((resolve) => setTimeout(resolve, 1000)); // sleep
thing.emitPropertyChange("time");
}
console.info({
hour: hourCounter,
minute: minuteCounter,
});

hourCounter++;
if (hourCounter === 24) {
hourCounter = 0;
}
}

servient.start().then((WoT) => {
WoT.produce({
title: "Smart Clock",
description: "a smart clock that runs 60 times faster than real time, where 1 hour happens in 1 minute.",
support: "https://github.com/eclipse-thingweb/node-wot/",
"@context": "https://www.w3.org/2022/wot/td/v1.1",
properties: {
time: {
readOnly: true,
observable: true,
type: "object",
properties: {
minute: {
type: "integer",
minimum: 0,
maximum: 59,
},
hour: {
type: "integer",
minimum: 0,
maximum: 23,
},
egekorkan marked this conversation as resolved.
Show resolved Hide resolved
},
},
},
})
.then(async (thing) => {
console.log("Produced " + thing.getThingDescription().title);

thing.setPropertyReadHandler("time", async () => {
return {
hour: hourCounter,
minute: minuteCounter,
};
});

timeCount(thing);
setInterval(async () => {
timeCount(thing);
thing.emitPropertyChange("time");
}, 61000); // if this is 60s, we never leave the for loop

// expose the thing
thing.expose().then(() => {
console.info(thing.getThingDescription().title + " ready");
});
})
.catch((e) => {
console.log(e);
});
});