ydb-embedded-ui 6.3.0 → 6.4.0
Sign up to get free protection for your applications and to get access to all the features.
- package/README.md +38 -16
- package/dist/assets/icons/disableFullscreen.svg +4 -0
- package/dist/assets/icons/emptyState.svg +13 -0
- package/dist/assets/icons/key.svg +6 -0
- package/dist/assets/icons/monitoring.svg +9 -0
- package/dist/assets/icons/network.svg +21 -0
- package/dist/components/BasicNodeViewer/BasicNodeViewer.js +11 -5
- package/dist/components/CriticalActionDialog/CriticalActionDialog.js +3 -4
- package/dist/components/CriticalActionDialog/CriticalActionDialog.scss +2 -0
- package/dist/components/EmptyState/EmptyState.js +3 -2
- package/dist/components/EnableFullscreenButton/EnableFullscreenButton.js +3 -3
- package/dist/components/Fullscreen/Fullscreen.js +3 -3
- package/dist/components/MonitoringButton/MonitoringButton.js +3 -3
- package/dist/components/NodeHostWrapper/NodeHostWrapper.js +3 -3
- package/dist/components/PDiskInfo/i18n/index.d.ts +1 -1
- package/dist/components/QueryExecutionStatus/QueryExecutionStatus.js +4 -5
- package/dist/components/StatusIcon/StatusIcon.js +5 -7
- package/dist/containers/App/App.js +1 -2
- package/dist/containers/AsideNavigation/AsideNavigation.js +4 -9
- package/dist/containers/AsideNavigation/YdbInternalUser/YdbInternalUser.js +2 -3
- package/dist/containers/AsideNavigation/useNavigationMenuItems.js +5 -6
- package/dist/containers/Authentication/Authentication.js +2 -4
- package/dist/containers/Node/NodeStructure/Pdisk.js +4 -4
- package/dist/containers/Nodes/Nodes.js +19 -15
- package/dist/containers/Nodes/VirtualNodes.js +23 -6
- package/dist/containers/PDiskPage/PDiskPage.js +2 -2
- package/dist/containers/PDiskPage/i18n/index.d.ts +1 -1
- package/dist/containers/Storage/Storage.js +50 -22
- package/dist/containers/Storage/StorageGroups/getStorageGroupsColumns.js +2 -2
- package/dist/containers/Storage/VirtualStorage.js +32 -10
- package/dist/containers/Storage/utils/index.d.ts +4 -1
- package/dist/containers/Storage/utils/index.js +29 -0
- package/dist/containers/Tablet/Tablet.js +3 -3
- package/dist/containers/Tablet/i18n/index.d.ts +1 -1
- package/dist/containers/Tablets/Tablets.d.ts +1 -2
- package/dist/containers/Tablets/Tablets.js +112 -53
- package/dist/containers/Tablets/i18n/en.json +9 -4
- package/dist/containers/Tablets/i18n/index.d.ts +1 -1
- package/dist/containers/Tablets/i18n/index.js +1 -2
- package/dist/containers/Tenant/Diagnostics/Diagnostics.js +5 -5
- package/dist/containers/Tenant/Diagnostics/HotKeys/HotKeys.js +3 -2
- package/dist/containers/Tenant/Diagnostics/Network/Network.js +3 -3
- package/dist/containers/Tenant/Diagnostics/TenantOverview/Healthcheck/HealthcheckPreview.js +2 -2
- package/dist/containers/Tenant/ObjectGeneral/ObjectGeneral.js +2 -8
- package/dist/containers/Tenant/ObjectSummary/ObjectSummary.js +3 -3
- package/dist/containers/Tenant/Query/ExplainResult/ExplainResult.js +1 -1
- package/dist/containers/Tenant/Query/Issues/Issues.js +6 -9
- package/dist/containers/Tenant/Query/Preview/Preview.js +3 -3
- package/dist/containers/Tenant/Query/QueryEditor/QueryEditor.d.ts +1 -1
- package/dist/containers/Tenant/Query/QueryEditorControls/QueryEditorControls.js +4 -4
- package/dist/containers/Tenant/Query/SavedQueries/SavedQueries.js +3 -3
- package/dist/containers/Tenant/Schema/SchemaViewer/helpers.js +3 -2
- package/dist/containers/Tenant/utils/ToggleButton.scss +0 -2
- package/dist/containers/Tenant/utils/paneVisibilityToggleHelpers.js +4 -4
- package/dist/containers/Tenant/utils/schemaControls.js +3 -3
- package/dist/containers/VDiskPage/VDiskPage.js +2 -2
- package/dist/containers/VDiskPage/i18n/index.d.ts +1 -1
- package/dist/routes.d.ts +1 -1
- package/dist/services/settings.d.ts +18 -1
- package/dist/store/configureStore.d.ts +0 -8
- package/dist/store/defaultStore.d.ts +0 -4
- package/dist/store/reducers/authentication/authentication.d.ts +0 -6
- package/dist/store/reducers/executeQuery.d.ts +0 -2
- package/dist/store/reducers/explainQuery.d.ts +0 -4
- package/dist/store/reducers/healthcheckInfo/healthcheckInfo.d.ts +0 -40
- package/dist/store/reducers/host.d.ts +0 -2
- package/dist/store/reducers/index.d.ts +0 -6
- package/dist/store/reducers/index.js +0 -4
- package/dist/store/reducers/node/selectors.d.ts +0 -2
- package/dist/store/reducers/nodes/nodes.d.ts +1 -5
- package/dist/store/reducers/nodes/nodes.js +0 -27
- package/dist/store/reducers/nodes/types.d.ts +4 -13
- package/dist/store/reducers/nodesList.d.ts +0 -2
- package/dist/store/reducers/schema/schema.d.ts +0 -2
- package/dist/store/reducers/schemaAcl/schemaAcl.d.ts +0 -2
- package/dist/store/reducers/storage/selectors.d.ts +2 -17
- package/dist/store/reducers/storage/selectors.js +1 -36
- package/dist/store/reducers/storage/storage.d.ts +2 -6
- package/dist/store/reducers/storage/storage.js +0 -44
- package/dist/store/reducers/storage/types.d.ts +15 -22
- package/dist/store/reducers/storage/types.js +4 -1
- package/dist/store/reducers/tablets.d.ts +92 -1
- package/dist/store/reducers/tablets.js +16 -1
- package/dist/store/reducers/tabletsFilters.d.ts +0 -2
- package/dist/store/reducers/tenant/tenant.d.ts +2 -2
- package/dist/store/reducers/tenant/tenant.js +10 -1
- package/dist/store/reducers/tenant/types.d.ts +8 -3
- package/dist/store/reducers/tenant/types.js +3 -1
- package/dist/store/reducers/tenants/selectors.d.ts +0 -18
- package/dist/store/reducers/tenants/utils.d.ts +4 -4
- package/dist/store/reducers/tenants/utils.js +8 -8
- package/dist/store/reducers/topic.d.ts +0 -30
- package/dist/store/state-url-mapping.js +0 -22
- package/dist/utils/nodes.d.ts +2 -0
- package/dist/utils/nodes.js +4 -0
- package/dist/utils/tablet.d.ts +2 -0
- package/dist/utils/tablet.js +14 -0
- package/package.json +3 -2
- package/dist/assets/icons/bug.svg +0 -1
- package/dist/assets/icons/circle-exclamation.svg +0 -1
- package/dist/assets/icons/circle-info.svg +0 -1
- package/dist/assets/icons/circle-xmark.svg +0 -1
- package/dist/assets/icons/close.svg +0 -1
- package/dist/assets/icons/control-menu-button.svg +0 -1
- package/dist/assets/icons/dots.svg +0 -1
- package/dist/assets/icons/hide.svg +0 -1
- package/dist/assets/icons/question.svg +0 -1
- package/dist/assets/icons/server.svg +0 -1
- package/dist/assets/icons/settings-with-dot.svg +0 -1
- package/dist/assets/icons/settings.svg +0 -1
- package/dist/assets/icons/shield.svg +0 -3
- package/dist/assets/icons/show.svg +0 -1
- package/dist/assets/icons/signIn.svg +0 -1
- package/dist/assets/icons/signOut.svg +0 -1
- package/dist/assets/icons/storage.svg +0 -1
- package/dist/assets/icons/support.svg +0 -1
- package/dist/assets/icons/triangle-exclamation.svg +0 -1
- package/dist/assets/icons/update-arrow.svg +0 -6
- package/dist/components/Icon/Icon.d.ts +0 -14
- package/dist/components/Icon/Icon.js +0 -16
- package/dist/components/Icon/index.d.ts +0 -1
- package/dist/components/Icon/index.js +0 -1
- package/dist/containers/AppIcons/AppIcons.d.ts +0 -2
- package/dist/containers/AppIcons/AppIcons.js +0 -9
- package/dist/containers/Tablets/Tablets.scss +0 -35
- package/dist/containers/Tablets/i18n/ru.json +0 -6
@@ -2,6 +2,7 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
2
|
import React from 'react';
|
3
3
|
import { ASCENDING } from '@gravity-ui/react-data-table/build/esm/lib/constants';
|
4
4
|
import { skipToken } from '@reduxjs/toolkit/query';
|
5
|
+
import { StringParam, useQueryParams } from 'use-query-params';
|
5
6
|
import { EntitiesCount } from '../../components/EntitiesCount';
|
6
7
|
import { AccessDenied } from '../../components/Errors/403';
|
7
8
|
import { ResponseError } from '../../components/Errors/ResponseError';
|
@@ -11,21 +12,27 @@ import { ResizeableDataTable } from '../../components/ResizeableDataTable/Resize
|
|
11
12
|
import { Search } from '../../components/Search';
|
12
13
|
import { TableWithControlsLayout } from '../../components/TableWithControlsLayout/TableWithControlsLayout';
|
13
14
|
import { UptimeFilter } from '../../components/UptimeFIlter';
|
14
|
-
import { nodesApi
|
15
|
+
import { nodesApi } from '../../store/reducers/nodes/nodes';
|
15
16
|
import { filterNodes } from '../../store/reducers/nodes/selectors';
|
16
17
|
import { ProblemFilterValues, changeFilter } from '../../store/reducers/settings/settings';
|
17
18
|
import { cn } from '../../utils/cn';
|
18
19
|
import { DEFAULT_POLLING_INTERVAL, DEFAULT_TABLE_SETTINGS, USE_NODES_ENDPOINT_IN_DIAGNOSTICS_KEY, } from '../../utils/constants';
|
19
20
|
import { useSetting, useTableSort, useTypedDispatch, useTypedSelector } from '../../utils/hooks';
|
20
|
-
import { NodesUptimeFilterValues, isSortableNodesProperty, isUnavailableNode, } from '../../utils/nodes';
|
21
|
+
import { NodesUptimeFilterValues, isSortableNodesProperty, isUnavailableNode, nodesUptimeFilterValuesSchema, } from '../../utils/nodes';
|
21
22
|
import { NODES_COLUMNS_WIDTH_LS_KEY, getNodesColumns } from './getNodesColumns';
|
22
23
|
import i18n from './i18n';
|
23
24
|
import './Nodes.scss';
|
24
25
|
const b = cn('ydb-nodes');
|
25
26
|
export const Nodes = ({ path, additionalNodesProps = {} }) => {
|
27
|
+
var _a;
|
28
|
+
const [queryParams, setQueryParams] = useQueryParams({
|
29
|
+
uptimeFilter: StringParam,
|
30
|
+
search: StringParam,
|
31
|
+
});
|
32
|
+
const uptimeFilter = nodesUptimeFilterValuesSchema.parse(queryParams.uptimeFilter);
|
33
|
+
const searchValue = (_a = queryParams.search) !== null && _a !== void 0 ? _a : '';
|
26
34
|
const dispatch = useTypedDispatch();
|
27
35
|
const isClusterNodes = !path;
|
28
|
-
const { uptimeFilter, searchValue, sortOrder = ASCENDING, sortValue = 'NodeId', } = useTypedSelector((state) => state.nodes);
|
29
36
|
const problemFilter = useTypedSelector((state) => state.settings.problemFilter);
|
30
37
|
const { autorefresh } = useTypedSelector((state) => state.schema);
|
31
38
|
const [useNodesEndpoint] = useSetting(USE_NODES_ENDPOINT_IN_DIAGNOSTICS_KEY);
|
@@ -39,25 +46,22 @@ export const Nodes = ({ path, additionalNodesProps = {} }) => {
|
|
39
46
|
pollingInterval: autoRefreshInterval,
|
40
47
|
});
|
41
48
|
const { currentData: data, isLoading, error } = useGetComputeNodes ? computeQuery : nodesQuery;
|
42
|
-
const [
|
49
|
+
const [sortValue, setSortValue] = React.useState({
|
50
|
+
sortValue: 'NodeId',
|
51
|
+
sortOrder: ASCENDING,
|
52
|
+
});
|
53
|
+
const [sort, handleSort] = useTableSort(sortValue, (sortParams) => {
|
54
|
+
setSortValue(sortParams);
|
55
|
+
});
|
43
56
|
const handleSearchQueryChange = (value) => {
|
44
|
-
|
57
|
+
setQueryParams({ search: value || undefined }, 'replaceIn');
|
45
58
|
};
|
46
59
|
const handleProblemFilterChange = (value) => {
|
47
60
|
dispatch(changeFilter(value));
|
48
61
|
};
|
49
62
|
const handleUptimeFilterChange = (value) => {
|
50
|
-
|
63
|
+
setQueryParams({ uptimeFilter: value }, 'replaceIn');
|
51
64
|
};
|
52
|
-
// Since Nodes component is used in several places,
|
53
|
-
// we need to reset filters, searchValue
|
54
|
-
// in nodes reducer when path changes
|
55
|
-
React.useEffect(() => {
|
56
|
-
return () => {
|
57
|
-
// Clean data on component unmount
|
58
|
-
dispatch(setInitialState());
|
59
|
-
};
|
60
|
-
}, [dispatch, path]);
|
61
65
|
const nodes = React.useMemo(() => {
|
62
66
|
return filterNodes(data === null || data === void 0 ? void 0 : data.Nodes, { searchValue, uptimeFilter, problemFilter });
|
63
67
|
}, [data, searchValue, uptimeFilter, problemFilter]);
|
@@ -1,5 +1,6 @@
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
2
2
|
import React from 'react';
|
3
|
+
import { StringParam, useQueryParams } from 'use-query-params';
|
3
4
|
import { EntitiesCount } from '../../components/EntitiesCount';
|
4
5
|
import { AccessDenied } from '../../components/Errors/403';
|
5
6
|
import { ResponseError } from '../../components/Errors/ResponseError';
|
@@ -8,18 +9,25 @@ import { ProblemFilter } from '../../components/ProblemFilter';
|
|
8
9
|
import { Search } from '../../components/Search';
|
9
10
|
import { UptimeFilter } from '../../components/UptimeFIlter';
|
10
11
|
import { ResizeableVirtualTable } from '../../components/VirtualTable/ResizeableVirtualTable';
|
11
|
-
import { ProblemFilterValues } from '../../store/reducers/settings/settings';
|
12
|
+
import { ProblemFilterValues, changeFilter } from '../../store/reducers/settings/settings';
|
12
13
|
import { cn } from '../../utils/cn';
|
13
|
-
import {
|
14
|
+
import { useTypedDispatch, useTypedSelector } from '../../utils/hooks';
|
15
|
+
import { NodesUptimeFilterValues, getProblemParamValue, getUptimeParamValue, isSortableNodesProperty, isUnavailableNode, nodesUptimeFilterValuesSchema, } from '../../utils/nodes';
|
14
16
|
import { getNodes } from './getNodes';
|
15
17
|
import { NODES_COLUMNS_WIDTH_LS_KEY, getNodesColumns } from './getNodesColumns';
|
16
18
|
import i18n from './i18n';
|
17
19
|
import './Nodes.scss';
|
18
20
|
const b = cn('ydb-nodes');
|
19
21
|
export const VirtualNodes = ({ path, parentContainer, additionalNodesProps }) => {
|
20
|
-
|
21
|
-
const [
|
22
|
-
|
22
|
+
var _a;
|
23
|
+
const [queryParams, setQueryParams] = useQueryParams({
|
24
|
+
uptimeFilter: StringParam,
|
25
|
+
search: StringParam,
|
26
|
+
});
|
27
|
+
const uptimeFilter = nodesUptimeFilterValuesSchema.parse(queryParams.uptimeFilter);
|
28
|
+
const searchValue = (_a = queryParams.search) !== null && _a !== void 0 ? _a : '';
|
29
|
+
const dispatch = useTypedDispatch();
|
30
|
+
const problemFilter = useTypedSelector((state) => state.settings.problemFilter);
|
23
31
|
const filters = React.useMemo(() => {
|
24
32
|
return [path, searchValue, problemFilter, uptimeFilter];
|
25
33
|
}, [path, searchValue, problemFilter, uptimeFilter]);
|
@@ -39,7 +47,16 @@ export const VirtualNodes = ({ path, parentContainer, additionalNodesProps }) =>
|
|
39
47
|
return b('node', { unavailable: isUnavailableNode(row) });
|
40
48
|
};
|
41
49
|
const renderControls = ({ totalEntities, foundEntities, inited }) => {
|
42
|
-
|
50
|
+
const handleSearchQueryChange = (value) => {
|
51
|
+
setQueryParams({ search: value || undefined }, 'replaceIn');
|
52
|
+
};
|
53
|
+
const handleProblemFilterChange = (value) => {
|
54
|
+
dispatch(changeFilter(value));
|
55
|
+
};
|
56
|
+
const handleUptimeFilterChange = (value) => {
|
57
|
+
setQueryParams({ uptimeFilter: value }, 'replaceIn');
|
58
|
+
};
|
59
|
+
return (_jsxs(React.Fragment, { children: [_jsx(Search, { onChange: handleSearchQueryChange, placeholder: "Host name", className: b('search'), value: searchValue }), _jsx(ProblemFilter, { value: problemFilter, onChange: handleProblemFilterChange }), _jsx(UptimeFilter, { value: uptimeFilter, onChange: handleUptimeFilterChange }), _jsx(EntitiesCount, { total: totalEntities, current: foundEntities, label: 'Nodes', loading: !inited })] }));
|
43
60
|
};
|
44
61
|
const renderEmptyDataMessage = () => {
|
45
62
|
if (problemFilter !== ProblemFilterValues.ALL ||
|
@@ -1,5 +1,6 @@
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
2
2
|
import React from 'react';
|
3
|
+
import { ArrowRotateLeft } from '@gravity-ui/icons';
|
3
4
|
import { Icon } from '@gravity-ui/uikit';
|
4
5
|
import { skipToken } from '@reduxjs/toolkit/query';
|
5
6
|
import { Helmet } from 'react-helmet-async';
|
@@ -19,7 +20,6 @@ import { useTypedDispatch, useTypedSelector } from '../../utils/hooks';
|
|
19
20
|
import { PDiskGroups } from './PDiskGroups';
|
20
21
|
import { pDiskPageKeyset } from './i18n';
|
21
22
|
import { pdiskPageCn } from './shared';
|
22
|
-
import ArrowRotateLeftIcon from '@gravity-ui/icons/svgs/arrow-rotate-left.svg';
|
23
23
|
import './PDiskPage.scss';
|
24
24
|
export function PDiskPage() {
|
25
25
|
var _a;
|
@@ -74,7 +74,7 @@ export function PDiskPage() {
|
|
74
74
|
return (_jsx(DiskPageTitle, { entityName: pDiskPageKeyset('pdisk'), status: getSeverityColor(Severity), id: pDiskId, className: pdiskPageCn('title') }));
|
75
75
|
};
|
76
76
|
const renderControls = () => {
|
77
|
-
return (_jsx("div", { className: pdiskPageCn('controls'), children: _jsxs(ButtonWithConfirmDialog, { onConfirmAction: handleRestart, onConfirmActionSuccess: handleAfterRestart, buttonDisabled: !nodeId || !pDiskId, buttonView: "normal", dialogContent: pDiskPageKeyset('restart-pdisk-dialog'), children: [_jsx(Icon, { data:
|
77
|
+
return (_jsx("div", { className: pdiskPageCn('controls'), children: _jsxs(ButtonWithConfirmDialog, { onConfirmAction: handleRestart, onConfirmActionSuccess: handleAfterRestart, buttonDisabled: !nodeId || !pDiskId, buttonView: "normal", dialogContent: pDiskPageKeyset('restart-pdisk-dialog'), children: [_jsx(Icon, { data: ArrowRotateLeft }), pDiskPageKeyset('restart-pdisk-button')] }) }));
|
78
78
|
};
|
79
79
|
const renderInfo = () => {
|
80
80
|
if (pDiskLoading) {
|
@@ -1 +1 @@
|
|
1
|
-
export declare const pDiskPageKeyset: (key: "
|
1
|
+
export declare const pDiskPageKeyset: (key: "node" | "groups" | "fqdn" | "pdisk" | "restart-pdisk-button" | "restart-pdisk-dialog", params?: import("@gravity-ui/i18n").Params | undefined) => string;
|
@@ -1,28 +1,62 @@
|
|
1
1
|
import { __rest } from "tslib";
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
3
3
|
import React from 'react';
|
4
|
+
import { ArrayParam, StringParam, useQueryParams, withDefault } from 'use-query-params';
|
4
5
|
import { AccessDenied } from '../../components/Errors/403';
|
5
6
|
import { ResponseError } from '../../components/Errors/ResponseError';
|
6
7
|
import { TableWithControlsLayout } from '../../components/TableWithControlsLayout/TableWithControlsLayout';
|
7
8
|
import { selectNodesMap } from '../../store/reducers/nodesList';
|
8
9
|
import { STORAGE_TYPES, VISIBLE_ENTITIES } from '../../store/reducers/storage/constants';
|
9
|
-
import { filterGroups, filterNodes, getUsageFilterOptions,
|
10
|
-
import {
|
10
|
+
import { filterGroups, filterNodes, getUsageFilterOptions, } from '../../store/reducers/storage/selectors';
|
11
|
+
import { storageApi } from '../../store/reducers/storage/storage';
|
12
|
+
import { storageTypeSchema, visibleEntitiesSchema } from '../../store/reducers/storage/types';
|
11
13
|
import { DEFAULT_POLLING_INTERVAL, DEFAULT_TABLE_SETTINGS } from '../../utils/constants';
|
12
|
-
import { useNodesRequestParams, useStorageRequestParams, useTableSort,
|
13
|
-
import { NodesUptimeFilterValues } from '../../utils/nodes';
|
14
|
+
import { useNodesRequestParams, useStorageRequestParams, useTableSort, useTypedSelector, } from '../../utils/hooks';
|
15
|
+
import { NodesUptimeFilterValues, nodesUptimeFilterValuesSchema } from '../../utils/nodes';
|
14
16
|
import { StorageControls } from './StorageControls/StorageControls';
|
15
17
|
import { StorageGroups } from './StorageGroups/StorageGroups';
|
16
18
|
import { StorageNodes } from './StorageNodes/StorageNodes';
|
17
19
|
import { b } from './shared';
|
20
|
+
import { defaultSortNode, getDefaultSortGroup } from './utils';
|
18
21
|
import './Storage.scss';
|
22
|
+
const UsageFilterParam = withDefault({
|
23
|
+
encode: ArrayParam.encode,
|
24
|
+
decode: (input) => {
|
25
|
+
if (input === null || input === undefined) {
|
26
|
+
return input;
|
27
|
+
}
|
28
|
+
if (!Array.isArray(input)) {
|
29
|
+
return input ? [input] : [];
|
30
|
+
}
|
31
|
+
return input.filter(Boolean);
|
32
|
+
},
|
33
|
+
}, []);
|
19
34
|
export const Storage = ({ additionalNodesProps, tenant, nodeId }) => {
|
20
|
-
|
35
|
+
var _a;
|
21
36
|
const { autorefresh } = useTypedSelector((state) => state.schema);
|
22
|
-
const
|
37
|
+
const [queryParams, setQueryParams] = useQueryParams({
|
38
|
+
type: StringParam,
|
39
|
+
visible: StringParam,
|
40
|
+
search: StringParam,
|
41
|
+
uptimeFilter: StringParam,
|
42
|
+
usageFilter: UsageFilterParam,
|
43
|
+
});
|
44
|
+
const type = storageTypeSchema.parse(queryParams.type);
|
45
|
+
const visibleEntities = visibleEntitiesSchema.parse(queryParams.visible);
|
46
|
+
const filter = (_a = queryParams.search) !== null && _a !== void 0 ? _a : '';
|
47
|
+
const uptimeFilter = nodesUptimeFilterValuesSchema.parse(queryParams.uptimeFilter);
|
48
|
+
const usageFilter = queryParams.usageFilter;
|
23
49
|
const nodesMap = useTypedSelector(selectNodesMap);
|
24
|
-
const
|
25
|
-
|
50
|
+
const [nodeSort, setNodeSort] = React.useState({
|
51
|
+
sortOrder: undefined,
|
52
|
+
sortValue: undefined,
|
53
|
+
});
|
54
|
+
const nodesSortParams = nodeSort.sortValue ? nodeSort : defaultSortNode;
|
55
|
+
const [groupSort, setGroupSort] = React.useState({
|
56
|
+
sortOrder: undefined,
|
57
|
+
sortValue: undefined,
|
58
|
+
});
|
59
|
+
const groupsSortParams = groupSort.sortOrder ? groupSort : getDefaultSortGroup(visibleEntities);
|
26
60
|
// Do not display Nodes table for Node page (NodeId present)
|
27
61
|
const isNodePage = nodeId !== undefined;
|
28
62
|
const storageType = isNodePage ? STORAGE_TYPES.groups : type;
|
@@ -40,33 +74,27 @@ export const Storage = ({ additionalNodesProps, tenant, nodeId }) => {
|
|
40
74
|
const { currentData, isFetching, error } = storageType === STORAGE_TYPES.nodes ? nodesQuery : groupsQuery;
|
41
75
|
const { currentData: { nodes = [] } = {} } = nodesQuery;
|
42
76
|
const { currentData: { groups = [] } = {} } = groupsQuery;
|
43
|
-
const
|
77
|
+
const _b = currentData !== null && currentData !== void 0 ? currentData : { found: 0, total: 0 }, { nodes: _, groups: __ } = _b, entitiesCount = __rest(_b, ["nodes", "groups"]);
|
44
78
|
const isLoading = currentData === undefined && isFetching;
|
45
79
|
const storageNodes = React.useMemo(() => filterNodes(nodes, filter, uptimeFilter), [filter, nodes, uptimeFilter]);
|
46
80
|
const storageGroups = React.useMemo(() => filterGroups(groups, filter, usageFilter), [filter, groups, usageFilter]);
|
47
81
|
const usageFilterOptions = React.useMemo(() => getUsageFilterOptions(groups), [groups]);
|
48
|
-
|
49
|
-
|
50
|
-
// Clean data on component unmount
|
51
|
-
dispatch(setInitialState());
|
52
|
-
};
|
53
|
-
}, [dispatch]);
|
54
|
-
const [nodesSort, handleNodesSort] = useTableSort(nodesSortParams, (params) => dispatch(setNodesSortParams(params)));
|
55
|
-
const [groupsSort, handleGroupsSort] = useTableSort(groupsSortParams, (params) => dispatch(setGroupsSortParams(params)));
|
82
|
+
const [nodesSort, handleNodesSort] = useTableSort(nodesSortParams, (params) => setNodeSort(params));
|
83
|
+
const [groupsSort, handleGroupsSort] = useTableSort(groupsSortParams, (params) => setGroupSort(params));
|
56
84
|
const handleUsageFilterChange = (value) => {
|
57
|
-
|
85
|
+
setQueryParams({ usageFilter: value.length ? value : undefined }, 'replaceIn');
|
58
86
|
};
|
59
87
|
const handleTextFilterChange = (value) => {
|
60
|
-
|
88
|
+
setQueryParams({ search: value || undefined }, 'replaceIn');
|
61
89
|
};
|
62
90
|
const handleGroupVisibilityChange = (value) => {
|
63
|
-
|
91
|
+
setQueryParams({ visible: value }, 'replaceIn');
|
64
92
|
};
|
65
93
|
const handleStorageTypeChange = (value) => {
|
66
|
-
|
94
|
+
setQueryParams({ type: value }, 'replaceIn');
|
67
95
|
};
|
68
96
|
const handleUptimeFilterChange = (value) => {
|
69
|
-
|
97
|
+
setQueryParams({ uptimeFilter: value }, 'replaceIn');
|
70
98
|
};
|
71
99
|
const handleShowAllNodes = () => {
|
72
100
|
handleGroupVisibilityChange(VISIBLE_ENTITIES.all);
|
@@ -1,5 +1,6 @@
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
2
2
|
import React from 'react';
|
3
|
+
import { ShieldKeyhole } from '@gravity-ui/icons';
|
3
4
|
import DataTable from '@gravity-ui/react-data-table';
|
4
5
|
import { Icon, Label, Popover, PopoverBehavior } from '@gravity-ui/uikit';
|
5
6
|
import { CellWithPopover } from '../../../components/CellWithPopover/CellWithPopover';
|
@@ -14,7 +15,6 @@ import { isSortableStorageProperty } from '../../../utils/storage';
|
|
14
15
|
import { bytesToGB, bytesToSpeed } from '../../../utils/utils';
|
15
16
|
import { getDegradedSeverity, getUsageSeverityForStorageGroup } from '../utils';
|
16
17
|
import i18n from './i18n';
|
17
|
-
import shieldIcon from '../../../assets/icons/shield.svg';
|
18
18
|
import './StorageGroups.scss';
|
19
19
|
const b = cn('global-storage-groups');
|
20
20
|
export const STORAGE_GROUPS_COLUMNS_WIDTH_LS_KEY = 'storageGroupsColumnsWidth';
|
@@ -49,7 +49,7 @@ const typeColumn = {
|
|
49
49
|
width: 100,
|
50
50
|
resizeMinWidth: 100,
|
51
51
|
align: DataTable.LEFT,
|
52
|
-
render: ({ row }) => (_jsxs(React.Fragment, { children: [_jsx(Label, { children: row.MediaType || '—' }), '\u00a0', row.Encryption && (_jsx(Popover, { content: i18n('encrypted'), placement: "right", behavior: PopoverBehavior.Immediate, children: _jsx(Label, { children: _jsx(Icon, { data:
|
52
|
+
render: ({ row }) => (_jsxs(React.Fragment, { children: [_jsx(Label, { children: row.MediaType || '—' }), '\u00a0', row.Encryption && (_jsx(Popover, { content: i18n('encrypted'), placement: "right", behavior: PopoverBehavior.Immediate, children: _jsx(Label, { children: _jsx(Icon, { data: ShieldKeyhole, size: 18 }) }) }))] })),
|
53
53
|
sortable: false,
|
54
54
|
};
|
55
55
|
const erasureColumn = {
|
@@ -1,29 +1,51 @@
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
2
|
-
import
|
2
|
+
import { StringParam, useQueryParams } from 'use-query-params';
|
3
3
|
import { AccessDenied } from '../../components/Errors/403/AccessDenied';
|
4
4
|
import { ResponseError } from '../../components/Errors/ResponseError/ResponseError';
|
5
5
|
import { selectNodesMap } from '../../store/reducers/nodesList';
|
6
6
|
import { STORAGE_TYPES, VISIBLE_ENTITIES } from '../../store/reducers/storage/constants';
|
7
|
+
import { storageTypeSchema, visibleEntitiesSchema } from '../../store/reducers/storage/types';
|
7
8
|
import { useTypedSelector } from '../../utils/hooks';
|
8
|
-
import { NodesUptimeFilterValues } from '../../utils/nodes';
|
9
|
+
import { NodesUptimeFilterValues, nodesUptimeFilterValuesSchema } from '../../utils/nodes';
|
9
10
|
import { StorageControls } from './StorageControls/StorageControls';
|
10
11
|
import { VirtualStorageGroups } from './StorageGroups/VirtualStorageGroups';
|
11
12
|
import { VirtualStorageNodes } from './StorageNodes/VirtualStorageNodes';
|
12
13
|
export const VirtualStorage = ({ tenant, nodeId, parentContainer, additionalNodesProps, }) => {
|
13
|
-
|
14
|
-
const [
|
15
|
-
|
16
|
-
|
14
|
+
var _a;
|
15
|
+
const [queryParams, setQueryParams] = useQueryParams({
|
16
|
+
type: StringParam,
|
17
|
+
visible: StringParam,
|
18
|
+
search: StringParam,
|
19
|
+
uptimeFilter: StringParam,
|
20
|
+
});
|
21
|
+
const storageType = storageTypeSchema.parse(queryParams.type);
|
22
|
+
const visibleEntities = visibleEntitiesSchema.parse(queryParams.visible);
|
23
|
+
const searchValue = (_a = queryParams.search) !== null && _a !== void 0 ? _a : '';
|
24
|
+
const nodesUptimeFilter = nodesUptimeFilterValuesSchema.parse(queryParams.uptimeFilter);
|
25
|
+
const handleTextFilterChange = (value) => {
|
26
|
+
setQueryParams({ search: value || undefined }, 'replaceIn');
|
27
|
+
};
|
28
|
+
const handleGroupVisibilityChange = (value) => {
|
29
|
+
setQueryParams({ visible: value }, 'replaceIn');
|
30
|
+
};
|
31
|
+
const handleStorageTypeChange = (value) => {
|
32
|
+
setQueryParams({ type: value }, 'replaceIn');
|
33
|
+
};
|
34
|
+
const handleUptimeFilterChange = (value) => {
|
35
|
+
setQueryParams({ uptimeFilter: value }, 'replaceIn');
|
36
|
+
};
|
17
37
|
const nodesMap = useTypedSelector(selectNodesMap);
|
18
38
|
const handleShowAllGroups = () => {
|
19
|
-
|
39
|
+
handleGroupVisibilityChange(VISIBLE_ENTITIES.all);
|
20
40
|
};
|
21
41
|
const handleShowAllNodes = () => {
|
22
|
-
|
23
|
-
|
42
|
+
setQueryParams({
|
43
|
+
visible: VISIBLE_ENTITIES.all,
|
44
|
+
uptimeFilter: NodesUptimeFilterValues.All,
|
45
|
+
}, 'replaceIn');
|
24
46
|
};
|
25
47
|
const renderControls = ({ totalEntities, foundEntities, inited }) => {
|
26
|
-
return (_jsx(StorageControls, { searchValue: searchValue, handleSearchValueChange:
|
48
|
+
return (_jsx(StorageControls, { searchValue: searchValue, handleSearchValueChange: handleTextFilterChange, withTypeSelector: !nodeId, storageType: storageType, handleStorageTypeChange: handleStorageTypeChange, visibleEntities: visibleEntities, handleVisibleEntitiesChange: handleGroupVisibilityChange, nodesUptimeFilter: nodesUptimeFilter, handleNodesUptimeFilterChange: handleUptimeFilterChange, withGroupsUsageFilter: false, entitiesCountCurrent: foundEntities, entitiesCountTotal: totalEntities, entitiesLoading: !inited }));
|
27
49
|
};
|
28
50
|
const renderErrorMessage = (error) => {
|
29
51
|
if (error.status === 403) {
|
@@ -1,5 +1,8 @@
|
|
1
|
-
import type {
|
1
|
+
import type { NodesSortParams } from '../../../store/reducers/nodes/types';
|
2
|
+
import type { PreparedStorageGroup, StorageSortParams, VisibleEntities } from '../../../store/reducers/storage/types';
|
2
3
|
import { EFlag } from '../../../types/api/enums';
|
3
4
|
export declare const getDegradedSeverity: (group: PreparedStorageGroup) => "success" | "danger" | "warning" | undefined;
|
4
5
|
export declare const getUsageSeverityForStorageGroup: (value: number) => "success" | "danger" | "warning" | undefined;
|
5
6
|
export declare const getUsageSeverityForEntityStatus: (value: number) => EFlag.Green | EFlag.Yellow | EFlag.Red | undefined;
|
7
|
+
export declare const defaultSortNode: NodesSortParams;
|
8
|
+
export declare function getDefaultSortGroup(visibleEntities: VisibleEntities): StorageSortParams;
|
@@ -1,5 +1,9 @@
|
|
1
|
+
import { ASCENDING, DESCENDING } from '@gravity-ui/react-data-table/build/esm/lib/constants';
|
2
|
+
import { VISIBLE_ENTITIES } from '../../../store/reducers/storage/constants';
|
1
3
|
import { EFlag } from '../../../types/api/enums';
|
2
4
|
import { generateEvaluator } from '../../../utils/generateEvaluator';
|
5
|
+
import { NODES_SORT_VALUES } from '../../../utils/nodes';
|
6
|
+
import { STORAGE_SORT_VALUES } from '../../../utils/storage';
|
3
7
|
const defaultDegradationEvaluator = generateEvaluator(1, 2, ['success', 'warning', 'danger']);
|
4
8
|
const degradationEvaluators = {
|
5
9
|
'block-4-2': generateEvaluator(1, 2, ['success', 'warning', 'danger']),
|
@@ -22,3 +26,28 @@ export const getUsageSeverityForEntityStatus = generateEvaluator(80, 85, [
|
|
22
26
|
EFlag.Yellow,
|
23
27
|
EFlag.Red,
|
24
28
|
]);
|
29
|
+
export const defaultSortNode = {
|
30
|
+
sortValue: NODES_SORT_VALUES.NodeId,
|
31
|
+
sortOrder: ASCENDING,
|
32
|
+
};
|
33
|
+
const defaultSortGroup = {
|
34
|
+
sortValue: STORAGE_SORT_VALUES.PoolName,
|
35
|
+
sortOrder: ASCENDING,
|
36
|
+
};
|
37
|
+
const defaultSortGroupMissing = {
|
38
|
+
sortValue: STORAGE_SORT_VALUES.Degraded,
|
39
|
+
sortOrder: DESCENDING,
|
40
|
+
};
|
41
|
+
const defaultSortGroupSpace = {
|
42
|
+
sortValue: STORAGE_SORT_VALUES.Usage,
|
43
|
+
sortOrder: DESCENDING,
|
44
|
+
};
|
45
|
+
export function getDefaultSortGroup(visibleEntities) {
|
46
|
+
if (visibleEntities === VISIBLE_ENTITIES.missing) {
|
47
|
+
return defaultSortGroupMissing;
|
48
|
+
}
|
49
|
+
if (visibleEntities === VISIBLE_ENTITIES.space) {
|
50
|
+
return defaultSortGroupSpace;
|
51
|
+
}
|
52
|
+
return defaultSortGroup;
|
53
|
+
}
|
@@ -1,13 +1,13 @@
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
2
2
|
import React from 'react';
|
3
|
-
import {
|
3
|
+
import { ArrowUpRightFromSquare } from '@gravity-ui/icons';
|
4
|
+
import { Link as ExternalLink, Icon } from '@gravity-ui/uikit';
|
4
5
|
import { skipToken } from '@reduxjs/toolkit/query';
|
5
6
|
import { Helmet } from 'react-helmet-async';
|
6
7
|
import { useLocation, useParams } from 'react-router';
|
7
8
|
import { EmptyState } from '../../components/EmptyState';
|
8
9
|
import { EntityStatus } from '../../components/EntityStatus/EntityStatus';
|
9
10
|
import { ResponseError } from '../../components/Errors/ResponseError';
|
10
|
-
import { Icon } from '../../components/Icon';
|
11
11
|
import { Loader } from '../../components/Loader';
|
12
12
|
import { Tag } from '../../components/Tag';
|
13
13
|
import { parseQuery } from '../../routes';
|
@@ -66,7 +66,7 @@ export const Tablet = () => {
|
|
66
66
|
path: `/tablets?TabletID=${TabletId}`,
|
67
67
|
},
|
68
68
|
];
|
69
|
-
return (_jsx("div", { className: b(), children: _jsxs("div", { className: b('pane-wrapper'), children: [_jsxs("div", { className: b('left-pane'), children: [_jsx("ul", { className: b('links'), children: externalLinks.map(renderExternalLinks) }), _jsxs("div", { className: b('row', { header: true }), children: [_jsx("span", { className: b('title'), children: i18n('tablet.header') }), _jsx(EntityStatus, { status: Overall, name: TabletId }), _jsx("a", { rel: "noopener noreferrer", className: b('link', { external: true }), href: `${backend}/tablets?TabletID=${TabletId}`, target: "_blank", children: _jsx(Icon, {
|
69
|
+
return (_jsx("div", { className: b(), children: _jsxs("div", { className: b('pane-wrapper'), children: [_jsxs("div", { className: b('left-pane'), children: [_jsx("ul", { className: b('links'), children: externalLinks.map(renderExternalLinks) }), _jsxs("div", { className: b('row', { header: true }), children: [_jsx("span", { className: b('title'), children: i18n('tablet.header') }), _jsx(EntityStatus, { status: Overall, name: TabletId }), _jsx("a", { rel: "noopener noreferrer", className: b('link', { external: true }), href: `${backend}/tablets?TabletID=${TabletId}`, target: "_blank", children: _jsx(Icon, { data: ArrowUpRightFromSquare }) }), Leader && _jsx(Tag, { text: "Leader", type: "blue" }), _jsx("span", { className: b('loader'), children: loading && _jsx(Loader, { size: "s" }) })] }), _jsx(TabletInfo, { tablet: tablet, tenantPath: tenantName }), _jsx(TabletControls, { tablet: tablet, fetchData: refetch })] }), _jsx("div", { className: b('rigth-pane'), children: _jsx(TabletTable, { history: history }) })] }) }));
|
70
70
|
};
|
71
71
|
return (_jsxs(React.Fragment, { children: [_jsx(Helmet, { children: _jsx("title", { children: `${id} — ${i18n('tablet.header')} — ${tenantName || queryClusterName || CLUSTER_DEFAULT_TITLE}` }) }), renderView()] }));
|
72
72
|
};
|
@@ -1,2 +1,2 @@
|
|
1
|
-
declare const _default: (key: "
|
1
|
+
declare const _default: (key: "dialog.kill" | "tablet.header" | "controls.kill" | "controls.stop" | "controls.resume" | "dialog.stop" | "dialog.resume" | "emptyState", params?: import("@gravity-ui/i18n").Params | undefined) => string;
|
2
2
|
export default _default;
|
@@ -1,8 +1,7 @@
|
|
1
|
-
import './Tablets.scss';
|
2
1
|
interface TabletsProps {
|
3
2
|
path?: string;
|
4
3
|
nodeId?: string | number;
|
5
4
|
className?: string;
|
6
5
|
}
|
7
|
-
export declare
|
6
|
+
export declare function Tablets({ nodeId, path, className }: TabletsProps): import("react/jsx-runtime").JSX.Element;
|
8
7
|
export {};
|