diff --git a/package.json b/package.json index 7748042..24c929b 100644 --- a/package.json +++ b/package.json @@ -316,12 +316,12 @@ }, { "command": "vscode-kafka.explorer.deleteselected", - "when": "view == kafkaExplorer && viewItem =~ /^cluster$|^topic$/ && !listMultiSelection", + "when": "view == kafkaExplorer && viewItem =~ /^cluster$|^selectedCluster$|^topic$/ && !listMultiSelection", "group": "inline" }, { "command": "vscode-kafka.explorer.deleteselected", - "when": "view == kafkaExplorer && viewItem =~ /^cluster$|^topic$/ && !listMultiSelection", + "when": "view == kafkaExplorer && viewItem =~ /^cluster$|^selectedCluster$|^topic$/ && !listMultiSelection", "group": "3_modification" } ], diff --git a/src/constants.ts b/src/constants.ts index b4e9d2c..62b03b9 100644 --- a/src/constants.ts +++ b/src/constants.ts @@ -48,6 +48,11 @@ export class Icons { } } + +export enum GlyphChars { + Check = '\u2713' +} + export class CommonMessages { public static showNoSelectedCluster(): void { vscode.window.showInformationMessage("No cluster selected"); diff --git a/src/explorer/kafkaExplorer.ts b/src/explorer/kafkaExplorer.ts index 1e21a4e..4af3529 100644 --- a/src/explorer/kafkaExplorer.ts +++ b/src/explorer/kafkaExplorer.ts @@ -8,6 +8,7 @@ import { KafkaModel } from "./models/kafka"; import { ClusterItem } from "./models/cluster"; import { EOL } from 'os'; import { TopicItem } from "./models/topics"; +import { SelectedClusterChangedEvent } from "../settings/clusters"; const TREEVIEW_ID = 'kafkaExplorer'; @@ -39,8 +40,10 @@ export class KafkaExplorer implements vscode.Disposable, vscode.TreeDataProvider treeDataProvider: this, canSelectMany: true }); + this.clusterSettings.onDidChangeSelected((e) => { + this.updateClusterSelection(e); + }); } - public refresh(): void { // reset the kafka model this.root = null; @@ -155,4 +158,16 @@ export class KafkaExplorer implements vscode.Disposable, vscode.TreeDataProvider } } } + + private async updateClusterSelection(e: SelectedClusterChangedEvent): Promise { + const oldSelection = e.oldClusterId ? (await this.root?.findClusterItemById(e.oldClusterId)) : undefined; + if (oldSelection != undefined) { + this.onDidChangeTreeDataEvent.fire(oldSelection); + } + const newSelection = e.newClusterId ? (await this.root?.findClusterItemById(e.newClusterId)) : undefined; + if (newSelection != undefined) { + this.onDidChangeTreeDataEvent.fire(newSelection); + } + } + } diff --git a/src/explorer/models/cluster.ts b/src/explorer/models/cluster.ts index 880dd55..361c608 100644 --- a/src/explorer/models/cluster.ts +++ b/src/explorer/models/cluster.ts @@ -8,6 +8,7 @@ import { TopicGroupItem, TopicItem } from "./topics"; import { ConsumerGroupsItem } from "./consumerGroups"; import { KafkaModel } from "./kafka"; import { Disposable } from "vscode"; +import { GlyphChars } from "../../constants"; const TOPIC_INDEX = 1; @@ -15,7 +16,7 @@ export class ClusterItem extends NodeBase implements Disposable { public contextValue = "cluster"; public collapsibleState = vscode.TreeItemCollapsibleState.Collapsed; - constructor(public client: Client, public cluster: Cluster, parent: KafkaModel) { + constructor(public client: Client, public readonly cluster: Cluster, parent: KafkaModel) { super(parent); this.label = cluster.name; this.description = cluster.bootstrap; @@ -32,6 +33,22 @@ export class ClusterItem extends NodeBase implements Disposable { return super.getParent(); } + getTreeItem(): vscode.TreeItem { + const treeItem = super.getTreeItem(); + treeItem.id = this.cluster.name; + if (this.selected) { + treeItem.contextValue = 'selectedCluster'; + treeItem.label = GlyphChars.Check + ' ' + treeItem.label; + } else { + treeItem.contextValue = 'cluster'; + } + return treeItem; + } + + public get selected(): boolean { + return (this.getParent().clusterSettings.selected?.name === this.cluster.name); + } + public dispose(): void { this.client.dispose(); } @@ -60,14 +77,14 @@ export class NoClusterItem extends NodeBase { super(parent); this.label = 'Click here to add a cluster'; } - getTreeItem():vscode.TreeItem { + getTreeItem(): vscode.TreeItem { return { label: this.label, contextValue: this.contextValue, description: this.description, - command : { + command: { title: 'Add a cluster', - command:"vscode-kafka.explorer.addcluster" + command: "vscode-kafka.explorer.addcluster" } } } diff --git a/src/explorer/models/kafka.ts b/src/explorer/models/kafka.ts index 4d6cc45..ff828c3 100644 --- a/src/explorer/models/kafka.ts +++ b/src/explorer/models/kafka.ts @@ -10,7 +10,7 @@ export class KafkaModel extends NodeBase implements Disposable { public collapsibleState = TreeItemCollapsibleState.Collapsed; constructor( - protected clusterSettings: ClusterSettings, + public readonly clusterSettings: ClusterSettings, protected clientAccessor: ClientAccessor) { super(undefined); } @@ -42,4 +42,11 @@ export class KafkaModel extends NodeBase implements Disposable { clusters.find(child => (child).cluster.name === clusterName) ); } + + async findClusterItemById(clusterId: string): Promise { + return this.getChildren() + .then(clusters => + clusters.find(child => (child).cluster.id === clusterId) + ); + } } diff --git a/src/settings/clusters.ts b/src/settings/clusters.ts index 81a7165..1de6d50 100644 --- a/src/settings/clusters.ts +++ b/src/settings/clusters.ts @@ -2,7 +2,8 @@ import * as vscode from "vscode"; import { Cluster } from "../client"; import { Context } from "../context"; -interface SelectedClusterChangedEvent { +export interface SelectedClusterChangedEvent { + oldClusterId?: string, newClusterId?: string; } @@ -72,8 +73,9 @@ class MementoClusterSettings implements ClusterSettings { } set selected(value: Cluster | undefined) { + const oldClusterId = this.selected?.id; this.storage.update(this.selectedClusterIdStorageKey, value?.id); - this.onDidChangeSelectedEmitter.fire({ newClusterId: value?.id }); + this.onDidChangeSelectedEmitter.fire({ oldClusterId : oldClusterId, newClusterId: value?.id }); } getAll(): Cluster[] { @@ -122,4 +124,4 @@ class MementoClusterSettings implements ClusterSettings { } } -export const getClusterSettings = (): ClusterSettings => MementoClusterSettings.getInstance(); \ No newline at end of file +export const getClusterSettings = (): ClusterSettings => MementoClusterSettings.getInstance();