From b76dfa0da8c35cd5f53521786e11517bfda5c46b Mon Sep 17 00:00:00 2001 From: danielpeintner Date: Tue, 19 Dec 2023 10:35:01 +0100 Subject: [PATCH 1/6] refactor: avoid starting servient multiple times --- packages/core/src/servient.ts | 21 ++++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) diff --git a/packages/core/src/servient.ts b/packages/core/src/servient.ts index 627e3d4f7..200893f07 100644 --- a/packages/core/src/servient.ts +++ b/packages/core/src/servient.ts @@ -30,6 +30,9 @@ export default class Servient { private things: Map = new Map(); private credentialStore: Map> = new Map>(); + private started = false; + private shutdowned = false; + /** add a new codec to support a mediatype; offered mediatypes are listed in TDs */ public addMediaType(codec: ContentCodec, offered = false): void { ContentManager.addCodec(codec, offered); @@ -210,18 +213,30 @@ export default class Servient { // will return WoT object public async start(): Promise { + if (this.started) { + throw Error("Servient started already"); + } const serverStatus: Array> = []; this.servers.forEach((server) => serverStatus.push(server.start(this))); this.clientFactories.forEach((clientFactory) => clientFactory.init()); await Promise.all(serverStatus); + this.started = true; return new WoTImpl(this); } public async shutdown(): Promise { - this.clientFactories.forEach((clientFactory) => clientFactory.destroy()); + if (this.started) { + if (this.shutdowned) { + throw Error("Servient shutdowned already"); + } + this.clientFactories.forEach((clientFactory) => clientFactory.destroy()); - const promises = this.servers.map((server) => server.stop()); - await Promise.all(promises); + const promises = this.servers.map((server) => server.stop()); + await Promise.all(promises); + this.shutdowned = true; + } else { + debug(`Servient cannot be shutdown, wasn't even started`); + } } } From b2b4388aeb71135e178769faa7a50008ad08f664 Mon Sep 17 00:00:00 2001 From: danielpeintner Date: Tue, 19 Dec 2023 11:43:39 +0100 Subject: [PATCH 2/6] style: avoid nesting suggested by @JKRhb --- packages/core/src/servient.ts | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) diff --git a/packages/core/src/servient.ts b/packages/core/src/servient.ts index 200893f07..e9741180c 100644 --- a/packages/core/src/servient.ts +++ b/packages/core/src/servient.ts @@ -226,17 +226,18 @@ export default class Servient { } public async shutdown(): Promise { - if (this.started) { - if (this.shutdowned) { - throw Error("Servient shutdowned already"); - } - this.clientFactories.forEach((clientFactory) => clientFactory.destroy()); - - const promises = this.servers.map((server) => server.stop()); - await Promise.all(promises); - this.shutdowned = true; - } else { - debug(`Servient cannot be shutdown, wasn't even started`); + if (!this.started) { + debug("Servient cannot be shut down, wasn't even started"); + return; } + if (this.shutdowned) { + throw Error("Servient shutdowned already"); + } + + this.clientFactories.forEach((clientFactory) => clientFactory.destroy()); + + const promises = this.servers.map((server) => server.stop()); + await Promise.all(promises); + this.shutdowned = true; } } From 08e85536a462be9c2fed6abd01304ac9f0827dc7 Mon Sep 17 00:00:00 2001 From: danielpeintner Date: Tue, 19 Dec 2023 13:50:12 +0100 Subject: [PATCH 3/6] refactor: use shutdown everywhere with # --- packages/core/src/servient.ts | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/packages/core/src/servient.ts b/packages/core/src/servient.ts index e9741180c..5f49c1a8d 100644 --- a/packages/core/src/servient.ts +++ b/packages/core/src/servient.ts @@ -30,8 +30,8 @@ export default class Servient { private things: Map = new Map(); private credentialStore: Map> = new Map>(); - private started = false; - private shutdowned = false; + #started = false; + #shutdown = false; /** add a new codec to support a mediatype; offered mediatypes are listed in TDs */ public addMediaType(codec: ContentCodec, offered = false): void { @@ -213,7 +213,7 @@ export default class Servient { // will return WoT object public async start(): Promise { - if (this.started) { + if (this.#started) { throw Error("Servient started already"); } const serverStatus: Array> = []; @@ -221,23 +221,23 @@ export default class Servient { this.clientFactories.forEach((clientFactory) => clientFactory.init()); await Promise.all(serverStatus); - this.started = true; + this.#started = true; return new WoTImpl(this); } public async shutdown(): Promise { - if (!this.started) { - debug("Servient cannot be shut down, wasn't even started"); + if (!this.#started) { + debug("Servient cannot be shutdown, wasn't even started"); return; } - if (this.shutdowned) { - throw Error("Servient shutdowned already"); + if (this.#shutdown) { + throw Error("Servient shutdown already"); } this.clientFactories.forEach((clientFactory) => clientFactory.destroy()); const promises = this.servers.map((server) => server.stop()); await Promise.all(promises); - this.shutdowned = true; + this.#shutdown = true; } } From 0d0c1f0776432aee6548662f9ff672399e90c523 Mon Sep 17 00:00:00 2001 From: danielpeintner Date: Mon, 8 Jan 2024 14:24:23 +0100 Subject: [PATCH 4/6] refactor: follow proposal in https://github.com/eclipse-thingweb/node-wot/pull/1195#issuecomment-1880833020 --- packages/core/src/servient.ts | 23 ++++++++++++++--------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/packages/core/src/servient.ts b/packages/core/src/servient.ts index 5f49c1a8d..38e12146d 100644 --- a/packages/core/src/servient.ts +++ b/packages/core/src/servient.ts @@ -30,7 +30,7 @@ export default class Servient { private things: Map = new Map(); private credentialStore: Map> = new Map>(); - #started = false; + #startedWoT?: typeof WoT; #shutdown = false; /** add a new codec to support a mediatype; offered mediatypes are listed in TDs */ @@ -213,25 +213,29 @@ export default class Servient { // will return WoT object public async start(): Promise { - if (this.#started) { - throw Error("Servient started already"); + if (this.#startedWoT != null) { + debug("Servient started already -> nop -> returning previous WoT implementation"); + return this.#startedWoT; } + if (this.#shutdown) { + throw Error("Servient cannot be started (again) since it was already stopped"); + } + const serverStatus: Array> = []; this.servers.forEach((server) => serverStatus.push(server.start(this))); this.clientFactories.forEach((clientFactory) => clientFactory.init()); await Promise.all(serverStatus); - this.#started = true; - return new WoTImpl(this); + return (this.#startedWoT = new WoTImpl(this)); } public async shutdown(): Promise { - if (!this.#started) { - debug("Servient cannot be shutdown, wasn't even started"); - return; + if (this.#startedWoT === undefined) { + throw Error("Servient cannot be shutdown, wasn't even started"); } if (this.#shutdown) { - throw Error("Servient shutdown already"); + debug("Servient shutdown already -> nop"); + return; } this.clientFactories.forEach((clientFactory) => clientFactory.destroy()); @@ -239,5 +243,6 @@ export default class Servient { const promises = this.servers.map((server) => server.stop()); await Promise.all(promises); this.#shutdown = true; + this.#startedWoT = undefined; // clean-up reference } } From aa1537187cad8789907972262b7ef15c2f55fc0d Mon Sep 17 00:00:00 2001 From: danielpeintner Date: Thu, 11 Jan 2024 10:36:23 +0100 Subject: [PATCH 5/6] refactor: rename startedWoT to wotInstance as proposed by @JKRhb --- packages/core/src/servient.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/packages/core/src/servient.ts b/packages/core/src/servient.ts index 38e12146d..8085c9216 100644 --- a/packages/core/src/servient.ts +++ b/packages/core/src/servient.ts @@ -30,7 +30,7 @@ export default class Servient { private things: Map = new Map(); private credentialStore: Map> = new Map>(); - #startedWoT?: typeof WoT; + #wotInstance?: typeof WoT; #shutdown = false; /** add a new codec to support a mediatype; offered mediatypes are listed in TDs */ @@ -213,9 +213,9 @@ export default class Servient { // will return WoT object public async start(): Promise { - if (this.#startedWoT != null) { + if (this.#wotInstance != null) { debug("Servient started already -> nop -> returning previous WoT implementation"); - return this.#startedWoT; + return this.#wotInstance; } if (this.#shutdown) { throw Error("Servient cannot be started (again) since it was already stopped"); @@ -226,11 +226,11 @@ export default class Servient { this.clientFactories.forEach((clientFactory) => clientFactory.init()); await Promise.all(serverStatus); - return (this.#startedWoT = new WoTImpl(this)); + return (this.#wotInstance = new WoTImpl(this)); } public async shutdown(): Promise { - if (this.#startedWoT === undefined) { + if (this.#wotInstance === undefined) { throw Error("Servient cannot be shutdown, wasn't even started"); } if (this.#shutdown) { @@ -243,6 +243,6 @@ export default class Servient { const promises = this.servers.map((server) => server.stop()); await Promise.all(promises); this.#shutdown = true; - this.#startedWoT = undefined; // clean-up reference + this.#wotInstance = undefined; // clean-up reference } } From 16ec2876d6e64076da59621f25055f1e367279d1 Mon Sep 17 00:00:00 2001 From: danielpeintner Date: Thu, 11 Jan 2024 10:43:16 +0100 Subject: [PATCH 6/6] refactor: check for undefined to detect whether WoT instance was created --- packages/core/src/servient.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/core/src/servient.ts b/packages/core/src/servient.ts index 8085c9216..1a9111dfc 100644 --- a/packages/core/src/servient.ts +++ b/packages/core/src/servient.ts @@ -213,7 +213,7 @@ export default class Servient { // will return WoT object public async start(): Promise { - if (this.#wotInstance != null) { + if (this.#wotInstance !== undefined) { debug("Servient started already -> nop -> returning previous WoT implementation"); return this.#wotInstance; }