diff --git a/src/components/InfoViewer/InfoViewer.tsx b/src/components/InfoViewer/InfoViewer.tsx index 780497028..09e000a30 100644 --- a/src/components/InfoViewer/InfoViewer.tsx +++ b/src/components/InfoViewer/InfoViewer.tsx @@ -2,6 +2,8 @@ import React from 'react'; import {cn} from '../../utils/cn'; +import i18n from './i18n'; + import './InfoViewer.scss'; export interface InfoViewerItem { @@ -10,7 +12,7 @@ export interface InfoViewerItem { } export interface InfoViewerProps { - title?: string; + title?: React.ReactNode; info?: InfoViewerItem[]; dots?: boolean; size?: 's'; @@ -53,7 +55,7 @@ export const InfoViewer = ({ ))} ) : ( - No {title} data + i18n('no-data') )} ); diff --git a/src/components/InfoViewer/i18n/en.json b/src/components/InfoViewer/i18n/en.json index 5c4f44aaa..2ed830fef 100644 --- a/src/components/InfoViewer/i18n/en.json +++ b/src/components/InfoViewer/i18n/en.json @@ -1,4 +1,5 @@ { "common.created": "Created", - "common.type": "Type" + "common.type": "Type", + "no-data": "No data" } diff --git a/src/components/InfoViewer/i18n/index.ts b/src/components/InfoViewer/i18n/index.ts index 33853de36..b7acedb9e 100644 --- a/src/components/InfoViewer/i18n/index.ts +++ b/src/components/InfoViewer/i18n/index.ts @@ -1,8 +1,7 @@ import {registerKeysets} from '../../../utils/i18n'; import en from './en.json'; -import ru from './ru.json'; const COMPONENT = 'ydb-components-info-viewer'; -export default registerKeysets(COMPONENT, {ru, en}); +export default registerKeysets(COMPONENT, {en}); diff --git a/src/components/InfoViewer/i18n/ru.json b/src/components/InfoViewer/i18n/ru.json deleted file mode 100644 index f88f2cb2f..000000000 --- a/src/components/InfoViewer/i18n/ru.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - "common.created": "Создано", - "common.type": "Тип" -} diff --git a/src/containers/Tenant/Diagnostics/Overview/TableInfo/TableInfo.tsx b/src/containers/Tenant/Diagnostics/Overview/TableInfo/TableInfo.tsx index 07fb6513a..a87c16762 100644 --- a/src/containers/Tenant/Diagnostics/Overview/TableInfo/TableInfo.tsx +++ b/src/containers/Tenant/Diagnostics/Overview/TableInfo/TableInfo.tsx @@ -4,7 +4,7 @@ import {InfoViewer} from '../../../../../components/InfoViewer'; import type {KeyValueRow} from '../../../../../types/api/query'; import type {EPathType, TEvDescribeSchemeResult} from '../../../../../types/api/schema'; import {cn} from '../../../../../utils/cn'; -import {getEntityName} from '../../../utils'; +import {EntityTitle} from '../../../EntityTitle/EntityTitle'; import i18n from './i18n'; import {prepareTableInfo} from './prepareTableInfo'; @@ -20,7 +20,7 @@ interface TableInfoProps { } export const TableInfo = ({data, type, olapStats}: TableInfoProps) => { - const entityName = getEntityName(data?.PathDescription); + const title = ; const { generalInfo = [], @@ -33,9 +33,9 @@ export const TableInfo = ({data, type, olapStats}: TableInfoProps) => {
{entityName}
} + renderEmptyState={() =>
{title}
} />
diff --git a/src/containers/Tenant/EntityTitle/EntityTitle.tsx b/src/containers/Tenant/EntityTitle/EntityTitle.tsx new file mode 100644 index 000000000..953291d40 --- /dev/null +++ b/src/containers/Tenant/EntityTitle/EntityTitle.tsx @@ -0,0 +1,23 @@ +import {Flex, Label} from '@gravity-ui/uikit'; + +import type {TPathDescription} from '../../../types/api/schema'; +import i18n from '../i18n'; +import {getEntityName, isReadOnlyTable} from '../utils'; + +interface EntityTitleProps { + data?: TPathDescription; +} + +export function EntityTitle({data}: EntityTitleProps) { + const entityName = getEntityName(data); + + if (isReadOnlyTable(data)) { + return ( + + {entityName} + + ); + } + + return entityName; +} diff --git a/src/containers/Tenant/ObjectSummary/ObjectSummary.tsx b/src/containers/Tenant/ObjectSummary/ObjectSummary.tsx index ca7c84d57..c558bd5b8 100644 --- a/src/containers/Tenant/ObjectSummary/ObjectSummary.tsx +++ b/src/containers/Tenant/ObjectSummary/ObjectSummary.tsx @@ -15,7 +15,6 @@ import type {InfoViewerItem} from '../../../components/InfoViewer/InfoViewer'; import {LinkWithIcon} from '../../../components/LinkWithIcon/LinkWithIcon'; import {Loader} from '../../../components/Loader'; import SplitPane from '../../../components/SplitPane'; -import {getEntityName} from '../../../containers/Tenant/utils'; import routes, {createExternalUILink, createHref} from '../../../routes'; import {schemaApi, setShowPreview} from '../../../store/reducers/schema/schema'; import { @@ -33,6 +32,7 @@ import { import {formatDateTime, formatSecondsToHours} from '../../../utils/dataFormatters/dataFormatters'; import {useTypedDispatch, useTypedSelector} from '../../../utils/hooks'; import {Acl} from '../Acl/Acl'; +import {EntityTitle} from '../EntityTitle/EntityTitle'; import {SchemaTree} from '../Schema/SchemaTree/SchemaTree'; import {SchemaViewer} from '../Schema/SchemaViewer/SchemaViewer'; import {TENANT_INFO_TABS, TENANT_SCHEMA_TAB, TenantTabsGroups} from '../TenantPages'; @@ -159,7 +159,8 @@ export function ObjectSummary({ }); const {PathDescription} = currentObjectData; - const title = getEntityName(PathDescription); + + const title = ; const getPathTypeOverview: Record InfoViewerItem[]) | undefined> = { [EPathType.EPathTypeInvalid]: undefined, diff --git a/src/containers/Tenant/i18n/en.json b/src/containers/Tenant/i18n/en.json index 46e8b558d..8b358bb9a 100644 --- a/src/containers/Tenant/i18n/en.json +++ b/src/containers/Tenant/i18n/en.json @@ -21,6 +21,7 @@ "summary.mode": "Mode", "summary.format": "Format", "summary.retention": "Retention", + "label.read-only": "ReadOnly", "actions.copied": "The path is copied to the clipboard", "actions.notCopied": "Couldn’t copy the path", "actions.copyPath": "Copy path", diff --git a/src/containers/Tenant/utils/index.ts b/src/containers/Tenant/utils/index.ts index f85b2ccca..d0861b5a8 100644 --- a/src/containers/Tenant/utils/index.ts +++ b/src/containers/Tenant/utils/index.ts @@ -7,3 +7,9 @@ export const getEntityName = (pathDescription?: TPathDescription) => { return mapPathTypeToEntityName(PathType, PathSubType); }; + +export const isReadOnlyTable = (pathDescription?: TPathDescription) => { + return pathDescription?.UserAttributes?.some(({Key, Value}) => { + return Key === '__async_replica' && Value === 'true'; + }); +}; diff --git a/src/types/api/schema/schema.ts b/src/types/api/schema/schema.ts index 2bc0c781d..f4929b271 100644 --- a/src/types/api/schema/schema.ts +++ b/src/types/api/schema/schema.ts @@ -61,6 +61,7 @@ export interface TPathDescription { /** info about the path itself */ Self?: TDirEntry; DomainDescription?: TDomainDescription; + UserAttributes?: TUserAttribute[]; // for directory Children?: TDirEntry[]; @@ -309,3 +310,8 @@ interface TTablePartition { /** uint64 */ DatashardId?: string; } + +interface TUserAttribute { + Key?: string; + Value?: string; +}