(TENANT_INITIAL_PAGE_KEY);
- const {tenantPage} = useTypedSelector((state) => state.tenant);
-
- const {pathname} = location;
- const queryParams = parseQuery(location);
-
- const isTenantPage = pathname === routes.tenant;
-
- const menuItems: AsideHeaderMenuItem[] = React.useMemo(() => {
- if (!isTenantPage) {
- return [];
- }
-
- const items: MenuItem[] = [
- {
- id: TENANT_PAGES_IDS.query,
- title: i18n('pages.query'),
- icon: Terminal,
- iconSize: 20,
- location: getTenantPath({
- ...queryParams,
- [TENANT_PAGE]: TENANT_PAGES_IDS.query,
- }),
- },
- {
- id: TENANT_PAGES_IDS.diagnostics,
- title: i18n('pages.diagnostics'),
- icon: Pulse,
- iconSize: 20,
- location: getTenantPath({
- ...queryParams,
- [TENANT_PAGE]: TENANT_PAGES_IDS.diagnostics,
- }),
- },
- ];
-
- return items.map((item) => {
- const current = item.id === tenantPage;
-
- return {
- id: item.id,
- title: item.title,
- icon: item.icon,
- iconSize: item.iconSize,
- current,
- onItemClick: () => {
- setInitialTenantPage(item.id);
- history.push(item.location);
- },
- };
- });
- }, [tenantPage, isTenantPage, setInitialTenantPage, history, queryParams]);
-
- return menuItems;
-}
diff --git a/src/containers/Tenant/Diagnostics/Diagnostics.scss b/src/containers/Tenant/Diagnostics/Diagnostics.scss
index bde358fad8..9adf5592e9 100644
--- a/src/containers/Tenant/Diagnostics/Diagnostics.scss
+++ b/src/containers/Tenant/Diagnostics/Diagnostics.scss
@@ -6,7 +6,7 @@
height: 100%;
&__header-wrapper {
- padding: 13px 20px 16px;
+ padding: 0 20px 16px;
background-color: var(--g-color-base-background);
}
diff --git a/src/containers/Tenant/ObjectGeneral/ObjectGeneral.tsx b/src/containers/Tenant/ObjectGeneral/ObjectGeneral.tsx
index 969a5d4e16..b6ff4f77ab 100644
--- a/src/containers/Tenant/ObjectGeneral/ObjectGeneral.tsx
+++ b/src/containers/Tenant/ObjectGeneral/ObjectGeneral.tsx
@@ -7,6 +7,7 @@ import {cn} from '../../../utils/cn';
import {useTypedSelector} from '../../../utils/hooks';
import Diagnostics from '../Diagnostics/Diagnostics';
import {Query} from '../Query/Query';
+import {TenantNavigation} from '../TenantNavigation/TenantNavigation';
import './ObjectGeneral.scss';
@@ -24,7 +25,7 @@ function ObjectGeneral(props: ObjectGeneralProps) {
const {tenantPage} = useTypedSelector((state) => state.tenant);
- const renderTabContent = () => {
+ const renderPageContent = () => {
const {type, additionalTenantProps, additionalNodesProps, tenantName} = props;
switch (tenantPage) {
case TENANT_PAGES_IDS.query: {
@@ -47,7 +48,12 @@ function ObjectGeneral(props: ObjectGeneralProps) {
if (!tenantName) {
return null;
}
- return {renderTabContent()}
;
+ return (
+
+
+ {renderPageContent()}
+
+ );
};
return renderContent();
diff --git a/src/containers/Tenant/Query/Query.scss b/src/containers/Tenant/Query/Query.scss
index 8f9dbf1f9c..3644a537be 100644
--- a/src/containers/Tenant/Query/Query.scss
+++ b/src/containers/Tenant/Query/Query.scss
@@ -5,7 +5,7 @@
@include flex-container();
&__tabs {
- padding: 13px 20px 16px;
+ padding: 0 20px 16px;
}
&__content {
diff --git a/src/containers/Tenant/Query/i18n/en.json b/src/containers/Tenant/Query/i18n/en.json
index 8d2c29cf8e..0bab781726 100644
--- a/src/containers/Tenant/Query/i18n/en.json
+++ b/src/containers/Tenant/Query/i18n/en.json
@@ -1,7 +1,7 @@
{
"controls.query-mode-selector_type": "Query type:",
- "tabs.newQuery": "Query",
+ "tabs.newQuery": "Editor",
"tabs.history": "History",
"tabs.saved": "Saved",
diff --git a/src/containers/Tenant/TenantNavigation/TenantNavigation.scss b/src/containers/Tenant/TenantNavigation/TenantNavigation.scss
new file mode 100644
index 0000000000..a714bef959
--- /dev/null
+++ b/src/containers/Tenant/TenantNavigation/TenantNavigation.scss
@@ -0,0 +1,18 @@
+.ydb-tenant-navigation {
+ padding: 12px 16px 8px;
+
+ &__item {
+ display: flex;
+ align-items: center;
+ gap: 5px;
+ }
+
+ &__icon {
+ flex-shrink: 0;
+ }
+ &__text {
+ overflow: hidden;
+
+ text-overflow: ellipsis;
+ }
+}
diff --git a/src/containers/Tenant/TenantNavigation/TenantNavigation.tsx b/src/containers/Tenant/TenantNavigation/TenantNavigation.tsx
new file mode 100644
index 0000000000..a346fba132
--- /dev/null
+++ b/src/containers/Tenant/TenantNavigation/TenantNavigation.tsx
@@ -0,0 +1,48 @@
+import type {RadioButtonOption} from '@gravity-ui/uikit';
+import {Icon, RadioButton} from '@gravity-ui/uikit';
+
+import {cn} from '../../../utils/cn';
+
+import {useTenantNavigation} from './useTenantNavigation';
+
+import './TenantNavigation.scss';
+
+const b = cn('ydb-tenant-navigation');
+
+type MenuItem = ReturnType[0];
+
+const transformItemToOption = ({id, title, icon}: MenuItem): RadioButtonOption => {
+ const content = (
+
+
+ {title}
+
+ );
+
+ return {value: id, content};
+};
+
+export const TenantNavigation = () => {
+ const navigationItems = useTenantNavigation();
+
+ const handleUpdate = (value: string) => {
+ const nextItem = navigationItems.find((item) => item.id === value);
+
+ nextItem?.onForward();
+ };
+
+ const getCurrentItem = () => navigationItems.find((item) => item.current) || navigationItems[0];
+
+ return (
+
+
+
+ );
+};
diff --git a/src/containers/Tenant/TenantNavigation/useTenantNavigation.tsx b/src/containers/Tenant/TenantNavigation/useTenantNavigation.tsx
new file mode 100644
index 0000000000..e0a5c8a9a1
--- /dev/null
+++ b/src/containers/Tenant/TenantNavigation/useTenantNavigation.tsx
@@ -0,0 +1,59 @@
+import React from 'react';
+
+import {Pulse, Terminal} from '@gravity-ui/icons';
+import {useHistory, useLocation} from 'react-router';
+
+import routes, {parseQuery} from '../../../routes';
+import {TENANT_PAGE, TENANT_PAGES_IDS} from '../../../store/reducers/tenant/constants';
+import {TENANT_INITIAL_PAGE_KEY} from '../../../utils/constants';
+import {useSetting, useTypedSelector} from '../../../utils/hooks';
+import {getTenantPath} from '../TenantPages';
+import i18n from '../i18n';
+
+type TenantPages = keyof typeof TENANT_PAGES_IDS;
+
+const pagesList: Array = ['query', 'diagnostics'];
+
+const mapPageToIcon = {
+ query: Terminal,
+ diagnostics: Pulse,
+};
+
+export function useTenantNavigation() {
+ const history = useHistory();
+
+ const location = useLocation();
+ const queryParams = parseQuery(location);
+
+ const [, setInitialTenantPage] = useSetting(TENANT_INITIAL_PAGE_KEY);
+ const {tenantPage} = useTypedSelector((state) => state.tenant);
+
+ const menuItems = React.useMemo(() => {
+ if (location.pathname !== routes.tenant) {
+ return [];
+ }
+
+ const items = pagesList.map((key) => {
+ const pageId = TENANT_PAGES_IDS[key];
+ const pagePath = getTenantPath({...queryParams, [TENANT_PAGE]: pageId});
+
+ const nextItem = {
+ id: pageId,
+ title: i18n(`pages.${key}`),
+ icon: mapPageToIcon[key],
+ path: pagePath,
+ current: tenantPage === pageId,
+ onForward: () => {
+ setInitialTenantPage(pageId);
+ history.push(pagePath);
+ },
+ };
+
+ return nextItem;
+ });
+
+ return items;
+ }, [tenantPage, setInitialTenantPage, location.pathname, history, queryParams]);
+
+ return menuItems;
+}
diff --git a/src/containers/Tenant/i18n/en.json b/src/containers/Tenant/i18n/en.json
index c9c736a420..49d2366cae 100644
--- a/src/containers/Tenant/i18n/en.json
+++ b/src/containers/Tenant/i18n/en.json
@@ -1,6 +1,9 @@
{
"page.title": "Database",
+ "pages.query": "Query",
+ "pages.diagnostics": "Diagnostics",
+
"acl.owner": "Owner",
"acl.empty": "No Acl data",