diff --git a/datahub-web-react/src/app/preview/DefaultPreviewCard.tsx b/datahub-web-react/src/app/preview/DefaultPreviewCard.tsx
index 94660c123e..4dac5c7971 100644
--- a/datahub-web-react/src/app/preview/DefaultPreviewCard.tsx
+++ b/datahub-web-react/src/app/preview/DefaultPreviewCard.tsx
@@ -36,7 +36,8 @@ const PlatformInfo = styled.div`
`;
const TitleContainer = styled.div`
- margin-bottom: 8px;
+ margin-bottom: 0px;
+ line-height: 30px;
`;
const PreviewImage = styled(Image)`
@@ -49,7 +50,7 @@ const PreviewImage = styled(Image)`
const EntityTitle = styled(Typography.Text)<{ $titleSizePx?: number }>`
&&& {
- margin-bottom: 0;
+ margin-right 8px;
font-size: ${(props) => props.$titleSizePx || 16}px;
font-weight: 600;
vertical-align: middle;
@@ -91,7 +92,7 @@ const AvatarContainer = styled.div`
const TagContainer = styled.div`
display: inline-block;
- margin-left: 8px;
+ margin-left: 0px;
margin-top: -2px;
`;
diff --git a/datahub-web-react/src/app/search/SearchFilterLabel.tsx b/datahub-web-react/src/app/search/SearchFilterLabel.tsx
index 34682f2611..d842dd4a2e 100644
--- a/datahub-web-react/src/app/search/SearchFilterLabel.tsx
+++ b/datahub-web-react/src/app/search/SearchFilterLabel.tsx
@@ -1,8 +1,7 @@
import { BookOutlined } from '@ant-design/icons';
-import { Tag } from 'antd';
+import { Tag, Tooltip } from 'antd';
import * as React from 'react';
import styled from 'styled-components';
-
import {
AggregationMetadata,
Domain,
@@ -53,24 +52,27 @@ export const SearchFilterLabel = ({ aggregation, field }: Props) => {
if (aggregation.entity?.type === EntityType.Tag) {
const tag = aggregation.entity as TagType;
+ const displayName = entityRegistry.getDisplayName(EntityType.Tag, tag);
+ const truncatedDisplayName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
+
- {tag?.name}
+ {truncatedDisplayName}
({countText})
- >
+
);
}
if (aggregation.entity?.type === EntityType.CorpUser) {
const user = aggregation.entity as CorpUser;
const displayName = entityRegistry.getDisplayName(EntityType.CorpUser, user);
+ const truncatedDisplayName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
+
{
}}
/>
{displayName} ({countText})
- >
+
);
}
if (aggregation.entity?.type === EntityType.CorpGroup) {
const group = aggregation.entity as CorpGroup;
+ const displayName = entityRegistry.getDisplayName(EntityType.CorpGroup, group);
+ const truncatedDisplayName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
+
{entityRegistry.getIcon(EntityType.CorpGroup, 16, IconStyleType.ACCENT)}
- {entityRegistry.getDisplayName(EntityType.CorpGroup, group)} ({countText})
- >
+ {truncatedDisplayName} ({countText})
+
);
}
if (aggregation.entity?.type === EntityType.GlossaryTerm) {
const term = aggregation.entity as GlossaryTerm;
+ const displayName = entityRegistry.getDisplayName(EntityType.GlossaryTerm, term);
+ const truncatedDisplayName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
+
- {entityRegistry.getDisplayName(EntityType.GlossaryTerm, term)}
+ {truncatedDisplayName}
({countText})
- >
+
);
}
if (aggregation.entity?.type === EntityType.DataPlatform) {
const platform = aggregation.entity as DataPlatform;
+ const displayName = platform.properties?.displayName || platform.info?.displayName || platform.name;
+ const truncatedDisplayName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
+
{!!platform.properties?.logoUrl && (
)}
- {platform.properties?.displayName || platform.name} ({countText})
+ {truncatedDisplayName} ({countText})
- >
+
);
}
if (aggregation.entity?.type === EntityType.Container) {
const container = aggregation.entity as Container;
+ const displayName = entityRegistry.getDisplayName(EntityType.Container, container);
+ const truncatedDisplayName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
+
{!!container.platform?.properties?.logoUrl && (
)}
- {container.properties?.name} ({countText})
+ {truncatedDisplayName} ({countText})
- >
+
);
}
if (aggregation.entity?.type === EntityType.Domain) {
const domain = aggregation.entity as Domain;
+ const displayName = entityRegistry.getDisplayName(EntityType.Domain, domain);
+ const truncatedDomainName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
- (
- {countText})
- >
+
+ ({countText})
+
);
}
// Warning: Special casing for Sub-Types
if (field === 'typeNames') {
- const subTypeDisplayName = capitalizeFirstLetter(aggregation.value);
+ const displayName = capitalizeFirstLetter(aggregation.value) || '';
+ const truncatedDomainName = displayName.length > 25 ? `${displayName.slice(0, 25)}...` : displayName;
return (
- <>
+
- {subTypeDisplayName} ({countText})
+ {truncatedDomainName} ({countText})
- >
+
);
}
diff --git a/datahub-web-react/src/app/shared/TagStyleEntity.tsx b/datahub-web-react/src/app/shared/TagStyleEntity.tsx
index 69a30a7437..81aa5a3dff 100644
--- a/datahub-web-react/src/app/shared/TagStyleEntity.tsx
+++ b/datahub-web-react/src/app/shared/TagStyleEntity.tsx
@@ -1,11 +1,11 @@
-import React, { useEffect, useState } from 'react';
+import React, { useCallback, useEffect, useRef, useState } from 'react';
import { grey } from '@ant-design/colors';
import { Alert, Button, Divider, message, Typography } from 'antd';
import { useHistory } from 'react-router';
import { ApolloError } from '@apollo/client';
import styled from 'styled-components';
import { ChromePicker } from 'react-color';
-
+import ColorHash from 'color-hash';
import { PlusOutlined } from '@ant-design/icons';
import { useGetTagQuery } from '../../graphql/tag.generated';
import { EntityType, FacetMetadata, Maybe, Scalars } from '../../types.generated';
@@ -61,7 +61,6 @@ const TitleText = styled(Typography.Text)`
const ColorPicker = styled.div`
position: relative;
display: inline-block;
- margin-top: 1em;
`;
const ColorPickerButton = styled.div`
@@ -141,6 +140,12 @@ const OwnerButtonTitle = styled.span`
color: ${grey[10]};
`;
+const TagName = styled.div`
+ display: flex;
+ align-items: center;
+ justify-content: left;
+`;
+
const { Paragraph } = Typography;
type Props = {
@@ -152,6 +157,10 @@ type Props = {
};
};
+const generateColor = new ColorHash({
+ saturation: 0.9,
+});
+
/**
* Responsible for displaying metadata about a tag
*/
@@ -166,7 +175,7 @@ export default function TagStyleEntity({ urn, useGetSearchResults = useWrappedSe
const description = data?.tag?.properties?.description || '';
const [updatedDescription, setUpdatedDescription] = useState('');
- const hexColor = data?.tag?.properties?.colorHex || '';
+ const hexColor = data?.tag?.properties?.colorHex || generateColor.hex(urn);
const [displayColorPicker, setDisplayColorPicker] = useState(false);
const [colorValue, setColorValue] = useState('');
const ownersEmpty = !data?.tag?.ownership?.owners?.length;
@@ -195,9 +204,8 @@ export default function TagStyleEntity({ urn, useGetSearchResults = useWrappedSe
const aggregations = facets && facets[0]?.aggregations;
// Save Color Change
- const saveColor = async () => {
+ const saveColor = useCallback(async () => {
if (displayColorPicker) {
- message.loading({ content: 'Saving...' });
try {
await setTagColorMutation({
variables: {
@@ -206,17 +214,42 @@ export default function TagStyleEntity({ urn, useGetSearchResults = useWrappedSe
},
});
message.destroy();
- message.success({ content: 'Color Updated', duration: 2 });
+ message.success({ content: 'Color Saved!', duration: 2 });
setDisplayColorPicker(false);
} catch (e: unknown) {
message.destroy();
if (e instanceof Error) {
- message.error({ content: `Failed to update Color: \n ${e.message || ''}`, duration: 2 });
+ message.error({ content: `Failed to save tag color: \n ${e.message || ''}`, duration: 2 });
}
}
refetch?.();
}
- };
+ }, [urn, colorValue, displayColorPicker, setTagColorMutation, setDisplayColorPicker, refetch]);
+
+ const colorPickerRef = useRef(null);
+
+ useEffect(() => {
+ /**
+ * Save Color if Clicked outside of the Color Picker
+ */
+ function handleClickOutsideColorPicker(event) {
+ if (displayColorPicker) {
+ const { current }: any = colorPickerRef;
+ if (current) {
+ if (!current.contains(event.target)) {
+ setDisplayColorPicker(false);
+ saveColor();
+ }
+ }
+ }
+ }
+ // Bind the event listener
+ document.addEventListener('mousedown', handleClickOutsideColorPicker);
+ return () => {
+ // Unbind the event listener on clean up
+ document.removeEventListener('mousedown', handleClickOutsideColorPicker);
+ };
+ }, [colorPickerRef, displayColorPicker, saveColor]);
const handlePickerClick = () => {
setDisplayColorPicker(!displayColorPicker);
@@ -271,15 +304,17 @@ export default function TagStyleEntity({ urn, useGetSearchResults = useWrappedSe
{/* Tag Title */}
Tag
-
-
-
+
+
+
+
+ {data?.tag?.properties?.name}
+
{displayColorPicker && (
-
+
)}
- {data?.tag?.properties?.name}
{/* Tag Description */}
diff --git a/datahub-web-react/src/app/shared/tags/DomainLink.tsx b/datahub-web-react/src/app/shared/tags/DomainLink.tsx
index bab0a81714..35d31d363f 100644
--- a/datahub-web-react/src/app/shared/tags/DomainLink.tsx
+++ b/datahub-web-react/src/app/shared/tags/DomainLink.tsx
@@ -16,13 +16,14 @@ export type Props = {
name: string;
closable?: boolean;
onClose?: (e: any) => void;
+ tagStyle?: any | undefined;
};
-export const DomainLink = ({ urn, name, closable, onClose }: Props): JSX.Element => {
+export const DomainLink = ({ urn, name, closable, onClose, tagStyle }: Props): JSX.Element => {
const entityRegistry = useEntityRegistry();
return (
-
+
{entityRegistry.getIcon(EntityType.Domain, 10, IconStyleType.ACCENT)}