From ea2b67f06140c08037b358ec7f5182fe49f96406 Mon Sep 17 00:00:00 2001 From: Jari Kolehmainen Date: Thu, 19 Nov 2020 09:11:25 +0200 Subject: [PATCH 1/6] fix base store channel names Signed-off-by: Jari Kolehmainen --- src/common/base-store.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/common/base-store.ts b/src/common/base-store.ts index 6aab88e940..a240ac6fb0 100644 --- a/src/common/base-store.ts +++ b/src/common/base-store.ts @@ -38,11 +38,11 @@ export class BaseStore extends Singleton { } get syncRendererChannel() { - return `store-sync-renderer:${this.name}` + return `store-sync-renderer:${this.path}` } get syncMainChannel() { - return `store-sync-main:${this.name}` + return `store-sync-main:${this.path}` } get path() { From 43e361727f54d1c97471229c4a9502c52345712d Mon Sep 17 00:00:00 2001 From: Jari Kolehmainen Date: Thu, 19 Nov 2020 09:12:19 +0200 Subject: [PATCH 2/6] refactor/remove Cluster#frameId Signed-off-by: Jari Kolehmainen --- src/common/cluster-ipc.ts | 12 +++++++++--- src/common/ipc.ts | 10 ++++------ src/main/cluster.ts | 1 - src/main/window-manager.ts | 4 ++-- 4 files changed, 15 insertions(+), 12 deletions(-) diff --git a/src/common/cluster-ipc.ts b/src/common/cluster-ipc.ts index 15f4fef584..d7ff78fd37 100644 --- a/src/common/cluster-ipc.ts +++ b/src/common/cluster-ipc.ts @@ -3,12 +3,14 @@ import { ClusterId, clusterStore } from "./cluster-store"; import { appEventBus } from "./event-bus" import { ResourceApplier } from "../main/resource-applier"; import { ipcMain } from "electron"; +import { observable } from "mobx"; export const clusterActivateHandler = "cluster:activate" export const clusterSetFrameIdHandler = "cluster:set-frame-id" export const clusterRefreshHandler = "cluster:refresh" export const clusterDisconnectHandler = "cluster:disconnect" export const clusterKubectlApplyAllHandler = "cluster:kubectl-apply-all" +export const clusterFrameMap = observable.map(); if (ipcMain) { handleRequest(clusterActivateHandler, (event, clusterId: ClusterId, force = false) => { @@ -18,10 +20,10 @@ if (ipcMain) { } }) - handleRequest(clusterSetFrameIdHandler, (event, clusterId: ClusterId, frameId?: number) => { + handleRequest(clusterSetFrameIdHandler, (event, clusterId: ClusterId, frameId: number) => { const cluster = clusterStore.getById(clusterId); if (cluster) { - if (frameId) cluster.frameId = frameId; // save cluster's webFrame.routingId to be able to send push-updates + clusterFrameMap.set(cluster.id, frameId) return cluster.pushState(); } }) @@ -33,7 +35,11 @@ if (ipcMain) { handleRequest(clusterDisconnectHandler, (event, clusterId: ClusterId) => { appEventBus.emit({name: "cluster", action: "stop"}); - return clusterStore.getById(clusterId)?.disconnect(); + const cluster = clusterStore.getById(clusterId); + if (cluster) { + cluster.disconnect(); + clusterFrameMap.delete(cluster.id) + } }) handleRequest(clusterKubectlApplyAllHandler, (event, clusterId: ClusterId, resources: string[]) => { diff --git a/src/common/ipc.ts b/src/common/ipc.ts index 6e2a76c5ed..7878882343 100644 --- a/src/common/ipc.ts +++ b/src/common/ipc.ts @@ -2,8 +2,9 @@ // https://www.electronjs.org/docs/api/ipc-main // https://www.electronjs.org/docs/api/ipc-renderer -import { ipcMain, ipcRenderer, webContents, remote } from "electron" +import { ipcMain, ipcRenderer, webContents, remote } from "electron"; import logger from "../main/logger"; +import { clusterFrameMap } from "./cluster-ipc"; export function handleRequest(channel: string, listener: (...args: any[]) => any) { ipcMain.handle(channel, listener) @@ -15,11 +16,8 @@ export async function requestMain(channel: string, ...args: any[]) { async function getSubFrames(): Promise { const subFrames: number[] = []; - const { clusterStore } = await import("./cluster-store"); - clusterStore.clustersList.forEach(cluster => { - if (cluster.frameId) { - subFrames.push(cluster.frameId) - } + clusterFrameMap.forEach((frameId, _) => { + subFrames.push(frameId) }); return subFrames; } diff --git a/src/main/cluster.ts b/src/main/cluster.ts index 28dce65f0b..ecb6e6db9c 100644 --- a/src/main/cluster.ts +++ b/src/main/cluster.ts @@ -50,7 +50,6 @@ export interface ClusterState { export class Cluster implements ClusterModel, ClusterState { public id: ClusterId; - public frameId: number; public kubeCtl: Kubectl public contextHandler: ContextHandler; public ownerRef: string; diff --git a/src/main/window-manager.ts b/src/main/window-manager.ts index 33a943b552..5a536e6946 100644 --- a/src/main/window-manager.ts +++ b/src/main/window-manager.ts @@ -1,5 +1,4 @@ import type { ClusterId } from "../common/cluster-store"; -import { clusterStore } from "../common/cluster-store"; import { observable } from "mobx"; import { app, BrowserWindow, dialog, shell, webContents } from "electron" import windowStateKeeper from "electron-window-state" @@ -8,6 +7,7 @@ import { subscribeToBroadcast } from "../common/ipc" import { initMenu } from "./menu"; import { initTray } from "./tray"; import { Singleton } from "../common/utils"; +import { clusterFrameMap } from "../common/cluster-ipc"; export class WindowManager extends Singleton { protected mainWindow: BrowserWindow; @@ -130,7 +130,7 @@ export class WindowManager extends Singleton { } reload() { - const frameId = clusterStore.getById(this.activeClusterId)?.frameId; + const frameId = clusterFrameMap.get(this.activeClusterId) if (frameId) { this.sendToView({ channel: "renderer:reload", frameId }); } else { From 2d51af6be3611468892ec7826aed2867afc69f41 Mon Sep 17 00:00:00 2001 From: Jari Kolehmainen Date: Thu, 19 Nov 2020 09:52:05 +0200 Subject: [PATCH 3/6] simplify ExtensionLoader Signed-off-by: Jari Kolehmainen --- src/extensions/extension-loader.ts | 23 ++++++++++------------- 1 file changed, 10 insertions(+), 13 deletions(-) diff --git a/src/extensions/extension-loader.ts b/src/extensions/extension-loader.ts index 4893cd11e2..f4f6edc6bc 100644 --- a/src/extensions/extension-loader.ts +++ b/src/extensions/extension-loader.ts @@ -3,12 +3,10 @@ import type { LensMainExtension } from "./lens-main-extension" import type { LensRendererExtension } from "./lens-renderer-extension" import type { InstalledExtension } from "./extension-manager"; import path from "path" -import { broadcastMessage, subscribeToBroadcast } from "../common/ipc" +import { broadcastMessage, handleRequest, requestMain, subscribeToBroadcast } from "../common/ipc" import { action, computed, observable, reaction, toJS, when } from "mobx" import logger from "../main/logger" import { app, ipcRenderer, remote } from "electron" -import { appEventBus } from "./core-api/event-bus" -import { clusterStore } from "./core-api/stores" import * as registries from "./registries"; import { extensionsStore } from "./extensions-store"; @@ -20,32 +18,31 @@ export function extensionPackagesRoot() { export class ExtensionLoader { protected extensions = observable.map(); protected instances = observable.map(); + protected readonly requestExtensionsChannel = "extensions:loaded" @observable isLoaded = false; whenLoaded = when(() => this.isLoaded); constructor() { if (ipcRenderer) { - subscribeToBroadcast("extensions:loaded", (event, extensions: [LensExtensionId, InstalledExtension][]) => { - console.log("extensions", extensions) + const extensionListHandler = ( extensions: [LensExtensionId, InstalledExtension][]) => { this.isLoaded = true; extensions.forEach(([extId, ext]) => { if (!this.extensions.has(extId)) { this.extensions.set(extId, ext) } }) + } + requestMain(this.requestExtensionsChannel).then(extensionListHandler) + subscribeToBroadcast(this.requestExtensionsChannel, (event, extensions: [LensExtensionId, InstalledExtension][]) => { + extensionListHandler(extensions) }); } else { reaction(() => this.extensions.toJS(), () => { this.broadcastExtensions() }) - appEventBus.addListener((ev) => { - if (ev.name === "app" && ev.action === "dom-ready") { - this.broadcastExtensions() - } - }) - reaction(() => clusterStore.connectedClustersList, () => { - this.broadcastExtensions() + handleRequest(this.requestExtensionsChannel, () => { + return Array.from(this.toJSON()) }) } extensionsStore.manageState(this); @@ -156,7 +153,7 @@ export class ExtensionLoader { } broadcastExtensions() { - broadcastMessage("extensions:loaded", Array.from(this.toJSON())) + broadcastMessage(this.requestExtensionsChannel, Array.from(this.toJSON())) } } From cdc0af520d33db753a2ab80f3767c4f60d4bd355 Mon Sep 17 00:00:00 2001 From: Jari Kolehmainen Date: Thu, 19 Nov 2020 10:13:10 +0200 Subject: [PATCH 4/6] simplify ExtensionLoader Signed-off-by: Jari Kolehmainen --- src/extensions/extension-loader.ts | 63 +++++++++++++++++------------- src/renderer/bootstrap.tsx | 3 ++ 2 files changed, 39 insertions(+), 27 deletions(-) diff --git a/src/extensions/extension-loader.ts b/src/extensions/extension-loader.ts index f4f6edc6bc..c5339f31c9 100644 --- a/src/extensions/extension-loader.ts +++ b/src/extensions/extension-loader.ts @@ -23,31 +23,6 @@ export class ExtensionLoader { @observable isLoaded = false; whenLoaded = when(() => this.isLoaded); - constructor() { - if (ipcRenderer) { - const extensionListHandler = ( extensions: [LensExtensionId, InstalledExtension][]) => { - this.isLoaded = true; - extensions.forEach(([extId, ext]) => { - if (!this.extensions.has(extId)) { - this.extensions.set(extId, ext) - } - }) - } - requestMain(this.requestExtensionsChannel).then(extensionListHandler) - subscribeToBroadcast(this.requestExtensionsChannel, (event, extensions: [LensExtensionId, InstalledExtension][]) => { - extensionListHandler(extensions) - }); - } else { - reaction(() => this.extensions.toJS(), () => { - this.broadcastExtensions() - }) - handleRequest(this.requestExtensionsChannel, () => { - return Array.from(this.toJSON()) - }) - } - extensionsStore.manageState(this); - } - @computed get userExtensions(): Map { const extensions = this.extensions.toJS(); extensions.forEach((ext, extId) => { @@ -59,11 +34,45 @@ export class ExtensionLoader { } @action - async init(extensions: Map) { - this.extensions.replace(extensions); + async init(extensions?: Map) { + if (extensions) { + this.extensions.replace(extensions); + } + if (ipcRenderer) { + this.initRenderer() + } else { + this.initMain() + } + extensionsStore.manageState(this); + } + + protected async initMain() { this.isLoaded = true; this.loadOnMain(); this.broadcastExtensions(); + + reaction(() => this.extensions.toJS(), () => { + this.broadcastExtensions() + }) + + handleRequest(this.requestExtensionsChannel, () => { + return Array.from(this.toJSON()) + }) + } + + protected async initRenderer() { + const extensionListHandler = ( extensions: [LensExtensionId, InstalledExtension][]) => { + this.isLoaded = true; + extensions.forEach(([extId, ext]) => { + if (!this.extensions.has(extId)) { + this.extensions.set(extId, ext) + } + }) + } + requestMain(this.requestExtensionsChannel).then(extensionListHandler) + subscribeToBroadcast(this.requestExtensionsChannel, (event, extensions: [LensExtensionId, InstalledExtension][]) => { + extensionListHandler(extensions) + }); } loadOnMain() { diff --git a/src/renderer/bootstrap.tsx b/src/renderer/bootstrap.tsx index 52a92b7c11..cfadb5c379 100644 --- a/src/renderer/bootstrap.tsx +++ b/src/renderer/bootstrap.tsx @@ -14,6 +14,7 @@ import { clusterStore } from "../common/cluster-store"; import { i18nStore } from "./i18n"; import { themeStore } from "./theme.store"; import { extensionsStore } from "../extensions/extensions-store"; +import { extensionLoader } from "../extensions/extension-loader"; type AppComponent = React.ComponentType & { init?(): Promise; @@ -30,6 +31,8 @@ export async function bootstrap(App: AppComponent) { const rootElem = document.getElementById("app") rootElem.classList.toggle("is-mac", isMac); + extensionLoader.init() + // preload common stores await Promise.all([ userStore.load(), From 946519e39727e046a579b8ec9c29672420fa4f69 Mon Sep 17 00:00:00 2001 From: Jari Kolehmainen Date: Thu, 19 Nov 2020 10:19:28 +0200 Subject: [PATCH 5/6] fix cyclic dependencies Signed-off-by: Jari Kolehmainen --- src/common/cluster-frames.ts | 3 +++ src/common/cluster-ipc.ts | 4 ++-- src/common/ipc.ts | 2 +- src/main/window-manager.ts | 2 +- 4 files changed, 7 insertions(+), 4 deletions(-) create mode 100644 src/common/cluster-frames.ts diff --git a/src/common/cluster-frames.ts b/src/common/cluster-frames.ts new file mode 100644 index 0000000000..af950b0785 --- /dev/null +++ b/src/common/cluster-frames.ts @@ -0,0 +1,3 @@ +import { observable } from "mobx" + +export const clusterFrameMap = observable.map(); diff --git a/src/common/cluster-ipc.ts b/src/common/cluster-ipc.ts index d7ff78fd37..c2204bc6b4 100644 --- a/src/common/cluster-ipc.ts +++ b/src/common/cluster-ipc.ts @@ -3,14 +3,14 @@ import { ClusterId, clusterStore } from "./cluster-store"; import { appEventBus } from "./event-bus" import { ResourceApplier } from "../main/resource-applier"; import { ipcMain } from "electron"; -import { observable } from "mobx"; +import { clusterFrameMap } from "./cluster-frames" export const clusterActivateHandler = "cluster:activate" export const clusterSetFrameIdHandler = "cluster:set-frame-id" export const clusterRefreshHandler = "cluster:refresh" export const clusterDisconnectHandler = "cluster:disconnect" export const clusterKubectlApplyAllHandler = "cluster:kubectl-apply-all" -export const clusterFrameMap = observable.map(); + if (ipcMain) { handleRequest(clusterActivateHandler, (event, clusterId: ClusterId, force = false) => { diff --git a/src/common/ipc.ts b/src/common/ipc.ts index 7878882343..882498a3a4 100644 --- a/src/common/ipc.ts +++ b/src/common/ipc.ts @@ -4,7 +4,7 @@ import { ipcMain, ipcRenderer, webContents, remote } from "electron"; import logger from "../main/logger"; -import { clusterFrameMap } from "./cluster-ipc"; +import { clusterFrameMap } from "./cluster-frames"; export function handleRequest(channel: string, listener: (...args: any[]) => any) { ipcMain.handle(channel, listener) diff --git a/src/main/window-manager.ts b/src/main/window-manager.ts index 5a536e6946..019ed270eb 100644 --- a/src/main/window-manager.ts +++ b/src/main/window-manager.ts @@ -7,7 +7,7 @@ import { subscribeToBroadcast } from "../common/ipc" import { initMenu } from "./menu"; import { initTray } from "./tray"; import { Singleton } from "../common/utils"; -import { clusterFrameMap } from "../common/cluster-ipc"; +import { clusterFrameMap } from "../common/cluster-frames"; export class WindowManager extends Singleton { protected mainWindow: BrowserWindow; From d222c36c0ab3c57be67875f75854f46cb5007801 Mon Sep 17 00:00:00 2001 From: Jari Kolehmainen Date: Thu, 19 Nov 2020 10:45:50 +0200 Subject: [PATCH 6/6] protect syncXChannel Signed-off-by: Jari Kolehmainen --- src/common/base-store.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/common/base-store.ts b/src/common/base-store.ts index a240ac6fb0..17cc8d08e1 100644 --- a/src/common/base-store.ts +++ b/src/common/base-store.ts @@ -37,11 +37,11 @@ export class BaseStore extends Singleton { return path.basename(this.storeConfig.path); } - get syncRendererChannel() { + protected get syncRendererChannel() { return `store-sync-renderer:${this.path}` } - get syncMainChannel() { + protected get syncMainChannel() { return `store-sync-main:${this.path}` }