UNPKG

nope-js-browser

Version:

NoPE Runtime for the Browser. For nodejs please use nope-js-node

131 lines (130 loc) 5.65 kB
/** * @author Martin Karkowski * @email m.karkowski@zema.de * @create date 2022-01-06 07:15:22 * @modify date 2022-01-06 09:03:30 * @desc [description] */ import { registerGarbageCallback } from "../../helpers/gc"; import { generateId } from "../../helpers/idMethods"; import { defineNopeLogger } from "../../logger/getLogger"; import { INFO } from "../../logger/index.browser"; import { DataPubSubSystem, PubSubSystem } from "../../pubSub"; import { NopeConnectivityManager } from "../ConnectivityManager"; import { NopeInstanceManager, } from "../InstanceManager"; import { generateSelector, NopeRpcManager } from "../RpcManager"; export class NopeCore { constructor(options, generateEmitter, generateObservable, id = null) { var _a; this.options = options; this.generateEmitter = generateEmitter; this.generateObservable = generateObservable; this.id = id; // Store the communicator: this.communicator = options.communicator; if (id == null) { if (options.id) { this.id = options.id; } else { this.id = generateId(); } } this._logger = defineNopeLogger(options.logger, `core.rpc-manager`); if ((_a = this._logger) === null || _a === void 0 ? void 0 : _a.enabledFor(INFO)) { this._logger.info("setting up sub-systems."); } this.eventDistributor = new PubSubSystem(); this.dataDistributor = new DataPubSubSystem(); const defaultSelector = generateSelector(options.defaultSelector || "first", this); // Creating the Connectivity Manager: this.connectivityManager = new NopeConnectivityManager(options, generateObservable, this.id); // Create our RPC-Manger. this.rpcManager = new NopeRpcManager(options, generateObservable, defaultSelector, this.id, this.connectivityManager); // Create our Instance Manager this.instanceManager = new NopeInstanceManager(options, generateEmitter, generateObservable, defaultSelector, this.id, this.connectivityManager, this.rpcManager, this); this.ready = generateObservable(); this.ready.getter = () => { return (this.connectivityManager.ready.getContent() && this.rpcManager.ready.getContent() && this.instanceManager.ready.getContent()); }; const rcvExternally = generateId(); // 1. Subscribe to the events: this.communicator.on("event", (msg) => { if (msg.sender !== this.id) { // split the Message in segments const { path, data, ...options } = msg; // Now, we know, that we have updated the data // so, if there is an update, we will prevent this // by setting the sender to the external id options.sender = rcvExternally; // Push the Data. this.eventDistributor.emit(path, data, options); } }); this.eventDistributor.onIncrementalDataChange.subscribe((item) => { if (item.sender !== rcvExternally) { this.communicator.emit("event", { ...item, sender: this.id, }); } }); // Link the Data-Distributor: // 1. Subscribe to the changes: this.communicator.on("dataChanged", (msg) => { if (msg.sender !== this.id) { // split the Message in segments const { path: name, data, ...options } = msg; // We will prevent to options.sender = rcvExternally; // Push the Data. this.dataDistributor.pushData(name, data, options); } }); // 2. Enable emitting the updates this.dataDistributor.onIncrementalDataChange.subscribe((item) => { if (item.sender !== rcvExternally) { this.communicator.emit("dataChanged", { ...item, sender: this.id, }); } }); this.connectivityManager.ready.subscribe((_) => { this.ready.forcePublish(); }); this.rpcManager.ready.subscribe((_) => { this.ready.forcePublish(); }); this.instanceManager.ready.subscribe((_) => { this.ready.forcePublish(); }); this.disposing = false; registerGarbageCallback(this, this.dispose.bind(this)); } // See interface description async dispose() { this.disposing = true; await this.ready.dispose(); await this.eventDistributor.dispose(); await this.dataDistributor.dispose(); await this.connectivityManager.dispose(); await this.rpcManager.dispose(); await this.instanceManager.dispose(); } toDescription() { const ret = { ...this.connectivityManager.info, ready: this.ready.getContent(), bridge: this.options.communicator.toDescription(), eventDistributor: this.eventDistributor.toDescription(), dataDistributor: this.dataDistributor.toDescription(), connectivityManager: this.connectivityManager.toDescription(), rpcManager: this.rpcManager.toDescription(), instanceManager: this.instanceManager.toDescription(), }; return ret; } }