import React from 'react'; import {Flex} from '@gravity-ui/uikit'; import {isEmpty} from 'lodash'; import {InternalLink} from '../../../../../components/InternalLink'; import {getPDiskPagePath, useVDiskPagePath} from '../../../../../routes'; import type {Location} from '../../../../../types/api/healthcheck'; import {useHealthcheckContext} from '../../HealthcheckContext'; import i18n from '../../i18n'; import {NodeInfo} from './NodeInfo'; import {PoolInfo} from './PoolInfo'; import {IdList, LocationDetails, SectionWithTitle} from './utils'; export type LocationFieldStorage = 'pool' | 'node' | 'pdisk' | 'vdisk' | 'group'; type StorageLocationType = Location['storage']; const LocationFieldRenderer: Record< LocationFieldStorage, (location: StorageLocationType) => React.ReactNode > = { node: (location: StorageLocationType) => , pool: (location: StorageLocationType) => , group: (location: StorageLocationType) => , vdisk: (location: StorageLocationType) => , pdisk: (location: StorageLocationType) => , }; interface StorageLocationProps { location: StorageLocationType; hiddenFields?: LocationFieldStorage[]; } export function StorageLocation({location, hiddenFields = []}: StorageLocationProps) { const {node, pool} = location ?? {}; const {group} = pool ?? {}; const {vdisk} = group ?? {}; const {pdisk} = vdisk ?? {}; const fields = React.useMemo(() => { const fields: LocationFieldStorage[] = []; if (node) { fields.push('node'); } if (pool) { fields.push('pool'); } if (group) { fields.push('group'); } if (vdisk) { fields.push('vdisk'); } if (pdisk) { fields.push('pdisk'); } return fields.filter((field) => !hiddenFields.includes(field)); }, [node, pool, group, vdisk, pdisk, hiddenFields]); if (!location || isEmpty(location) || fields.length === 0) { return null; } return ( {fields.map((field) => LocationFieldRenderer[field](location))} ); } interface StorageSectionProps { location?: Location['storage']; } function GroupInfo({location}: StorageSectionProps) { const {pool} = location ?? {}; const {group} = pool ?? {}; const ids = group?.id; const pileName = group?.pile?.name; if (!ids?.length && !pileName) { return null; } return ( : undefined, title: i18n('label_group-id'), }, {value: pileName, title: i18n('label_pile')}, ]} /> ); } function VDiskInfo({location}: StorageSectionProps) { const {clusterName, database} = useHealthcheckContext(); const getVDiskPagePath = useVDiskPagePath(database); const {node, pool} = location ?? {}; const {group} = pool ?? {}; const {vdisk} = group ?? {}; const ids = vdisk?.id; if (!ids?.length) { return null; } return ( ( {id} )} /> ) : undefined, title: i18n('label_vdisk-id'), }, ]} /> ); } function PDiskInfo({location}: StorageSectionProps) { const {clusterName, database} = useHealthcheckContext(); const {pool} = location ?? {}; const {group} = pool ?? {}; const {vdisk} = group ?? {}; const {pdisk} = vdisk ?? {}; if (!pdisk?.length) { return null; } return pdisk.map((disk) => { let nodeId: string | undefined; let pdiskId: string | undefined; if (disk.id) { const splittedId = disk.id.split('-'); nodeId = splittedId[0]; pdiskId = splittedId.slice(1).join('-'); } return ( {disk.id} ) : ( disk.id ), title: i18n('label_pdisk-id'), }, {value: disk.path, title: i18n('label_pdisk-path')}, ]} /> ); }); }