mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 09:48:58 -04:00
# Backport This will backport the following commits from `main` to `8.7`: - [[Infrastructure UI] Fix inventory table pagination navigation (#153849)](https://github.com/elastic/kibana/pull/153849) <!--- Backport version: 8.9.7 --> ### Questions ? Please refer to the [Backport tool documentation](https://github.com/sqren/backport) <!--BACKPORT [{"author":{"name":"Marco Antonio Ghiani","email":"marcoantonio.ghiani01@gmail.com"},"sourceCommit":{"committedDate":"2023-03-29T07:44:24Z","message":"[Infrastructure UI] Fix inventory table pagination navigation (#153849)\n\n## 📓 Summary\r\n\r\nCloses #153739 \r\n\r\nEach time the whole inventory table was rerendering due to a click on an\r\nentry, a new list of items was regenerated, reinitializing the in-memory\r\ntable component from the first page.\r\n\r\nMemoizing the generated items solves the issue and the table work as\r\nexpected.\r\n\r\nThis PR also solve another issue occurring when multiple table entries\r\nwere clicked, which resulted in many popovers opened and a blocked UI as\r\nper the following screenshot:\r\n\r\n<img width=\"1267\" alt=\"multi-popover\"\r\nsrc=\"https://user-images.githubusercontent.com/34506779/228196645-9c0444b7-9114-47c2-8e5d-0bec29ed5305.png\">\r\n\r\n## 🧪 Testing\r\n- Navigate to `Inventory` and select the `Kubernetes Pods` option from\r\nthe **Show** filter.\r\n- Switch the view to a table with the top-right selector\r\n- Verify the popover correctly opens on any entry of the first table\r\npage, then switch to different pages and check the behaviour is\r\nmaintained and there are no reinitializations for the table.\r\n- Verify the same from the `Docker Containers` list.\r\n\r\n\r\n\r\nhttps://user-images.githubusercontent.com/34506779/228198613-afafe3fe-f714-4c88-a288-fc4c95ca801a.mov\r\n\r\nCo-authored-by: Marco Antonio Ghiani <marcoantonio.ghiani@elastic.co>","sha":"f17457b86e2137f8c84171583a5291835c5b7d62","branchLabelMapping":{"^v8.8.0$":"main","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:fix","Team:Infra Monitoring UI","backport:prev-minor","v8.8.0"],"number":153849,"url":"https://github.com/elastic/kibana/pull/153849","mergeCommit":{"message":"[Infrastructure UI] Fix inventory table pagination navigation (#153849)\n\n## 📓 Summary\r\n\r\nCloses #153739 \r\n\r\nEach time the whole inventory table was rerendering due to a click on an\r\nentry, a new list of items was regenerated, reinitializing the in-memory\r\ntable component from the first page.\r\n\r\nMemoizing the generated items solves the issue and the table work as\r\nexpected.\r\n\r\nThis PR also solve another issue occurring when multiple table entries\r\nwere clicked, which resulted in many popovers opened and a blocked UI as\r\nper the following screenshot:\r\n\r\n<img width=\"1267\" alt=\"multi-popover\"\r\nsrc=\"https://user-images.githubusercontent.com/34506779/228196645-9c0444b7-9114-47c2-8e5d-0bec29ed5305.png\">\r\n\r\n## 🧪 Testing\r\n- Navigate to `Inventory` and select the `Kubernetes Pods` option from\r\nthe **Show** filter.\r\n- Switch the view to a table with the top-right selector\r\n- Verify the popover correctly opens on any entry of the first table\r\npage, then switch to different pages and check the behaviour is\r\nmaintained and there are no reinitializations for the table.\r\n- Verify the same from the `Docker Containers` list.\r\n\r\n\r\n\r\nhttps://user-images.githubusercontent.com/34506779/228198613-afafe3fe-f714-4c88-a288-fc4c95ca801a.mov\r\n\r\nCo-authored-by: Marco Antonio Ghiani <marcoantonio.ghiani@elastic.co>","sha":"f17457b86e2137f8c84171583a5291835c5b7d62"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v8.8.0","labelRegex":"^v8.8.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/153849","number":153849,"mergeCommit":{"message":"[Infrastructure UI] Fix inventory table pagination navigation (#153849)\n\n## 📓 Summary\r\n\r\nCloses #153739 \r\n\r\nEach time the whole inventory table was rerendering due to a click on an\r\nentry, a new list of items was regenerated, reinitializing the in-memory\r\ntable component from the first page.\r\n\r\nMemoizing the generated items solves the issue and the table work as\r\nexpected.\r\n\r\nThis PR also solve another issue occurring when multiple table entries\r\nwere clicked, which resulted in many popovers opened and a blocked UI as\r\nper the following screenshot:\r\n\r\n<img width=\"1267\" alt=\"multi-popover\"\r\nsrc=\"https://user-images.githubusercontent.com/34506779/228196645-9c0444b7-9114-47c2-8e5d-0bec29ed5305.png\">\r\n\r\n## 🧪 Testing\r\n- Navigate to `Inventory` and select the `Kubernetes Pods` option from\r\nthe **Show** filter.\r\n- Switch the view to a table with the top-right selector\r\n- Verify the popover correctly opens on any entry of the first table\r\npage, then switch to different pages and check the behaviour is\r\nmaintained and there are no reinitializations for the table.\r\n- Verify the same from the `Docker Containers` list.\r\n\r\n\r\n\r\nhttps://user-images.githubusercontent.com/34506779/228198613-afafe3fe-f714-4c88-a288-fc4c95ca801a.mov\r\n\r\nCo-authored-by: Marco Antonio Ghiani <marcoantonio.ghiani@elastic.co>","sha":"f17457b86e2137f8c84171583a5291835c5b7d62"}}]}] BACKPORT-->
This commit is contained in:
parent
85a8f79b88
commit
da88da012d
2 changed files with 40 additions and 56 deletions
|
@ -7,8 +7,6 @@
|
|||
|
||||
import { APP_WRAPPER_CLASS } from '@kbn/core/public';
|
||||
|
||||
export const CONTAINER_CLASSNAME = 'infra-container-element';
|
||||
|
||||
export const prepareMountElement = (element: HTMLElement, testSubject?: string) => {
|
||||
// Ensure all wrapping elements have the APP_WRAPPER_CLASS so that the KinanaPageTemplate works as expected
|
||||
element.classList.add(APP_WRAPPER_CLASS);
|
||||
|
|
|
@ -9,7 +9,7 @@ import { EuiButtonEmpty, EuiInMemoryTable, EuiToolTip, EuiBasicTableColumn } fro
|
|||
import { i18n } from '@kbn/i18n';
|
||||
|
||||
import { last, first } from 'lodash';
|
||||
import React, { useState, useCallback, useEffect } from 'react';
|
||||
import React, { useState, useMemo } from 'react';
|
||||
import { EuiPopover } from '@elastic/eui';
|
||||
import { createWaffleMapNode } from '../lib/nodes_to_wafflemap';
|
||||
import { InfraWaffleMapNode, InfraWaffleMapOptions } from '../../../../lib/lib';
|
||||
|
@ -17,7 +17,6 @@ import { fieldToName } from '../lib/field_to_display_name';
|
|||
import { NodeContextMenu } from './waffle/node_context_menu';
|
||||
import { InventoryItemType } from '../../../../../common/inventory_models/types';
|
||||
import { SnapshotNode, SnapshotNodePath } from '../../../../../common/http_api/snapshot_api';
|
||||
import { CONTAINER_CLASSNAME } from '../../../../apps/common_styles';
|
||||
|
||||
interface Props {
|
||||
nodes: SnapshotNode[];
|
||||
|
@ -28,6 +27,13 @@ interface Props {
|
|||
onFilter: (filter: string) => void;
|
||||
}
|
||||
|
||||
const initialSorting = {
|
||||
sort: {
|
||||
field: 'value',
|
||||
direction: 'desc',
|
||||
},
|
||||
} as const;
|
||||
|
||||
const getGroupPaths = (path: SnapshotNodePath[]) => {
|
||||
switch (path.length) {
|
||||
case 3:
|
||||
|
@ -41,33 +47,10 @@ const getGroupPaths = (path: SnapshotNodePath[]) => {
|
|||
|
||||
export const TableView = (props: Props) => {
|
||||
const { nodes, options, formatter, currentTime, nodeType } = props;
|
||||
const [openPopovers, setOpenPopovers] = useState<string[]>([]);
|
||||
const openPopoverFor = useCallback(
|
||||
(id: string) => () => {
|
||||
setOpenPopovers([...openPopovers, id]);
|
||||
},
|
||||
[openPopovers]
|
||||
);
|
||||
|
||||
const closePopoverFor = useCallback(
|
||||
(id: string) => () => {
|
||||
if (openPopovers.includes(id)) {
|
||||
setOpenPopovers(openPopovers.filter((subject) => subject !== id));
|
||||
}
|
||||
},
|
||||
[openPopovers]
|
||||
);
|
||||
const [openPopoverId, setOpenPopoverId] = useState<string | null>(null);
|
||||
|
||||
useEffect(() => {
|
||||
const el = document.getElementsByClassName(CONTAINER_CLASSNAME)[0];
|
||||
if (el instanceof HTMLElement) {
|
||||
if (openPopovers.length > 0) {
|
||||
el.style.overflowY = 'hidden';
|
||||
} else {
|
||||
el.style.overflowY = 'auto';
|
||||
}
|
||||
}
|
||||
}, [openPopovers]);
|
||||
const closePopover = () => setOpenPopoverId(null);
|
||||
|
||||
const columns: Array<EuiBasicTableColumn<typeof items[number]>> = [
|
||||
{
|
||||
|
@ -84,15 +67,20 @@ export const TableView = (props: Props) => {
|
|||
const uniqueID = [...item.node.path.map((p) => p.value), item.node.name].join(':');
|
||||
const button = (
|
||||
<EuiToolTip content={tooltipText}>
|
||||
<EuiButtonEmpty onClick={openPopoverFor(uniqueID)}>{value}</EuiButtonEmpty>
|
||||
<EuiButtonEmpty
|
||||
data-test-subj="infraColumnsButton"
|
||||
onClick={() => setOpenPopoverId(uniqueID)}
|
||||
>
|
||||
{value}
|
||||
</EuiButtonEmpty>
|
||||
</EuiToolTip>
|
||||
);
|
||||
|
||||
return (
|
||||
<EuiPopover
|
||||
button={button}
|
||||
isOpen={openPopovers.includes(uniqueID)}
|
||||
closePopover={closePopoverFor(uniqueID)}
|
||||
isOpen={openPopoverId === uniqueID}
|
||||
closePopover={closePopover}
|
||||
anchorPosition="rightCenter"
|
||||
>
|
||||
<NodeContextMenu
|
||||
|
@ -148,30 +136,28 @@ export const TableView = (props: Props) => {
|
|||
},
|
||||
];
|
||||
|
||||
const items = nodes.map((node) => {
|
||||
const name = last(node.path);
|
||||
const metric = first(node.metrics);
|
||||
return {
|
||||
name: (name && name.label) || 'unknown',
|
||||
...getGroupPaths(node.path).reduce(
|
||||
(acc, path, index) => ({
|
||||
...acc,
|
||||
[`group_${index}`]: path.label,
|
||||
}),
|
||||
{}
|
||||
),
|
||||
value: (metric && metric.value) || 0,
|
||||
avg: (metric && metric.avg) || 0,
|
||||
max: (metric && metric.max) || 0,
|
||||
node: createWaffleMapNode(node),
|
||||
};
|
||||
});
|
||||
const initialSorting = {
|
||||
sort: {
|
||||
field: 'value',
|
||||
direction: 'desc',
|
||||
},
|
||||
} as const;
|
||||
const items = useMemo(
|
||||
() =>
|
||||
nodes.map((node) => {
|
||||
const name = last(node.path);
|
||||
const metric = first(node.metrics);
|
||||
return {
|
||||
name: (name && name.label) || 'unknown',
|
||||
...getGroupPaths(node.path).reduce(
|
||||
(acc, path, index) => ({
|
||||
...acc,
|
||||
[`group_${index}`]: path.label,
|
||||
}),
|
||||
{}
|
||||
),
|
||||
value: (metric && metric.value) || 0,
|
||||
avg: (metric && metric.avg) || 0,
|
||||
max: (metric && metric.max) || 0,
|
||||
node: createWaffleMapNode(node),
|
||||
};
|
||||
}),
|
||||
[nodes]
|
||||
);
|
||||
|
||||
return (
|
||||
<EuiInMemoryTable pagination={true} sorting={initialSorting} items={items} columns={columns} />
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue