From 448a8699986bc3bbc9f6b80e91dd285773b95f7f Mon Sep 17 00:00:00 2001 From: Julian Waller Date: Tue, 17 Oct 2023 23:44:20 +0100 Subject: [PATCH] wip: refactoring --- lib/Cloud/Controller.js | 2 +- lib/Cloud/Region.js | 2 +- lib/Data/Controller.js | 2 +- lib/Data/ImportExport.js | 4 +-- lib/Data/Metrics.js | 2 +- lib/Graphics/Preview.js | 54 ++++++++++++++++++++++++++++------------ lib/Log/Controller.js | 26 +++++++++---------- lib/Registry.js | 37 ++++++++++++++++++++------- lib/Service/EmberPlus.js | 4 +-- lib/Service/Satellite.js | 2 +- lib/UI/Controller.js | 6 +++-- lib/UI/Handler.js | 4 +-- lib/UI/Server.js | 7 ++---- lib/UI/Update.js | 38 +++++++++++++++------------- 14 files changed, 117 insertions(+), 73 deletions(-) diff --git a/lib/Cloud/Controller.js b/lib/Cloud/Controller.js index 37dfeae82..6ee406301 100644 --- a/lib/Cloud/Controller.js +++ b/lib/Cloud/Controller.js @@ -103,7 +103,7 @@ class CloudController extends CoreBase { this.clouddb = clouddb this.cache = cache - this.companionId = registry.machineId + this.companionId = registry.appInfo.machineId const uuid = this.clouddb.getKey('uuid', undefined) this.setState({ uuid }) diff --git a/lib/Cloud/Region.js b/lib/Cloud/Region.js index 1f1432a80..d3cd2f9c6 100644 --- a/lib/Cloud/Region.js +++ b/lib/Cloud/Region.js @@ -153,7 +153,7 @@ class CloudRegion { token: this.cloud.data.token, uuid: this.cloud.state.uuid, companionId: this.cloud.companionId, - version: this.cloud.registry.appBuild, + version: this.cloud.registry.appInfo.appBuild, }) this.logger.debug('Login ok') diff --git a/lib/Data/Controller.js b/lib/Data/Controller.js index f5299938b..32f94a19c 100644 --- a/lib/Data/Controller.js +++ b/lib/Data/Controller.js @@ -9,7 +9,7 @@ class DataController { * @param {import('../Registry.js').default} registry */ constructor(registry) { - this.cache = new DataCache(registry.configDir) + this.cache = new DataCache(registry.appInfo.configDir) this.userconfig = new DataUserConfig(registry) this.importExport = new DataImportExport(registry) this.metrics = new DataMetrics(registry) diff --git a/lib/Data/ImportExport.js b/lib/Data/ImportExport.js index 5fcad70f7..a9939d04e 100644 --- a/lib/Data/ImportExport.js +++ b/lib/Data/ImportExport.js @@ -417,7 +417,7 @@ class DataImportExport extends CoreBase { archive.glob( '*', { - cwd: this.registry.configDir, + cwd: this.registry.appInfo.configDir, nodir: true, ignore: [ 'cloud', // Ignore companion-cloud credentials @@ -427,7 +427,7 @@ class DataImportExport extends CoreBase { ) // Add the logs if found - const logsDir = path.join(this.registry.configDir, '../logs') + const logsDir = path.join(this.registry.appInfo.configDir, '../logs') if (fs.existsSync(logsDir)) { archive.glob( '*', diff --git a/lib/Data/Metrics.js b/lib/Data/Metrics.js index b9ba315ee..2cf4f8dd1 100644 --- a/lib/Data/Metrics.js +++ b/lib/Data/Metrics.js @@ -60,7 +60,7 @@ class DataMetrics extends CoreBase { try { const payload = { - i: this.registry.machineId, + i: this.registry.appInfo.machineId, r: process.uptime(), m: instanceCount, d: relevantDevices, diff --git a/lib/Graphics/Preview.js b/lib/Graphics/Preview.js index 5a2c443f7..b4a1a1c6c 100644 --- a/lib/Graphics/Preview.js +++ b/lib/Graphics/Preview.js @@ -1,7 +1,6 @@ -import CoreBase from '../Core/Base.js' -import Registry from '../Registry.js' import { ControlConfigRoom } from '../Controls/ControlBase.js' import { ParseInternalControlReference } from '../Internal/Util.js' +// import LogController from '../Log/Controller.js' /** * Get Socket.io room for preview updates @@ -28,7 +27,6 @@ function ensureLocationIsNumber(location) { /** * The class that manages bank preview generation/relay for interfaces * - * @extends CoreBase * @author Håkon Nessjøen * @author Keith Rocheck * @author William Viker @@ -46,7 +44,27 @@ function ensureLocationIsNumber(location) { * develop commercial activities involving the Companion software without * disclosing the source code of your own applications. */ -class GraphicsPreview extends CoreBase { +class GraphicsPreview { + // #logger = LogController.createLogger('Graphics/Preview') + + /** + * @readonly + * @type {import('./Controller.js').default} + */ + #graphicsController + + /** + * @readonly + * @type {import('../UI/Handler.js').default} + */ + #ioController + + /** + * @readonly + * @type {import('../Page/Controller.js').default} + */ + #pageController + /** * Current bank reference previews * @type {Map} @@ -54,12 +72,16 @@ class GraphicsPreview extends CoreBase { #bankReferencePreviews = new Map() /** - * @param {Registry} registry - the application core + * @param {import('./Controller.js').default} graphicsController + * @param {import("../UI/Handler.js").default } ioController + * @param {import("../Page/Controller.js").default} pageController */ - constructor(registry) { - super(registry, 'preview', 'Graphics/Preview') + constructor(graphicsController, ioController, pageController) { + this.#graphicsController = graphicsController + this.#ioController = ioController + this.#pageController = pageController - this.graphics.on('button_drawn', this.#updateButton.bind(this)) + this.#graphicsController.on('button_drawn', this.#updateButton.bind(this)) } /** @@ -94,7 +116,7 @@ class GraphicsPreview extends CoreBase { client.join(PreviewLocationRoom(location)) - const render = this.graphics.getBank(location) + const render = this.#graphicsController.getBank(location) return { image: render.asDataUrl, isUsed: !!render.style } } ) @@ -149,7 +171,7 @@ class GraphicsPreview extends CoreBase { client, }) - return result.location ? this.graphics.getBank(result.location).asDataUrl : null + return result.location ? this.#graphicsController.getBank(result.location).asDataUrl : null } ) client.onPromise( @@ -174,17 +196,17 @@ class GraphicsPreview extends CoreBase { */ #updateButton(location, render) { // Push the updated render to any clients viewing a preview of a control - const controlId = this.page.getControlIdAt(location) + const controlId = this.#pageController.getControlIdAt(location) if (controlId) { const controlRoom = ControlConfigRoom(controlId) - if (this.io.countRoomMembers(controlRoom) > 0) { - this.io.emitToRoom(controlRoom, `controls:preview-${controlId}`, render.asDataUrl) + if (this.#ioController.countRoomMembers(controlRoom) > 0) { + this.#ioController.emitToRoom(controlRoom, `controls:preview-${controlId}`, render.asDataUrl) } } const locationRoom = PreviewLocationRoom(location) - if (this.io.countRoomMembers(locationRoom) > 0) { - this.io.emitToRoom(locationRoom, `preview:location:render`, location, render.asDataUrl, !!render.style) + if (this.#ioController.countRoomMembers(locationRoom) > 0) { + this.#ioController.emitToRoom(locationRoom, `preview:location:render`, location, render.asDataUrl, !!render.style) } // Lookup any sessions @@ -238,7 +260,7 @@ class GraphicsPreview extends CoreBase { previewSession.client.emit( `preview:button-reference:update:${previewSession.id}`, - this.graphics.getBank(result.location).asDataUrl + this.#graphicsController.getBank(result.location).asDataUrl ) } } diff --git a/lib/Log/Controller.js b/lib/Log/Controller.js index da9a8ea3e..bb7c47f6c 100644 --- a/lib/Log/Controller.js +++ b/lib/Log/Controller.js @@ -80,10 +80,9 @@ class LogController { #history = [] /** - * The socket.io server * @type {import('../UI/Handler.js').default | null} */ - #io = null + #ioController = null /** * Create a new logger @@ -184,10 +183,10 @@ class LogController { client.onPromise('logs:clear', () => { this.#history = [] - if (this.#io && this.#io.countRoomMembers(LogRoom) > 0) { - this.#io.emitToRoom(LogRoom, 'logs:clear') + if (this.#ioController && this.#ioController.countRoomMembers(LogRoom) > 0) { + this.#ioController.emitToRoom(LogRoom, 'logs:clear') - this.#io.emitToRoom(LogRoom, 'logs:lines', [ + this.#ioController.emitToRoom(LogRoom, 'logs:lines', [ { time: Date.now(), source: 'log', @@ -203,8 +202,8 @@ class LogController { #pendingLines = [] debounceSendLines = debounceFn( () => { - if (this.#io && this.#io.countRoomMembers(LogRoom) > 0) { - this.#io.emitToRoom(LogRoom, 'logs:lines', this.#pendingLines) + if (this.#ioController && this.#ioController.countRoomMembers(LogRoom) > 0) { + this.#ioController.emitToRoom(LogRoom, 'logs:lines', this.#pendingLines) } this.#pendingLines = [] }, @@ -265,12 +264,13 @@ class LogController { /** * Initialize Sentry and UI logging - * @param {import('../Registry.js').default} registry + * @param {import('../Registry.js').AppInfo } appInfo + * @param {import('../UI/Handler.js').default} ioController * @returns {void} * @access public */ - init(registry) { - this.#io = registry.io + init(appInfo, ioController) { + this.#ioController = ioController // Allow the DSN to be provided as an env variable let sentryDsn = process.env.SENTRY_DSN @@ -289,7 +289,7 @@ class LogController { try { init({ dsn: sentryDsn, - release: `companion@${registry.appBuild || registry.appVersion}`, + release: `companion@${appInfo.appBuild || appInfo.appVersion}`, beforeSend(event) { if (event.exception) { console.log('sentry', 'error', JSON.stringify(event.exception, undefined, 4)) @@ -300,8 +300,8 @@ class LogController { }) configureScope((scope) => { - scope.setUser({ id: registry.machineId }) - scope.setExtra('build', registry.appBuild) + scope.setUser({ id: appInfo.machineId }) + scope.setExtra('build', appInfo.appBuild) }) } catch (e) { this.logger.info(`Failed to setup sentry reporting: ${e}`) diff --git a/lib/Registry.js b/lib/Registry.js index 38a0631c6..d9359b186 100644 --- a/lib/Registry.js +++ b/lib/Registry.js @@ -180,6 +180,13 @@ class Registry extends EventEmitter { */ api_router + /** + * @type {AppInfo} + * @access public + * @readonly + */ + appInfo + /** * Create a new application Registry * @param {string} configDir - the configuration path @@ -197,11 +204,13 @@ class Registry extends EventEmitter { this.logger.info(`Build ${buildNumber}`) this.logger.info(`configuration directory: ${configDir}`) - this.configDir = configDir - this.machineId = machineId - this.appVersion = pkgInfo.version - this.appBuild = buildNumber - this.pkgInfo = pkgInfo + this.appInfo = { + configDir: configDir, + machineId: machineId, + appVersion: pkgInfo.version, + appBuild: buildNumber, + pkgInfo: pkgInfo, + } } /** @@ -216,15 +225,15 @@ class Registry extends EventEmitter { this.api_router = express.Router() this.ui = new UIController(this) this.io = this.ui.io - this.db = new DataDatabase(this.configDir) - this.clouddb = new CloudDatabase(this.configDir) + this.db = new DataDatabase(this.appInfo.configDir) + this.clouddb = new CloudDatabase(this.appInfo.configDir) this.data = new DataController(this) this.userconfig = this.data.userconfig - LogController.init(this) + LogController.init(this.appInfo, this.ui.io) this.page = new PageController(this) this.controls = new ControlsController(this) this.graphics = new GraphicsController(this) - this.preview = new GraphicsPreview(this) + this.preview = new GraphicsPreview(this.graphics, this.io, this.page) this.surfaces = new SurfaceController(this) this.instance = new InstanceController(this) this.services = new ServiceController(this) @@ -348,3 +357,13 @@ class Registry extends EventEmitter { } export default Registry + +/** + * @typedef {{ + * configDir: string + * machineId: string + * appVersion: string + * appBuild: string + * pkgInfo: string + * }} AppInfo + */ diff --git a/lib/Service/EmberPlus.js b/lib/Service/EmberPlus.js index 2218bf24a..ba1bf1b51 100644 --- a/lib/Service/EmberPlus.js +++ b/lib/Service/EmberPlus.js @@ -220,7 +220,7 @@ class ServiceEmberPlus extends ServiceBase { EmberModel.ParameterType.String, 'version', undefined, - this.registry.appVersion + this.registry.appInfo.appVersion ) ), 3: new EmberModel.NumberedTreeNodeImpl( @@ -229,7 +229,7 @@ class ServiceEmberPlus extends ServiceBase { EmberModel.ParameterType.String, 'build', undefined, - this.registry.appBuild + this.registry.appInfo.appBuild ) ), }), diff --git a/lib/Service/Satellite.js b/lib/Service/Satellite.js index 95f9093a8..6591315e4 100644 --- a/lib/Service/Satellite.js +++ b/lib/Service/Satellite.js @@ -280,7 +280,7 @@ class ServiceSatellite extends ServiceBase { socket.on('close', doCleanup) - socket.write(`BEGIN CompanionVersion=${this.registry.appBuild} ApiVersion=${API_VERSION}\n`) + socket.write(`BEGIN CompanionVersion=${this.registry.appInfo.appBuild} ApiVersion=${API_VERSION}\n`) } /** diff --git a/lib/UI/Controller.js b/lib/UI/Controller.js index 590187c46..e37d37349 100644 --- a/lib/UI/Controller.js +++ b/lib/UI/Controller.js @@ -10,9 +10,11 @@ class UIController { */ constructor(registry) { this.express = new UIExpress(registry) - this.server = new UIServer(registry, this.express.app) + this.server = new UIServer(this.express.app) + registry.on('http_rebind', this.server.rebindHttp.bind(this.server)) + this.io = new UIHandler(registry, this.server) - this.update = new UIUpdate(registry) + this.update = new UIUpdate(registry.appInfo, this.io) } /** diff --git a/lib/UI/Handler.js b/lib/UI/Handler.js index 49741d3bf..ea878317e 100644 --- a/lib/UI/Handler.js +++ b/lib/UI/Handler.js @@ -166,8 +166,8 @@ class UIHandler { client.onPromise('app-version-info', () => { return { - appVersion: this.registry.appVersion, - appBuild: this.registry.appBuild, + appVersion: this.registry.appInfo.appVersion, + appBuild: this.registry.appInfo.appBuild, } }) diff --git a/lib/UI/Server.js b/lib/UI/Server.js index c54e3c9d0..15432dcbb 100644 --- a/lib/UI/Server.js +++ b/lib/UI/Server.js @@ -24,13 +24,10 @@ class UIServer extends _http { #logger = LogController.createLogger('UI/Server') /** - * @param {import('../Registry.js').default} registry * @param {import('express').Express} express */ - constructor(registry, express) { + constructor(express) { super(express) - - registry.on('http_rebind', this.#rebindHttp.bind(this)) } /** @@ -38,7 +35,7 @@ class UIServer extends _http { * @param {string} bind_ip * @param {number} http_port */ - #rebindHttp(bind_ip, http_port) { + rebindHttp(bind_ip, http_port) { this.bind_ip = bind_ip this.http_port = http_port diff --git a/lib/UI/Update.js b/lib/UI/Update.js index 456fb47b9..80bb87eac 100644 --- a/lib/UI/Update.js +++ b/lib/UI/Update.js @@ -23,6 +23,18 @@ import LogController from '../Log/Controller.js' class UIUpdate { #logger = LogController.createLogger('UI/Update') + /** + * @type {import('../Registry.js').AppInfo} + * @readonly + */ + #appInfo + + /** + * @type {import('./Handler.js').default} + * @readonly + */ + #ioController + /** * Latest update information * @type {Record | null} @@ -31,11 +43,13 @@ class UIUpdate { #latestUpdateData = null /** - * @param {import('../Registry.js').default} registry + * @param {import('../Registry.js').AppInfo} appInfo + * @param {import('./Handler.js').default} ioController */ - constructor(registry) { + constructor(appInfo, ioController) { this.#logger.silly('loading update') - this.registry = registry + this.#appInfo = appInfo + this.#ioController = ioController // Make a request now this.#requestUpdate() @@ -59,14 +73,6 @@ class UIUpdate { }) } - get io() { - if (this.registry) { - return this.registry.io - } else { - return null - } - } - /** * Compile update payload */ @@ -80,15 +86,15 @@ class UIUpdate { // we can filter out certain kinds of OS/versions if there // is known bugs etc. app_name: 'companion', - app_build: this.registry.appBuild, - app_version: this.registry.appVersion, + app_build: this.#appInfo.appBuild, + app_version: this.#appInfo.appVersion, arch: os.arch(), tz: off, cpus: os.cpus(), platform: os.platform(), release: os.release(), type: os.type(), - id: this.registry.machineId, + id: this.#appInfo.machineId, } } @@ -105,9 +111,7 @@ class UIUpdate { this.#logger.debug('fresh update data received', body) this.#latestUpdateData = body - if (this.io) { - this.io.emit('app-update-info', body) - } + this.#ioController.emit('app-update-info', body) }) .catch((e) => { this.#logger.verbose('update server said something unexpected!', e)