Skip to content

Commit 4588b22

Browse files
committed
feat: Nodes
1 parent f476783 commit 4588b22

File tree

14 files changed

+118
-19
lines changed

14 files changed

+118
-19
lines changed

src/components/nodesColumns/columns.tsx

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,16 @@ export function getRackColumn<T extends {Rack?: string}>(): Column<T> {
110110
width: 100,
111111
};
112112
}
113+
114+
export function getPileNameColumn<T extends {PileName?: string}>(): Column<T> {
115+
return {
116+
name: NODES_COLUMNS_IDS.PileName,
117+
header: i18n('PileName'),
118+
align: DataTable.LEFT,
119+
render: ({row}) => row.PileName || EMPTY_DATA_PLACEHOLDER,
120+
width: 100,
121+
};
122+
}
113123
export function getVersionColumn<T extends {Version?: string}>(): Column<T> {
114124
return {
115125
name: NODES_COLUMNS_IDS.Version,

src/components/nodesColumns/constants.ts

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ export const NODES_COLUMNS_IDS = {
3232
Missing: 'Missing',
3333
Tablets: 'Tablets',
3434
PDisks: 'PDisks',
35+
PileName: 'PileName',
3536
} as const;
3637

3738
export type NodesColumnId = ValueOf<typeof NODES_COLUMNS_IDS>;
@@ -130,6 +131,9 @@ export const NODES_COLUMNS_TITLES = {
130131
get PDisks() {
131132
return i18n('pdisks');
132133
},
134+
get PileName() {
135+
return i18n('PileName');
136+
},
133137
} as const satisfies Record<NodesColumnId, string>;
134138

135139
const NODES_COLUMNS_GROUP_BY_TITLES = {
@@ -178,6 +182,9 @@ const NODES_COLUMNS_GROUP_BY_TITLES = {
178182
get PingTime() {
179183
return i18n('ping-time');
180184
},
185+
get PileName() {
186+
return i18n('PileName');
187+
},
181188
} as const satisfies Record<NodesGroupByField, string>;
182189

183190
export function getNodesGroupByFieldTitle(groupByField: NodesGroupByField) {
@@ -213,6 +220,7 @@ export const NODES_COLUMNS_TO_DATA_FIELDS: Record<NodesColumnId, NodesRequiredFi
213220
Missing: ['Missing'],
214221
Tablets: ['Tablets', 'Database'],
215222
PDisks: ['PDisks'],
223+
PileName: ['PileName'],
216224
};
217225

218226
const NODES_COLUMNS_TO_SORT_FIELDS: Record<NodesColumnId, NodesSortValue | undefined> = {
@@ -242,6 +250,7 @@ const NODES_COLUMNS_TO_SORT_FIELDS: Record<NodesColumnId, NodesSortValue | undef
242250
Missing: 'Missing',
243251
Tablets: undefined,
244252
PDisks: undefined,
253+
PileName: undefined,
245254
};
246255

247256
export function getNodesColumnSortField(columnId?: string) {

src/components/nodesColumns/i18n/en.json

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,10 +18,9 @@
1818
"sessions": "Sessions",
1919
"missing": "Missing",
2020
"pdisks": "PDisks",
21-
2221
"field_memory-used": "Memory used",
2322
"field_memory-limit": "Memory limit",
24-
23+
"PileName": "Pile Name",
2524
"system-state": "System State",
2625
"connect-status": "Connect Status",
2726
"utilization": "Utilization",
@@ -33,7 +32,6 @@
3332
"ping": "Ping",
3433
"send": "Send",
3534
"receive": "Receive",
36-
3735
"max": "Max",
3836
"min": "Min",
3937
"avg": "Avg",

src/containers/Cluster/ClusterInfo/ClusterInfo.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,7 @@ export const ClusterInfo = ({
9999
}
100100
return (
101101
<InfoSection>
102-
<Flex gap={6} width="full">
102+
<Flex gap={10} width="full">
103103
<Flex direction="column" gap={2}>
104104
<Text as="div" variant="subheader-2" className={b('section-title')}>
105105
{i18n('title_storage-groups')}{' '}

src/containers/Cluster/i18n/en.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
"title_network": "Network",
1818
"title_links": "Links",
1919
"title_details": "Details",
20-
"title_bridge": "Bridge",
20+
"title_bridge": "Bridge Piles",
2121
"label_overview": "Overview",
2222
"label_load": "Load",
2323
"label_name": "Name",

src/containers/Nodes/Nodes.tsx

Lines changed: 59 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,15 @@
11
import React from 'react';
22

33
import type {Column} from '../../components/PaginatedTable';
4+
import {getPileNameColumn} from '../../components/nodesColumns/columns';
45
import {
6+
NODES_COLUMNS_IDS,
57
isMonitoringUserNodesColumn,
8+
isSortableNodesColumn,
69
isViewerUserNodesColumn,
710
} from '../../components/nodesColumns/constants';
811
import type {NodesColumnId} from '../../components/nodesColumns/constants';
12+
import {useBridgeModeEnabled} from '../../store/reducers/capabilities/hooks';
913
import type {NodesPreparedEntity} from '../../store/reducers/nodes/types';
1014
import type {AdditionalNodesProps} from '../../types/additionalProps';
1115
import type {NodesGroupByField} from '../../types/api/nodes';
@@ -50,21 +54,71 @@ export function Nodes({
5054
selectedColumnsKey = NODES_TABLE_SELECTED_COLUMNS_LS_KEY,
5155
groupByParams = ALL_NODES_GROUP_BY_PARAMS,
5256
}: NodesProps) {
57+
const bridgeModeEnabled = useBridgeModeEnabled();
58+
59+
const columnsWithPile = React.useMemo(() => {
60+
if (!bridgeModeEnabled) {
61+
return columns;
62+
}
63+
64+
const hasPile = columns.some((c) => c.name === NODES_COLUMNS_IDS.PileName);
65+
if (hasPile) {
66+
return columns;
67+
}
68+
69+
const pileColumn = getPileNameColumn<NodesPreparedEntity>();
70+
// Type trick above is irrelevant at runtime; cast to any and enhance with sortable
71+
const enhancedPileColumn = {
72+
...pileColumn,
73+
sortable: isSortableNodesColumn(NODES_COLUMNS_IDS.PileName),
74+
} as (typeof columns)[number];
75+
76+
const rackIndex = columns.findIndex((c) => c.name === NODES_COLUMNS_IDS.Rack);
77+
const dcIndex = columns.findIndex((c) => c.name === NODES_COLUMNS_IDS.DC);
78+
let insertIndex = columns.length;
79+
if (rackIndex !== -1) {
80+
insertIndex = rackIndex;
81+
} else if (dcIndex !== -1) {
82+
insertIndex = dcIndex + 1;
83+
}
84+
85+
const next = columns.slice();
86+
next.splice(insertIndex, 0, enhancedPileColumn);
87+
return next;
88+
}, [bridgeModeEnabled, columns]);
89+
90+
const effectiveDefaultColumns = React.useMemo(() => {
91+
if (!bridgeModeEnabled) {
92+
return defaultColumnsIds;
93+
}
94+
return defaultColumnsIds.includes(NODES_COLUMNS_IDS.PileName)
95+
? defaultColumnsIds
96+
: [...defaultColumnsIds, NODES_COLUMNS_IDS.PileName];
97+
}, [bridgeModeEnabled, defaultColumnsIds]);
5398
const isUserAllowedToMakeChanges = useIsUserAllowedToMakeChanges();
5499
const isViewerUser = useIsViewerUser();
55100

56101
const preparedColumns = React.useMemo(() => {
57102
if (isUserAllowedToMakeChanges) {
58-
return columns;
103+
return columnsWithPile;
59104
}
60-
const filteredColumns = columns.filter(
105+
const filteredColumns = columnsWithPile.filter(
61106
(column) => !isMonitoringUserNodesColumn(column.name),
62107
);
63108
if (isViewerUser) {
64109
return filteredColumns;
65110
}
66111
return filteredColumns.filter((column) => !isViewerUserNodesColumn(column.name));
67-
}, [columns, isUserAllowedToMakeChanges, isViewerUser]);
112+
}, [columnsWithPile, isUserAllowedToMakeChanges, isViewerUser]);
113+
114+
const effectiveGroupByParams = React.useMemo(() => {
115+
if (!bridgeModeEnabled || !groupByParams) {
116+
return groupByParams;
117+
}
118+
return groupByParams.includes('PileName')
119+
? groupByParams
120+
: ([...groupByParams, 'PileName'] as NodesGroupByField[]);
121+
}, [bridgeModeEnabled, groupByParams]);
68122

69123
return (
70124
<PaginatedNodes
@@ -73,10 +127,10 @@ export function Nodes({
73127
scrollContainerRef={scrollContainerRef}
74128
withPeerRoleFilter={withPeerRoleFilter}
75129
columns={preparedColumns}
76-
defaultColumnsIds={defaultColumnsIds}
130+
defaultColumnsIds={effectiveDefaultColumns}
77131
requiredColumnsIds={requiredColumnsIds}
78132
selectedColumnsKey={selectedColumnsKey}
79-
groupByParams={groupByParams}
133+
groupByParams={effectiveGroupByParams}
80134
/>
81135
);
82136
}

src/containers/Nodes/columns/columns.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ export function getNodesColumns(params: GetNodesColumnsParams): Column<NodesPrep
2424
getHostColumn<NodesPreparedEntity>(params),
2525
getNodeNameColumn<NodesPreparedEntity>(),
2626
getDataCenterColumn<NodesPreparedEntity>(),
27+
// PileName will be added conditionally by callers based on capability
2728
getRackColumn<NodesPreparedEntity>(),
2829
getUptimeColumn<NodesPreparedEntity>(),
2930
getCpuColumn<NodesPreparedEntity>(),

src/containers/Storage/PaginatedStorageNodesTable/columns/columns.tsx

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import {
99
getMissingDisksColumn,
1010
getNodeIdColumn,
1111
getNodeNameColumn,
12+
getPileNameColumn,
1213
getPoolsColumn,
1314
getRAMColumn,
1415
getRackColumn,
@@ -86,6 +87,7 @@ export const getStorageNodesColumns = ({
8687
getHostColumn<PreparedStorageNode>({getNodeRef, database}),
8788
getNodeNameColumn<PreparedStorageNode>(),
8889
getDataCenterColumn<PreparedStorageNode>(),
90+
getPileNameColumn<PreparedStorageNode>(),
8991
getRackColumn<PreparedStorageNode>(),
9092
getUptimeColumn<PreparedStorageNode>(),
9193
getCpuColumn<PreparedStorageNode>(),

src/containers/Storage/PaginatedStorageNodesTable/columns/hooks.ts

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import {
44
NODES_COLUMNS_IDS,
55
NODES_COLUMNS_TITLES,
66
} from '../../../../components/nodesColumns/constants';
7+
import {useBridgeModeEnabled} from '../../../../store/reducers/capabilities/hooks';
78
import {VISIBLE_ENTITIES} from '../../../../store/reducers/storage/constants';
89
import {useSelectedColumns} from '../../../../utils/hooks/useSelectedColumns';
910

@@ -31,18 +32,29 @@ export function useStorageNodesSelectedColumns({
3132
});
3233
}, [database, additionalNodesProps, viewContext, columnsSettings]);
3334

35+
const bridgeModeEnabled = useBridgeModeEnabled();
36+
3437
const requiredColumns = React.useMemo(() => {
3538
if (visibleEntities === VISIBLE_ENTITIES.missing) {
3639
return [...REQUIRED_STORAGE_NODES_COLUMNS, NODES_COLUMNS_IDS.Missing];
3740
}
3841
return REQUIRED_STORAGE_NODES_COLUMNS;
3942
}, [visibleEntities]);
4043

44+
const defaultColumns = React.useMemo(() => {
45+
if (!bridgeModeEnabled) {
46+
return DEFAULT_STORAGE_NODES_COLUMNS;
47+
}
48+
return DEFAULT_STORAGE_NODES_COLUMNS.includes(NODES_COLUMNS_IDS.PileName)
49+
? DEFAULT_STORAGE_NODES_COLUMNS
50+
: [...DEFAULT_STORAGE_NODES_COLUMNS, NODES_COLUMNS_IDS.PileName];
51+
}, [bridgeModeEnabled]);
52+
4153
return useSelectedColumns(
4254
columns,
4355
STORAGE_NODES_SELECTED_COLUMNS_LS_KEY,
4456
NODES_COLUMNS_TITLES,
45-
DEFAULT_STORAGE_NODES_COLUMNS,
57+
defaultColumns,
4658
requiredColumns,
4759
);
4860
}

src/containers/Versions/NodesTable/NodesTable.tsx

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import {
66
getHostColumn,
77
getLoadAverageColumn,
88
getNodeIdColumn,
9+
getPileNameColumn,
910
getRAMColumn,
1011
getUptimeColumn,
1112
} from '../../../components/nodesColumns/columns';
@@ -18,12 +19,13 @@ const VERSIONS_COLUMNS_WIDTH_LS_KEY = 'versionsTableColumnsWidth';
1819

1920
function getColumns(params: GetNodesColumnsParams): Column<NodesPreparedEntity>[] {
2021
return [
21-
getNodeIdColumn(),
22-
getHostColumn(params),
23-
getUptimeColumn(),
24-
getRAMColumn(),
25-
getCpuColumn(),
26-
getLoadAverageColumn(),
22+
getNodeIdColumn<NodesPreparedEntity>(),
23+
getHostColumn<NodesPreparedEntity>(params),
24+
getPileNameColumn<NodesPreparedEntity>(),
25+
getUptimeColumn<NodesPreparedEntity>(),
26+
getRAMColumn<NodesPreparedEntity>(),
27+
getCpuColumn<NodesPreparedEntity>(),
28+
getLoadAverageColumn<NodesPreparedEntity>(),
2729
];
2830
}
2931

0 commit comments

Comments
 (0)