diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ContainerSummary/ContainerSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ContainerSummary/ContainerSummary.component.tsx index 6ed03eb3581..d2f367cec74 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ContainerSummary/ContainerSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ContainerSummary/ContainerSummary.component.tsx @@ -71,16 +71,10 @@ function ContainerSummary({ diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DashboardSummary/DashboardSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DashboardSummary/DashboardSummary.component.tsx index 3465362b55a..0b391421fa3 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DashboardSummary/DashboardSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DashboardSummary/DashboardSummary.component.tsx @@ -112,15 +112,10 @@ function DashboardSummary({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DataModelSummary/DataModelSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DataModelSummary/DataModelSummary.component.tsx index fcce021a4b4..4717ee7ab63 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DataModelSummary/DataModelSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DataModelSummary/DataModelSummary.component.tsx @@ -80,15 +80,10 @@ const DataModelSummary = ({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSchemaSummary/DatabaseSchemaSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSchemaSummary/DatabaseSchemaSummary.component.tsx index 75ca862f8bf..09cee626584 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSchemaSummary/DatabaseSchemaSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSchemaSummary/DatabaseSchemaSummary.component.tsx @@ -54,15 +54,10 @@ const DatabaseSchemaSummary = ({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSummary/DatabaseSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSummary/DatabaseSummary.component.tsx index 90f80304f7b..8eed1179562 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSummary/DatabaseSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/DatabaseSummary/DatabaseSummary.component.tsx @@ -73,15 +73,10 @@ const DatabaseSummary = ({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/MlModelSummary/MlModelSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/MlModelSummary/MlModelSummary.component.tsx index f1305ac8a0c..7e299a34402 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/MlModelSummary/MlModelSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/MlModelSummary/MlModelSummary.component.tsx @@ -82,15 +82,10 @@ function MlModelSummary({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/PipelineSummary/PipelineSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/PipelineSummary/PipelineSummary.component.tsx index d5ac71f2d54..1b94a05b6c7 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/PipelineSummary/PipelineSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/PipelineSummary/PipelineSummary.component.tsx @@ -82,15 +82,10 @@ function PipelineSummary({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SearchIndexSummary/SearchIndexSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SearchIndexSummary/SearchIndexSummary.component.tsx index c2fc947aaa3..720092d867e 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SearchIndexSummary/SearchIndexSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SearchIndexSummary/SearchIndexSummary.component.tsx @@ -97,15 +97,10 @@ function SearchIndexSummary({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ServiceSummary/ServiceSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ServiceSummary/ServiceSummary.component.tsx index 37f344b7919..42874461342 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ServiceSummary/ServiceSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/ServiceSummary/ServiceSummary.component.tsx @@ -54,15 +54,10 @@ const ServiceSummary = ({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/StoredProcedureSummary/StoredProcedureSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/StoredProcedureSummary/StoredProcedureSummary.component.tsx index 3eeae4ec3e6..141b39fba12 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/StoredProcedureSummary/StoredProcedureSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/StoredProcedureSummary/StoredProcedureSummary.component.tsx @@ -61,15 +61,10 @@ const StoredProcedureSummary = ({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SummaryList/SummaryList.interface.ts b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SummaryList/SummaryList.interface.ts index a2de6f39958..1b456fc8b87 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SummaryList/SummaryList.interface.ts +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/SummaryList/SummaryList.interface.ts @@ -22,12 +22,16 @@ import { } from '../../../../generated/entity/data/table'; import { TagLabel } from '../../../../generated/type/tagLabel'; +export interface HighlightedTagLabel extends TagLabel { + isHighlighted: boolean; +} + export interface BasicEntityInfo { algorithm?: string; name: string; title: ReactNode; type?: DataType | ChartType | FeatureType | string; - tags?: TagLabel[]; + tags?: Array; description?: string; columnConstraint?: Constraint; tableConstraints?: TableConstraint[]; diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TableSummary/TableSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TableSummary/TableSummary.component.tsx index 2c26d6d7292..755085315af 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TableSummary/TableSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TableSummary/TableSummary.component.tsx @@ -247,15 +247,10 @@ function TableSummary({ entityDetail={tableDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: tableDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + tableDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TopicSummary/TopicSummary.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TopicSummary/TopicSummary.component.tsx index 1b2bae4083a..91b07eff908 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TopicSummary/TopicSummary.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Explore/EntitySummaryPanel/TopicSummary/TopicSummary.component.tsx @@ -167,15 +167,10 @@ function TopicSummary({ entityDetail={entityDetails} tags={ tags ?? - getSortedTagsWithHighlight({ - tags: entityDetails.tags, - sortTagsBasedOnGivenTagFQNs: get( - highlights, - 'tag.name', - [] as string[] - ), - }) ?? - [] + getSortedTagsWithHighlight( + entityDetails.tags, + get(highlights, 'tag.name') + ) } /> diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.component.tsx index 2aba33ef2c7..66aab57f39f 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.component.tsx @@ -22,11 +22,11 @@ import { ROUTES } from '../../../constants/constants'; import { TAG_START_WITH } from '../../../constants/Tag.constants'; import { TagSource } from '../../../generated/type/tagLabel'; import { reduceColorOpacity } from '../../../utils/CommonUtils'; -import { HighlightedTagLabel } from '../../../utils/EntitySummaryPanelUtils'; import { getEntityName } from '../../../utils/EntityUtils'; import Fqn from '../../../utils/Fqn'; import { getEncodedFqn } from '../../../utils/StringsUtils'; import { getTagDisplay, getTagTooltip } from '../../../utils/TagsUtils'; +import { HighlightedTagLabel } from '../../Explore/EntitySummaryPanel/SummaryList/SummaryList.interface'; import { TagsV1Props } from './TagsV1.interface'; import './tagsV1.less'; diff --git a/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.interface.ts b/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.interface.ts index 9524dcef9aa..b6602c42df0 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.interface.ts +++ b/openmetadata-ui/src/main/resources/ui/src/components/Tag/TagsV1/TagsV1.interface.ts @@ -14,7 +14,7 @@ import { TagProps } from 'antd'; import { TAG_START_WITH } from '../../../constants/Tag.constants'; import { TagLabel, TagSource } from '../../../generated/type/tagLabel'; -import { HighlightedTagLabel } from '../../../utils/EntitySummaryPanelUtils'; +import { HighlightedTagLabel } from '../../Explore/EntitySummaryPanel/SummaryList/SummaryList.interface'; export type TagsV1Props = { tag: TagLabel | HighlightedTagLabel; diff --git a/openmetadata-ui/src/main/resources/ui/src/components/common/SummaryTagsDescription/SummaryTagsDescription.component.tsx b/openmetadata-ui/src/main/resources/ui/src/components/common/SummaryTagsDescription/SummaryTagsDescription.component.tsx index 7794764585a..59b3c3b7d6d 100644 --- a/openmetadata-ui/src/main/resources/ui/src/components/common/SummaryTagsDescription/SummaryTagsDescription.component.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/components/common/SummaryTagsDescription/SummaryTagsDescription.component.tsx @@ -14,15 +14,15 @@ import { Col, Divider, Row, Typography } from 'antd'; import React from 'react'; import { useTranslation } from 'react-i18next'; import TagsViewer from '../../../components/Tag/TagsViewer/TagsViewer'; -import { TagLabel } from '../../../generated/type/tagLabel'; +import { BasicEntityInfo } from '../../Explore/EntitySummaryPanel/SummaryList/SummaryList.interface'; import { EntityUnion } from '../../Explore/ExplorePage.interface'; import RichTextEditorPreviewer from '../RichTextEditor/RichTextEditorPreviewer'; const SummaryTagsDescription = ({ - tags, + tags = [], entityDetail, }: { - tags: TagLabel[]; + tags: BasicEntityInfo['tags']; entityDetail: EntityUnion; }) => { const { t } = useTranslation(); diff --git a/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.test.tsx b/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.test.tsx index 53ecc638b3d..e7f9fbf16d3 100644 --- a/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.test.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.test.tsx @@ -15,6 +15,8 @@ import { SummaryEntityType } from '../enums/EntitySummary.enum'; import { Column } from '../generated/entity/data/table'; import { getFormattedEntityData, + getHighlightOfListItem, + getMapOfListHighlights, getSortedTagsWithHighlight, getSummaryListItemType, getTitle, @@ -24,87 +26,146 @@ import { mockEntityDataWithNestingResponse, mockEntityDataWithoutNesting, mockEntityDataWithoutNestingResponse, + mockGetHighlightOfListItemResponse, + mockGetMapOfListHighlightsResponse, mockGetSummaryListItemTypeResponse, + mockHighlights, mockInvalidDataResponse, mockLinkBasedSummaryTitleResponse, + mockListItemNameHighlight, mockTagFQNsForHighlight, - mockTagsDataAfterSortAndHighlight, - mockTagsDataBeforeSortAndHighlight, + mockTagsSortAndHighlightResponse, mockTextBasedSummaryTitleResponse, } from './mocks/EntitySummaryPanelUtils.mock'; +jest.mock('../constants/EntitySummaryPanelUtils.constant', () => ({ + ...jest.requireActual('../constants/EntitySummaryPanelUtils.constant'), + SummaryListHighlightKeys: [ + 'columns.name', + 'columns.description', + 'columns.children.name', + ], +})); + describe('EntitySummaryPanelUtils tests', () => { - it('getFormattedEntityData should return formatted data properly for table columns data without nesting, and also sort the data based on given arr', () => { - const highlights = { - 'tag.name': ['PersonalData.SpecialCategory'], - }; - const resultFormattedData = getFormattedEntityData( - SummaryEntityType.COLUMN, - mockEntityDataWithoutNesting, - highlights - ); + describe('getFormattedEntityData', () => { + it('getFormattedEntityData should return formatted data properly for table columns data with nesting, and also sort the data based on highlights', () => { + const resultFormattedData = getFormattedEntityData( + SummaryEntityType.COLUMN, + mockEntityDataWithNesting, + mockHighlights + ); - expect(resultFormattedData).toEqual(mockEntityDataWithoutNestingResponse); - }); - - it('getFormattedEntityData should return formatted data properly for topic fields data with nesting', () => { - const resultFormattedData = getFormattedEntityData( - SummaryEntityType.COLUMN, - mockEntityDataWithNesting - ); - - expect(resultFormattedData).toEqual(mockEntityDataWithNestingResponse); - }); - - it('getFormattedEntityData should return empty array in case entityType is given other than from type SummaryEntityType', () => { - const resultFormattedData = getFormattedEntityData( - 'otherType' as SummaryEntityType, - mockEntityDataWithNesting - ); - - expect(resultFormattedData).toEqual([]); - }); - - it('getFormattedEntityData should not throw error if entityDetails sent does not have fields present', () => { - const resultFormattedData = getFormattedEntityData( - SummaryEntityType.COLUMN, - [{}] as Column[] - ); - - expect(resultFormattedData).toEqual(mockInvalidDataResponse); - }); - - it('getSortedTagsWithHighlight should return the sorted and highlighted tags data based on given tagFQN array', () => { - const sortedTags = getSortedTagsWithHighlight({ - sortTagsBasedOnGivenTagFQNs: mockTagFQNsForHighlight, - tags: mockTagsDataBeforeSortAndHighlight, + expect(resultFormattedData).toEqual(mockEntityDataWithNestingResponse); }); - expect(sortedTags).toEqual(mockTagsDataAfterSortAndHighlight); - }); + it('getFormattedEntityData should return formatted data properly for pipeline data without nesting', () => { + const resultFormattedData = getFormattedEntityData( + SummaryEntityType.TASK, + mockEntityDataWithoutNesting + ); - it('getSummaryListItemType should return the summary item type based on given entityType', () => { - const summaryItemType = getSummaryListItemType( - SummaryEntityType.COLUMN, - mockEntityDataWithoutNesting[0] - ); - - expect(summaryItemType).toEqual(mockGetSummaryListItemTypeResponse); - }); - - it('getTitle should return title as link or text based on sourceUrl present or not in given data', () => { - const textBasedTitle = getTitle({ - content: 'Title1', - sourceUrl: undefined, + expect(resultFormattedData).toEqual(mockEntityDataWithoutNestingResponse); }); - expect(textBasedTitle).toEqual(mockTextBasedSummaryTitleResponse); + it('getFormattedEntityData should return empty array in case entityType is given other than from type SummaryEntityType', () => { + const resultFormattedData = getFormattedEntityData( + 'otherType' as SummaryEntityType, + mockEntityDataWithNesting + ); - const linkBasedTitle = getTitle({ - content: 'Title2', - sourceUrl: 'https://task1.com', + expect(resultFormattedData).toEqual([]); }); - expect(linkBasedTitle).toEqual(mockLinkBasedSummaryTitleResponse); + it('getFormattedEntityData should not throw error if entityDetails sent does not have fields present', () => { + const resultFormattedData = getFormattedEntityData( + SummaryEntityType.COLUMN, + [{}] as Column[] + ); + + expect(resultFormattedData).toEqual(mockInvalidDataResponse); + }); + }); + + describe('getSortedTagsWithHighlight', () => { + it('getSortedTagsWithHighlight should return the sorted and highlighted tags data based on given tagFQN array', () => { + const sortedTags = getSortedTagsWithHighlight( + mockEntityDataWithNesting[2].tags, + mockTagFQNsForHighlight + ); + + expect(sortedTags).toEqual(mockTagsSortAndHighlightResponse); + }); + }); + + describe('getSummaryListItemType', () => { + it('getSummaryListItemType should return the summary item type based on given entityType', () => { + const summaryItemType = getSummaryListItemType( + SummaryEntityType.TASK, + mockEntityDataWithoutNesting[0] + ); + + expect(summaryItemType).toEqual(mockGetSummaryListItemTypeResponse); + }); + }); + + describe('getTitle', () => { + it('getTitle should return title as text if sourceUrl not present in listItem and also apply highlight if present', () => { + const textBasedTitle = getTitle( + mockEntityDataWithNesting[0], + mockListItemNameHighlight + ); + + expect(textBasedTitle).toEqual(mockTextBasedSummaryTitleResponse); + }); + + it('getTitle should return title as link if sourceUrl present in listItem', () => { + const linkBasedTitle = getTitle(mockEntityDataWithoutNesting[0]); + + expect(linkBasedTitle).toEqual(mockLinkBasedSummaryTitleResponse); + }); + }); + + describe('getMapOfListHighlights', () => { + it('getMapOfListHighlights should returns empty arrays and map when highlights is undefined', () => { + const result = getMapOfListHighlights(); + + expect(result.listHighlights).toEqual([]); + expect(result.listHighlightsMap).toEqual({}); + }); + + it('getMapOfListHighlights should returns listHighlights and listHighlightsMap correctly', () => { + const result = getMapOfListHighlights(mockHighlights); + + expect(result).toEqual(mockGetMapOfListHighlightsResponse); + }); + }); + + describe('getHighlightOfListItem', () => { + it('getHighlightOfListItem should return highlights of listItem undefined, if listHighlights and tagHighlights not passed in params', () => { + const result = getHighlightOfListItem( + mockEntityDataWithNesting[0], + [] as string[], + [] as string[], + {} as { [key: string]: number } + ); + + expect(result).toEqual({ + highlightedTags: undefined, + highlightedTitle: undefined, + highlightedDescription: undefined, + }); + }); + + it('getHighlightOfListItem should return highlights of listItem if listHighlights and tagHighlights get in params', () => { + const result = getHighlightOfListItem( + mockEntityDataWithNesting[1], + mockTagFQNsForHighlight, + mockGetMapOfListHighlightsResponse.listHighlights, + mockGetMapOfListHighlightsResponse.listHighlightsMap + ); + + expect(result).toEqual(mockGetHighlightOfListItemResponse); + }); }); }); diff --git a/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.tsx b/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.tsx index 61c3f31d877..f4b9b06d666 100644 --- a/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/utils/EntitySummaryPanelUtils.tsx @@ -17,7 +17,10 @@ import React from 'react'; import { Link } from 'react-router-dom'; import { SearchedDataProps } from '../../src/components/SearchedData/SearchedData.interface'; import { ReactComponent as IconExternalLink } from '../assets/svg/external-links.svg'; -import { BasicEntityInfo } from '../components/Explore/EntitySummaryPanel/SummaryList/SummaryList.interface'; +import { + BasicEntityInfo, + HighlightedTagLabel, +} from '../components/Explore/EntitySummaryPanel/SummaryList/SummaryList.interface'; import { NO_DATA_PLACEHOLDER } from '../constants/constants'; import { SummaryListHighlightKeys } from '../constants/EntitySummaryPanelUtils.constant'; import { SummaryEntityType } from '../enums/EntitySummary.enum'; @@ -37,20 +40,30 @@ export interface EntityNameProps { displayName?: string; } -export interface HighlightedTagLabel extends TagLabel { - isHighlighted: boolean; +export type SummaryListItem = Column | Field | Chart | Task | MlFeature; + +export interface ListItemHighlights { + highlightedTags?: BasicEntityInfo['tags']; + highlightedTitle?: string; + highlightedDescription?: string; } -const getTitleName = (data: EntityNameProps) => - getEntityName(data) || NO_DATA_PLACEHOLDER; +/* @param { + listItem: SummaryItem, + highlightedTitle: will be a string if the title of given summaryItem is present in highlights | undefined +} + + @return SummaryItemTitle +*/ +export const getTitle = ( + listItem: SummaryListItem, + highlightedTitle?: ListItemHighlights['highlightedTitle'] +): JSX.Element | JSX.Element[] => { + const title = highlightedTitle + ? stringToHTML(highlightedTitle) + : getEntityName(listItem) || NO_DATA_PLACEHOLDER; + const sourceUrl = (listItem as Chart | Task).sourceUrl; -export const getTitle = ({ - content, - sourceUrl, -}: { - content: string | JSX.Element | JSX.Element[] | undefined; - sourceUrl: string | undefined; -}) => { return sourceUrl ? (
@@ -58,65 +71,189 @@ export const getTitle = ({ className="entity-title text-link-color font-medium m-r-xss" data-testid="entity-title" ellipsis={{ tooltip: true }}> - {content} + {title}
) : ( - {content} + {title} ); }; +/* @param { + entityType: will be any type of SummaryEntityType, + listItem: SummaryItem +} + @return listItemType +*/ export const getSummaryListItemType = ( entityType: SummaryEntityType, - listItemInfo: Column | Field | Chart | Task | MlFeature -) => { + listItem: SummaryListItem +): BasicEntityInfo['type'] => { switch (entityType) { case SummaryEntityType.COLUMN: case SummaryEntityType.FIELD: case SummaryEntityType.MLFEATURE: case SummaryEntityType.SCHEMAFIELD: - return (listItemInfo as Column | Field | MlFeature).dataType; + return (listItem as Column | Field | MlFeature).dataType; case SummaryEntityType.CHART: - return (listItemInfo as Chart).chartType; + return (listItem as Chart).chartType; case SummaryEntityType.TASK: - return (listItemInfo as Task).taskType; + return (listItem as Task).taskType; default: return ''; } }; -export const getSortedTagsWithHighlight = ({ - sortTagsBasedOnGivenTagFQNs, - tags, -}: { - sortTagsBasedOnGivenTagFQNs: string[]; - tags?: TagLabel[]; -}): (TagLabel | HighlightedTagLabel)[] => { - const ColumnDataTags: { - tagForSort: HighlightedTagLabel[]; - remainingTags: TagLabel[]; - } = { tagForSort: [], remainingTags: [] }; - - tags?.reduce((acc, tag) => { - if (sortTagsBasedOnGivenTagFQNs.includes(tag.tagFQN)) { - acc.tagForSort.push({ ...tag, isHighlighted: true }); - } else { - acc.remainingTags.push(tag); +/* + @params { + sortTagsBasedOnGivenTagFQNs: array of TagFQNs, + tags: Tags array, } - return acc; - }, ColumnDataTags); + @return array of tags highlighted and sorted if tagFQN present in sortTagsBasedOnGivenTagFQNs +*/ +export const getSortedTagsWithHighlight = ( + tags: TagLabel[] = [], + sortTagsBasedOnGivenTagFQNs: string[] = [] +): ListItemHighlights['highlightedTags'] => { + const { sortedTags, remainingTags } = tags.reduce( + (acc, tag) => { + if (sortTagsBasedOnGivenTagFQNs.includes(tag.tagFQN)) { + acc.sortedTags.push({ ...tag, isHighlighted: true }); + } else { + acc.remainingTags.push(tag); + } - return [...ColumnDataTags.tagForSort, ...ColumnDataTags.remainingTags]; + return acc; + }, + { + sortedTags: [] as HighlightedTagLabel[], + remainingTags: [] as TagLabel[], + } + ); + + return [...sortedTags, ...remainingTags]; }; +/* + @param {highlights: all the other highlights come from the query api + only omitted displayName and description key as it is already updated in parent component + } + + @return { + listHighlights: single array of all highlights get from query api + listHighlightsMap: to reduce the search time complexity in listHighlight + } + + Todo: apply highlights on entityData in parent where we apply highlight for entityDisplayName and entityDescription + for that we need to update multiple summary components +*/ +export const getMapOfListHighlights = ( + highlights?: SearchedDataProps['data'][number]['highlight'] +): { + listHighlights: string[]; + listHighlightsMap: { [key: string]: number }; +} => { + // checking for the all highlight key present in highlight get from query api + // and create a array of highlights + const listHighlights: string[] = []; + SummaryListHighlightKeys.forEach((highlightKey) => { + listHighlights.push(...get(highlights, highlightKey, [])); + }); + + // using hashmap methodology to reduce the search time complexity from O(n) to O(1) + // to get highlight from the listHighlights array for applying highlight + const listHighlightsMap: { [key: string]: number } = {}; + + listHighlights?.reduce((acc, colHighlight, index) => { + acc[colHighlight.replaceAll(/<\/?span(.*?)>/g, '')] = index; + + return acc; + }, listHighlightsMap); + + return { listHighlights, listHighlightsMap }; +}; + +/* + @params { + listItem: SummaryItem + tagsHighlights: tagFQNs array to highlight and sort tags + listHighlights: single array of all highlights get from query api + listHighlightsMap: to reduce the search time complexity in listHighlight + } + @return highlights of listItem +*/ +export const getHighlightOfListItem = ( + listItem: SummaryListItem, + tagHighlights: string[], + listHighlights: string[], + listHighlightsMap: { [key: string]: number } +): ListItemHighlights => { + let highlightedTags; + let highlightedTitle; + let highlightedDescription; + + // if any of the listItem.tags present in given tagHighlights list then sort and highlights the tag + const shouldSortListItemTags = listItem.tags?.find((tag) => + tagHighlights.includes(tag.tagFQN) + ); + + if (shouldSortListItemTags) { + highlightedTags = getSortedTagsWithHighlight(listItem.tags, tagHighlights); + } + + // highlightedListItemNameIndex will be undefined if listItem.name is not present in highlights + const highlightedListItemNameIndex = listHighlightsMap[listItem.name ?? '']; + + const shouldApplyHighlightOnTitle = !isUndefined( + highlightedListItemNameIndex + ); + + if (shouldApplyHighlightOnTitle) { + highlightedTitle = listHighlights[highlightedListItemNameIndex]; + } + + // highlightedListItemDescriptionIndex will be undefined if listItem.description is not present in highlights + const highlightedListItemDescriptionIndex = + listHighlightsMap[listItem.description ?? '']; + + const shouldApplyHighlightOnDescription = !isUndefined( + highlightedListItemDescriptionIndex + ); + + if (shouldApplyHighlightOnDescription) { + highlightedDescription = + listHighlights[highlightedListItemDescriptionIndex]; + } + + return { + highlightedTags, + highlightedTitle, + highlightedDescription, + }; +}; + +/* + @params { + entityType: SummaryEntityType, + entityInfo: Array = [], + highlights: highlights get from the query api + highlights added for tags (i.e. tag.name) + tableConstraints: only pass for SummayEntityType.Column + } + @return sorted and highlighted listItem array, but listItem will be type of BasicEntityInfo + + Note: SummaryItem will be sort and highlight only if - + # if listItem.tags present in highlights.tags + # if listItem.name present in highlights comes from query api + # if listItem.description present in highlights comes from query api +*/ export const getFormattedEntityData = ( entityType: SummaryEntityType, - entityInfo?: Array, + entityInfo: Array = [], highlights?: SearchedDataProps['data'][number]['highlight'], tableConstraints?: TableConstraint[] ): BasicEntityInfo[] => { @@ -124,97 +261,68 @@ export const getFormattedEntityData = ( return []; } - // sort and highlights list items based on tags and global search highlights data + // Only go ahead if entityType is present in SummaryEntityType enum if (Object.values(SummaryEntityType).includes(entityType)) { + // tagHighlights is the array of tagFQNs for highlighting tags const tagHighlights = get(highlights, 'tag.name', [] as string[]); - const listHighlights: string[] = []; - const listHighlightsMap: { [key: string]: number } = {}; - const SummaryListData = { - listItemWithSortOption: [] as BasicEntityInfo[], - listItemWithoutSortOption: [] as BasicEntityInfo[], - }; - SummaryListHighlightKeys.forEach((highlightKey) => { - listHighlights.push(...get(highlights, highlightKey, [])); - }); + // listHighlights i.e. highlight get from query api + // listHighlightsMap i.e. map of highlight get from api to reduce search time complexity in highlights array + const { listHighlights, listHighlightsMap } = + getMapOfListHighlights(highlights); - listHighlights?.reduce((acc, colHighlight, index) => { - acc[colHighlight.replaceAll(/<\/?span(.*?)>/g, '')] = index; + const { highlightedListItem, remainingListItem } = entityInfo.reduce( + (acc, listItem) => { + // return the highlight of listItem + const { highlightedTags, highlightedTitle, highlightedDescription } = + getHighlightOfListItem( + listItem, + tagHighlights, + listHighlights, + listHighlightsMap + ); - return acc; - }, listHighlightsMap); + // convert listItem in BasicEntityInfo type + const listItemModifiedData = { + name: listItem.name ?? '', + title: getTitle(listItem, highlightedTitle), + type: getSummaryListItemType(entityType, listItem), + tags: highlightedTags ?? listItem.tags, + description: highlightedDescription ?? listItem.description, + ...(entityType === SummaryEntityType.COLUMN && { + columnConstraint: (listItem as Column).constraint, + tableConstraints: tableConstraints, + }), + ...(entityType === SummaryEntityType.MLFEATURE && { + algorithm: (listItem as MlFeature).featureAlgorithm, + }), + ...((entityType === SummaryEntityType.COLUMN || + entityType === SummaryEntityType.FIELD) && { + children: getFormattedEntityData( + entityType, + (listItem as Column | Field).children, + highlights + ), + }), + }; - entityInfo?.reduce((acc, listItem) => { - const listItemModifiedData = { - name: listItem.name ?? '', - title: getTitle({ - content: getTitleName(listItem), - sourceUrl: (listItem as Chart | Task).sourceUrl, - }), - type: getSummaryListItemType(entityType, listItem), - tags: listItem.tags, - description: listItem.description, - ...(entityType === SummaryEntityType.COLUMN && { - columnConstraint: (listItem as Column).constraint, - tableConstraints: tableConstraints, - }), - ...(entityType === SummaryEntityType.MLFEATURE && { - algorithm: (listItem as MlFeature).featureAlgorithm, - }), - children: getFormattedEntityData( - entityType, - (listItem as Column | Field).children, - highlights, - tableConstraints - ), - }; - - const isTagHighlightsPresentInListItemTags = listItem.tags?.find((tag) => - tagHighlights.includes(tag.tagFQN) - ); - - const highlightedListItemNameIndex = - listHighlightsMap[listItem.name ?? '']; - const highlightedListItemDescriptionIndex = - listHighlightsMap[listItem.description ?? '']; - - if ( - isTagHighlightsPresentInListItemTags || - !isUndefined(highlightedListItemNameIndex) || - !isUndefined(highlightedListItemDescriptionIndex) - ) { - if (isTagHighlightsPresentInListItemTags) { - listItemModifiedData.tags = getSortedTagsWithHighlight({ - sortTagsBasedOnGivenTagFQNs: tagHighlights, - tags: listItem.tags, - }); + // if highlights present in listItem then sort the listItem + if (highlightedTags || highlightedTitle || highlightedDescription) { + acc.highlightedListItem.push(listItemModifiedData); + } else { + acc.remainingListItem.push(listItemModifiedData); } - if (!isUndefined(highlightedListItemNameIndex)) { - listItemModifiedData.title = getTitle({ - content: stringToHTML(listHighlights[highlightedListItemNameIndex]), - sourceUrl: (listItem as Chart | Task).sourceUrl, - }); - } - - if (!isUndefined(highlightedListItemDescriptionIndex)) { - listItemModifiedData.description = - listHighlights[highlightedListItemDescriptionIndex]; - } - - acc.listItemWithSortOption.push(listItemModifiedData); - } else { - acc.listItemWithoutSortOption.push(listItemModifiedData); + return acc; + }, + { + highlightedListItem: [] as BasicEntityInfo[], + remainingListItem: [] as BasicEntityInfo[], } + ); - return acc; - }, SummaryListData); - - return [ - ...SummaryListData.listItemWithSortOption, - ...SummaryListData.listItemWithoutSortOption, - ]; - } else { - return []; + return [...highlightedListItem, ...remainingListItem]; } + + return []; }; diff --git a/openmetadata-ui/src/main/resources/ui/src/utils/mocks/EntitySummaryPanelUtils.mock.tsx b/openmetadata-ui/src/main/resources/ui/src/utils/mocks/EntitySummaryPanelUtils.mock.tsx index 84f48aa15d0..8b3edaa9d4b 100644 --- a/openmetadata-ui/src/main/resources/ui/src/utils/mocks/EntitySummaryPanelUtils.mock.tsx +++ b/openmetadata-ui/src/main/resources/ui/src/utils/mocks/EntitySummaryPanelUtils.mock.tsx @@ -14,6 +14,8 @@ import { Typography } from 'antd'; import React from 'react'; import { Link } from 'react-router-dom'; +import { BasicEntityInfo } from '../../components/Explore/EntitySummaryPanel/SummaryList/SummaryList.interface'; +import { Task } from '../../generated/entity/data/pipeline'; import { Column, DataType, @@ -21,21 +23,189 @@ import { State, TagSource, } from '../../generated/entity/data/table'; -import { DataTypeTopic, Field } from '../../generated/entity/data/topic'; import { ReactComponent as IconExternalLink } from '../assets/svg/external-links.svg'; const { Text } = Typography; -export const mockEntityDataWithoutNesting: Column[] = [ +export const mockTextBasedSummaryTitleResponse = ( + + title2 + +); + +export const mockLinkBasedSummaryTitleResponse = ( + +
+ + dim_address Task + + +
+ +); + +export const mockGetSummaryListItemTypeResponse = 'PrestoOperator'; + +export const mockTagsSortAndHighlightResponse = [ { - name: 'title', + tagFQN: 'PersonalData.SpecialCategory', + description: + 'GDPR special category data is personal information of data subjects that is especially sensitive.', + source: TagSource.Classification, + labelType: LabelType.Manual, + state: State.Confirmed, + isHighlighted: true, + }, + { + tagFQN: 'PersonalData.Category1', + description: + 'GDPR special category data is personal information of data subjects that is especially sensitive.', + source: TagSource.Classification, + labelType: LabelType.Manual, + state: State.Confirmed, + }, +]; + +export const mockTagFQNsForHighlight = ['PersonalData.SpecialCategory']; + +export const mockListItemNameHighlight = + 'title2'; + +const mockListItemDescriptionHighlight = + 'some description of title2'; + +export const mockHighlights = { + 'columns.name': [mockListItemNameHighlight], + 'columns.description': [mockListItemDescriptionHighlight], + 'tag.name': mockTagFQNsForHighlight, +}; + +export const mockGetMapOfListHighlightsResponse = { + listHighlights: [mockListItemNameHighlight, mockListItemDescriptionHighlight], + listHighlightsMap: { + title2: 0, + 'some description of title2': 1, + }, +}; + +export const mockGetHighlightOfListItemResponse = { + highlightedTags: undefined, + highlightedTitle: mockListItemNameHighlight, + highlightedDescription: mockListItemDescriptionHighlight, +}; + +export const mockEntityDataWithoutNesting: Task[] = [ + { + name: 'dim_address_task', + displayName: 'dim_address Task', + fullyQualifiedName: 'sample_airflow.dim_address_etl.dim_address_task', + description: + 'Airflow operator to perform ETL and generate dim_address table', + sourceUrl: + 'http://localhost:8080/taskinstance/list/?flt1_dag_id_equals=dim_address_task', + downstreamTasks: ['assert_table_exists'], + taskType: 'PrestoOperator', + tags: [], + }, + { + name: 'assert_table_exists', + displayName: 'Assert Table Exists', + fullyQualifiedName: 'sample_airflow.dim_address_etl.assert_table_exists', + description: 'Assert if a table exists', + sourceUrl: + 'http://localhost:8080/taskinstance/list/?flt1_dag_id_equals=assert_table_exists', + downstreamTasks: [], + taskType: 'HiveOperator', + tags: [], + }, +]; + +export const mockEntityDataWithoutNestingResponse: BasicEntityInfo[] = [ + { + name: 'dim_address_task', + title: mockLinkBasedSummaryTitleResponse, + description: + 'Airflow operator to perform ETL and generate dim_address table', + type: mockGetSummaryListItemTypeResponse, + tags: [], + }, + { + name: 'assert_table_exists', + title: ( + +
+ + Assert Table Exists + + +
+ + ), + description: 'Assert if a table exists', + type: 'HiveOperator', + tags: [], + }, +]; + +export const mockEntityDataWithNesting: Column[] = [ + { + name: 'Customer', + dataType: DataType.Varchar, + fullyQualifiedName: 'sample_kafka.customer_events.Customer', + tags: [], + description: + 'Full name of the app or channel. For example, Point of Sale, Online Store.', + children: [ + { + name: 'id', + dataType: DataType.Varchar, + fullyQualifiedName: 'sample_kafka.customer_events.Customer.id', + tags: [], + }, + { + name: 'first_name', + dataType: DataType.Varchar, + fullyQualifiedName: 'sample_kafka.customer_events.Customer.first_name', + tags: [], + }, + { + name: 'last_name', + dataType: DataType.Varchar, + fullyQualifiedName: 'sample_kafka.customer_events.Customer.last_name', + tags: [], + }, + { + name: 'email', + dataType: DataType.Varchar, + fullyQualifiedName: 'sample_kafka.customer_events.Customer.email', + tags: [], + }, + ], + }, + { + name: 'title2', dataType: DataType.Varchar, dataLength: 100, dataTypeDisplay: 'varchar', - description: - 'Full name of the app or channel. For example, Point of Sale, Online Store.', + description: 'some description of title2', fullyQualifiedName: - 'sample_data.ecommerce_db.shopify."dim.api/client".title', + 'sample_data.ecommerce_db.shopify."dim.api/client".title2', tags: [], ordinalPosition: 2, }, @@ -69,227 +239,103 @@ export const mockEntityDataWithoutNesting: Column[] = [ }, ]; -export const mockEntityDataWithoutNestingResponse = [ +export const mockEntityDataWithNestingResponse: BasicEntityInfo[] = [ { + name: 'title2', + title: mockTextBasedSummaryTitleResponse, + type: DataType.Varchar, + description: mockListItemDescriptionHighlight, + tags: [], + tableConstraints: undefined, + columnConstraint: undefined, children: [], - description: - 'ID of the API client that called the Shopify API. For example, the ID for the online store is 580111.', + }, + { name: 'api_client_id', - tags: [ - { - tagFQN: 'PersonalData.SpecialCategory', - description: - 'GDPR special category data is personal information of data subjects that is especially sensitive.', - source: 'Classification', - labelType: 'Manual', - state: 'Confirmed', - isHighlighted: true, - }, - { - tagFQN: 'PersonalData.Category1', - description: - 'GDPR special category data is personal information of data subjects that is especially sensitive.', - source: 'Classification', - labelType: 'Manual', - state: 'Confirmed', - }, - ], title: ( api_client_id ), - type: 'NUMERIC', - tableConstraints: undefined, - columnConstraint: undefined, - }, - { - children: [], + type: DataType.Numeric, description: - 'Full name of the app or channel. For example, Point of Sale, Online Store.', - name: 'title', - tags: [], - title: ( - - title - - ), - type: 'VARCHAR', + 'ID of the API client that called the Shopify API. For example, the ID for the online store is 580111.', + tags: mockTagsSortAndHighlightResponse, tableConstraints: undefined, columnConstraint: undefined, + children: [], }, -]; - -export const mockEntityDataWithNesting: Field[] = [ { name: 'Customer', - dataType: DataTypeTopic.Record, - fullyQualifiedName: 'sample_kafka.customer_events.Customer', - tags: [], - children: [ - { - name: 'id', - dataType: DataTypeTopic.String, - fullyQualifiedName: 'sample_kafka.customer_events.Customer.id', - tags: [], - }, - { - name: 'first_name', - dataType: DataTypeTopic.String, - fullyQualifiedName: 'sample_kafka.customer_events.Customer.first_name', - tags: [], - }, - { - name: 'last_name', - dataType: DataTypeTopic.String, - fullyQualifiedName: 'sample_kafka.customer_events.Customer.last_name', - tags: [], - }, - { - name: 'email', - dataType: DataTypeTopic.String, - fullyQualifiedName: 'sample_kafka.customer_events.Customer.email', - tags: [], - }, - { - name: 'address_line_1', - dataType: DataTypeTopic.String, - fullyQualifiedName: - 'sample_kafka.customer_events.Customer.address_line_1', - tags: [], - }, - { - name: 'address_line_2', - dataType: DataTypeTopic.String, - fullyQualifiedName: - 'sample_kafka.customer_events.Customer.address_line_2', - tags: [], - }, - { - name: 'post_code', - dataType: DataTypeTopic.String, - fullyQualifiedName: 'sample_kafka.customer_events.Customer.post_code', - tags: [], - }, - { - name: 'country', - dataType: DataTypeTopic.String, - fullyQualifiedName: 'sample_kafka.customer_events.Customer.country', - tags: [], - }, - ], - }, -]; - -export const mockEntityDataWithNestingResponse = [ - { - children: [ - { - children: [], - description: undefined, - name: 'id', - tags: [], - title: ( - - id - - ), - type: 'STRING', - }, - { - children: [], - description: undefined, - name: 'first_name', - tags: [], - title: ( - - first_name - - ), - type: 'STRING', - }, - { - children: [], - description: undefined, - name: 'last_name', - tags: [], - title: ( - - last_name - - ), - type: 'STRING', - }, - { - children: [], - description: undefined, - name: 'email', - tags: [], - title: ( - - email - - ), - type: 'STRING', - }, - { - children: [], - description: undefined, - name: 'address_line_1', - tags: [], - title: ( - - address_line_1 - - ), - type: 'STRING', - }, - { - children: [], - description: undefined, - name: 'address_line_2', - tags: [], - title: ( - - address_line_2 - - ), - type: 'STRING', - }, - { - children: [], - description: undefined, - name: 'post_code', - tags: [], - title: ( - - post_code - - ), - type: 'STRING', - }, - { - children: [], - description: undefined, - name: 'country', - tags: [], - title: ( - - country - - ), - type: 'STRING', - }, - ], - description: undefined, - name: 'Customer', - tags: [], title: ( Customer ), - type: 'RECORD', + type: DataType.Varchar, + tags: [], + description: + 'Full name of the app or channel. For example, Point of Sale, Online Store.', + tableConstraints: undefined, + columnConstraint: undefined, + children: [ + { + name: 'id', + title: ( + + id + + ), + type: DataType.Varchar, + tags: [], + children: [], + description: undefined, + tableConstraints: undefined, + columnConstraint: undefined, + }, + { + name: 'first_name', + title: ( + + first_name + + ), + type: DataType.Varchar, + tags: [], + children: [], + description: undefined, + tableConstraints: undefined, + columnConstraint: undefined, + }, + { + name: 'last_name', + title: ( + + last_name + + ), + type: DataType.Varchar, + tags: [], + children: [], + description: undefined, + tableConstraints: undefined, + columnConstraint: undefined, + }, + { + name: 'email', + title: ( + + email + + ), + type: DataType.Varchar, + tags: [], + children: [], + description: undefined, + tableConstraints: undefined, + columnConstraint: undefined, + }, + ], }, ]; @@ -309,94 +355,3 @@ export const mockInvalidDataResponse = [ type: undefined, }, ]; - -export const mockTagsDataBeforeSortAndHighlight = [ - { - tagFQN: 'gs1.term1', - name: 'term1', - displayName: '', - description: 'term1 desc', - style: {}, - source: TagSource.Glossary, - labelType: LabelType.Manual, - state: State.Confirmed, - }, - { - tagFQN: 'gs1.term2', - name: 'term2', - displayName: '', - description: 'term2 desc', - style: {}, - source: TagSource.Glossary, - labelType: LabelType.Manual, - state: State.Confirmed, - }, - { - tagFQN: 'gs1.term3', - name: 'term3', - displayName: '', - description: 'term3 desc', - style: {}, - source: TagSource.Glossary, - labelType: LabelType.Manual, - state: State.Confirmed, - }, -]; - -export const mockTagsDataAfterSortAndHighlight = [ - { - tagFQN: 'gs1.term2', - name: 'term2', - displayName: '', - description: 'term2 desc', - style: {}, - source: TagSource.Glossary, - labelType: LabelType.Manual, - state: State.Confirmed, - isHighlighted: true, - }, - { - tagFQN: 'gs1.term1', - name: 'term1', - displayName: '', - description: 'term1 desc', - style: {}, - source: TagSource.Glossary, - labelType: LabelType.Manual, - state: State.Confirmed, - }, - { - tagFQN: 'gs1.term3', - name: 'term3', - displayName: '', - description: 'term3 desc', - style: {}, - source: TagSource.Glossary, - labelType: LabelType.Manual, - state: State.Confirmed, - }, -]; - -export const mockTagFQNsForHighlight = ['gs1.term2']; - -export const mockGetSummaryListItemTypeResponse = DataType.Varchar; - -export const mockTextBasedSummaryTitleResponse = ( - - Title1 - -); - -export const mockLinkBasedSummaryTitleResponse = ( - -
- - Title2 - - -
- -);