Skip to content

Commit 5d038bb

Browse files
committed
CNV-73283: Support for UI plugins for 3rd party integration
1 parent ac400d2 commit 5d038bb

6 files changed

Lines changed: 198 additions & 13 deletions

File tree

_topic_maps/_topic_map.yml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4855,6 +4855,8 @@ Topics:
48554855
File: virt-accessing-vm-consoles
48564856
- Name: Configuring SSH access to VMs
48574857
File: virt-accessing-vm-ssh
4858+
- Name: Customize the web console
4859+
File: virt-customize-web-console
48584860
- Name: Editing virtual machines
48594861
File: virt-edit-vms
48604862
- Name: Editing boot order
Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
// Module included in the following assemblies:
2+
//
3+
// * list assemblies
4+
5+
:_mod-docs-content-type: PROCEDURE
6+
[id="virt-create-custom-console-tabs_{context}"]
7+
= Create custom tabs in the web console
8+
9+
[role="_abstract"]
10+
As a cluster administrator, you can customize the {product-title} web console by adding customized tabs to the *Virtualization* page.
11+
12+
.Prerequisites
13+
14+
* You have created a dynamic plugin.
15+
* You have cluster administrator permissions.
16+
* You have access to an {product-title} cluster where {VirtProductName} is installed.
17+
18+
.Procedure
19+
20+
* Add the `kubevirt.tab/horizontalNav` extension to the `plugin-extensions.ts` file of the KubeVirt plugin:
21+
+
22+
[source,typescript]
23+
----
24+
{
25+
type: 'kubevirt.tab/horizontalNav',
26+
properties: {
27+
model: {
28+
version: 'v1',
29+
group: 'kubevirt.io',
30+
kind: 'VirtualMachine',
31+
},
32+
page: {
33+
name: 'Kubevirt Test',
34+
href: 'kubevirt-test',
35+
},
36+
isVisible: { $codeRef: 'isKubevirtTabVisible' },
37+
component: { $codeRef: 'KubevirtTestTab' },
38+
},
39+
}
40+
----
41+
** The `component` flag that references `KubevirtTestTab` refers to the actual tab content that you want to include.
42+
** The `isVisible` flag refers to the following example code reference:
43+
+
44+
[source,typescript]
45+
----
46+
import { K8sResourceCommon } from '@openshift-console/dynamic-plugin-sdk';
47+
48+
const isKubevirtTabVisible = ({
49+
created,
50+
}: {
51+
created: boolean;
52+
obj: K8sResourceCommon & { cluster?: string };
53+
}) => created;
54+
export default isKubevirtTabVisible;
55+
----
56+
+
57+
This parameter is provided by the KubeVirt plugin, and is `true` if the referenced object has been already created. This flag ensures that the plugin author can prevent the custom tab from being displayed on certain pages, such as the *Create Virtual Machine* page.
58+
59+
.Verification
60+
61+
. Log in to the {product-title} web console.
62+
. Go to the *Virtualization* page and verify that the custom tab you have created is visible.
63+
. Go to the *Create Virtual Machine* page and verify that your custom backup actions or tabs do not appear.
Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
// Module included in the following assemblies:
2+
//
3+
// * virt/managing_vms/virt-customize-web-console.adoc
4+
5+
:_mod-docs-content-type: PROCEDURE
6+
[id="virt-enable-bulk-operations-web-console_{context}"]
7+
= Enable bulk operations for virtual machines
8+
9+
[role="_abstract"]
10+
You can enable virtual machine (VM) owners to perform large-scale management tasks, such as backups and storage migrations, across multiple virtual machines simultaneously, by creating a dynamic plugin that enables bulk actions in the web console.
11+
12+
This integration reduces manual overhead for multi-VM environments and ensures that custom actions are available as native, selectable bulk actions from within the *Virtualization* page.
13+
14+
.Prerequisites
15+
16+
* You have created a dynamic plugin.
17+
* You have cluster administrator permissions.
18+
* You have access to an {product-title} cluster where {VirtProductName} is installed.
19+
20+
.Procedure
21+
22+
. In the configuration file of your plugin, add a `console.action/provider` extension.
23+
+
24+
To enable bulk actions, you must use a `contextId` field that targets an array of `VirtualMachine` resources.
25+
+
26+
Example `console-extensions.json` file excerpt:
27+
+
28+
[source,json]
29+
----
30+
{
31+
type: 'console.action/provider',
32+
properties: {
33+
contextId: 'kubevirt.io~v1~VirtualMachine[]',
34+
provider: {
35+
$codeRef: 'useSimpleBulkActions',
36+
},
37+
},
38+
}
39+
----
40+
** `properties.contextId` specifies a string for which the KubeVirt plugin declares support.
41+
** `properties.provider` specifies the React hook or function in your source code that generates the action items.
42+
43+
. In the source file referenced by the extension, implement a hook that handles the array of selected resources.
44+
+
45+
Example plugin:
46+
+
47+
[source,ts]
48+
----
49+
import {
50+
type ExtensionHook,
51+
AccessReviewResourceAttributes,
52+
Action,
53+
} from '@openshift-console/dynamic-plugin-sdk';
54+
import { V1VirtualMachine } from '@kubevirt-ui-ext/kubevirt-api/kubevirt';
55+
import { VirtualMachineModel } from '@kubevirt-ui-ext/kubevirt-api/console';
56+
import { useMemo } from 'react';
57+
58+
const useSimpleBulkActions: ExtensionHook<Action[], (V1VirtualMachine & { cluster?: string })[]> = (
59+
vms,
60+
) => {
61+
const areAllRunning = vms.every((vm) => vm.status?.printableStatus === 'Running');
62+
const isCrossCluster = new Set(vms.map((vm) => vm.cluster)).size > 1;
63+
const firstVm = vms[0];
64+
65+
const accessReview: AccessReviewResourceAttributes = useMemo(
66+
() => ({
67+
cluster: firstVm?.cluster,
68+
group: VirtualMachineModel.apiGroup,
69+
name: firstVm?.metadata?.name,
70+
namespace: firstVm?.metadata?.namespace,
71+
resource: VirtualMachineModel.plural,
72+
verb: 'delete',
73+
}),
74+
[firstVm?.cluster, firstVm?.metadata?.name, firstVm?.metadata?.namespace],
75+
);
76+
77+
const checkAllRunningAction: Action = useMemo(
78+
() => ({
79+
id: 'check-all-running',
80+
cta: () => console.log('All selected VMs are running?', areAllRunning),
81+
label: 'Check VMs are running',
82+
disabled: isCrossCluster,
83+
disabledTooltip: isCrossCluster ? 'VMs from different clusters detected' : '',
84+
accessReview,
85+
}),
86+
[areAllRunning, isCrossCluster, accessReview],
87+
);
88+
89+
const actions = useMemo(() => [checkAllRunningAction], [checkAllRunningAction]);
90+
return [actions, true, null];
91+
};
92+
93+
export default useSimpleBulkActions;
94+
----
95+
+
96+
The plugin shown in the previous example checks if all selected VMs are running and prints a log message to the console.
97+
98+
. Deploy the plugin to the cluster.
99+
100+
.Verification
101+
102+
. Log in to the {product-title} web console.
103+
104+
. Verify that you can apply bulk actions to VMs.
105+
.. Go to *Virtualization* -> *VirtualMachines*.
106+
.. Select the checkboxes for two or more existing VMs.
107+
.. Click the *Actions* drop-down menu. Confirm that you can run the custom action you created.
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
:_mod-docs-content-type: ASSEMBLY
2+
include::_attributes/common-attributes.adoc[]
3+
[id="virt-customize-web-console"]
4+
= Customize the web console
5+
:context: virt-customize-web-console
6+
7+
toc::[]
8+
9+
[role="_abstract"]
10+
As a cluster administrator, you can customize the {product-title} web console by integrating xref:../../web_console/dynamic-plugin/overview-dynamic-plugin.adoc#overview-dynamic-plugin[dynamic plugins]. Virtual machine (VM) owners can then use the actions provided by these plugins from different tabs on the *Virtualization* page.
11+
12+
include::modules/virt-enable-bulk-operations-web-console.adoc[leveloffset=+1]
13+
14+
include::modules/virt-create-custom-console-tabs.adoc[leveloffset=+1]
15+
16+
[role="_additional-resources"]
17+
== Additional resources
18+
* xref:../../web_console/dynamic-plugin/dynamic-plugins-get-started.adoc#dynamic-plugins-get-started[Getting started with dynamic plugins]

web_console/dynamic-plugin/dynamic-plugins-get-started.adoc

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,8 @@
11
:_mod-docs-content-type: ASSEMBLY
2-
[id="dynamic-plugins-get-started_{context}"]
3-
= Getting started with dynamic plugins
4-
52
include::_attributes/common-attributes.adoc[]
63
include::_attributes/attributes-openshift-dedicated.adoc[]
4+
[id="dynamic-plugins-get-started_{context}"]
5+
= Getting started with dynamic plugins
76
:context: dynamic-plugins-get-started
87

98
toc::[]

web_console/dynamic-plugin/overview-dynamic-plugin.adoc

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,12 @@
11
:_mod-docs-content-type: ASSEMBLY
2-
[id="overview-of-dynamic-plugins_{context}"]
3-
= Overview of dynamic plugins
4-
52
include::_attributes/common-attributes.adoc[]
63
include::_attributes/attributes-openshift-dedicated.adoc[]
7-
:context: overview-of-dynamic-plugins
4+
[id="overview-dynamic-plugin_{context}"]
5+
= Overview of dynamic plugins
6+
:context: overview-dynamic-plugin
87

98
toc::[]
109

11-
[id="dynamic-plug-in-overview"]
12-
== About dynamic plugins
13-
1410
[role="_abstract"]
1511
Dynamic plugins are loaded and interpreted from remote sources at runtime. One way to deliver and expose dynamic plugins to the console is through OLM Operators. The Operator creates a deployment on the platform with an HTTP server to host the plugin and exposes it using a Kubernetes service.
1612

@@ -57,8 +53,8 @@ When creating your plugin, follow these guidelines for using PatternFly:
5753

5854
* Use link:https://www.patternfly.org/components/all-components/[PatternFly] components and PatternFly CSS variables. Core PatternFly components are available through the SDK. Using PatternFly components and variables help your plugin look consistent in future console versions.
5955
ifndef::openshift-rosa-hcp[]
60-
** Use PatternFly 4.x if you are using {product-title} versions 4.14 and earlier.
61-
** Use PatternFly 5.x if you are using {product-title} versions 4.15 through 4.18.
56+
** Use PatternFly 4.x if you are using {product-title} versions 4.14 and earlier.
57+
** Use PatternFly 5.x if you are using {product-title} versions 4.15 through 4.18.
6258
** Use PatternFly 6.x if you are using {product-title} versions 4.19 and later.
6359

6460
endif::openshift-rosa-hcp[]
@@ -69,4 +65,4 @@ endif::openshift-rosa-hcp[]
6965
* Avoid using other CSS libraries such as Bootstrap or Tailwind. They might conflict with PatternFly and not match the rest of the console. Plugins should only include styles that are specific to their user interfaces to be evaluated on top of base PatternFly styles. Do not import styles directly from `@patternfly/react-styles/**/*.css` or `@patternfly/patternfly`. Instead, use components and CSS variables provided by the console SDK.
7066
* The console application is responsible for loading base styles for all supported PatternFly versions.
7167

72-
include::modules/dynamic-plugin-localization.adoc[leveloffset=+2]
68+
include::modules/dynamic-plugin-localization.adoc[leveloffset=+2]

0 commit comments

Comments
 (0)