Skip to content

Commit

Permalink
Merge branch 'master' into feat/supportMultiSort
Browse files Browse the repository at this point in the history
  • Loading branch information
RyanHolstien authored Aug 9, 2024
2 parents 378a325 + 5b16252 commit c2ff037
Show file tree
Hide file tree
Showing 56 changed files with 720 additions and 426 deletions.
1 change: 0 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -138,7 +138,6 @@ Here are the companies that have officially adopted DataHub. Please feel free to
- [Peloton](https://www.onepeloton.com)
- [PITS Global Data Recovery Services](https://www.pitsdatarecovery.net/)
- [Razer](https://www.razer.com)
- [Saxo Bank](https://www.home.saxo)
- [Showroomprive](https://www.showroomprive.com/)
- [SpotHero](https://spothero.com)
- [Stash](https://www.stash.com)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,5 +21,6 @@ public class FeatureFlags {
private boolean schemaFieldEntityFetchEnabled = false;
private boolean businessAttributeEntityEnabled = false;
private boolean dataContractsEnabled = false;
private boolean editableDatasetNameEnabled = false;
private boolean showSeparateSiblings = false;
}
Original file line number Diff line number Diff line change
Expand Up @@ -186,6 +186,7 @@ public CompletableFuture<AppConfig> get(final DataFetchingEnvironment environmen
.setNestedDomainsEnabled(_featureFlags.isNestedDomainsEnabled())
.setPlatformBrowseV2(_featureFlags.isPlatformBrowseV2())
.setDataContractsEnabled(_featureFlags.isDataContractsEnabled())
.setEditableDatasetNameEnabled(_featureFlags.isEditableDatasetNameEnabled())
.setShowSeparateSiblings(_featureFlags.isShowSeparateSiblings())
.build();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,11 @@
import static com.linkedin.datahub.graphql.resolvers.mutate.MutationUtils.persistAspect;

import com.linkedin.businessattribute.BusinessAttributeInfo;
import com.linkedin.common.AuditStamp;
import com.linkedin.common.urn.CorpuserUrn;
import com.linkedin.common.urn.Urn;
import com.linkedin.common.urn.UrnUtils;
import com.linkedin.data.template.SetMode;
import com.linkedin.datahub.graphql.QueryContext;
import com.linkedin.datahub.graphql.authorization.AuthorizationUtils;
import com.linkedin.datahub.graphql.concurrency.GraphQLConcurrencyUtils;
Expand All @@ -20,6 +22,7 @@
import com.linkedin.datahub.graphql.resolvers.mutate.util.DomainUtils;
import com.linkedin.datahub.graphql.resolvers.mutate.util.GlossaryUtils;
import com.linkedin.dataproduct.DataProductProperties;
import com.linkedin.dataset.EditableDatasetProperties;
import com.linkedin.domain.DomainProperties;
import com.linkedin.domain.Domains;
import com.linkedin.entity.client.EntityClient;
Expand Down Expand Up @@ -70,6 +73,8 @@ public CompletableFuture<Boolean> get(DataFetchingEnvironment environment) throw
return updateDataProductName(targetUrn, input, context);
case Constants.BUSINESS_ATTRIBUTE_ENTITY_NAME:
return updateBusinessAttributeName(targetUrn, input, environment.getContext());
case Constants.DATASET_ENTITY_NAME:
return updateDatasetName(targetUrn, input, environment.getContext());
default:
throw new RuntimeException(
String.format(
Expand Down Expand Up @@ -236,6 +241,37 @@ private Boolean updateGroupName(Urn targetUrn, UpdateNameInput input, QueryConte
"Unauthorized to perform this action. Please contact your DataHub administrator.");
}

// udpates editable dataset properties aspect's name field
private Boolean updateDatasetName(Urn targetUrn, UpdateNameInput input, QueryContext context) {
if (AuthorizationUtils.canEditProperties(targetUrn, context)) {
try {
if (input.getName() != null) {
final EditableDatasetProperties editableDatasetProperties =
new EditableDatasetProperties();
editableDatasetProperties.setName(input.getName());
final AuditStamp auditStamp = new AuditStamp();
Urn actor = UrnUtils.getUrn(context.getActorUrn());
auditStamp.setActor(actor, SetMode.IGNORE_NULL);
auditStamp.setTime(System.currentTimeMillis());
editableDatasetProperties.setLastModified(auditStamp);
persistAspect(
context.getOperationContext(),
targetUrn,
Constants.EDITABLE_DATASET_PROPERTIES_ASPECT_NAME,
editableDatasetProperties,
actor,
_entityService);
}
return true;
} catch (Exception e) {
throw new RuntimeException(
String.format("Failed to perform update against input %s", input), e);
}
}
throw new AuthorizationException(
"Unauthorized to perform this action. Please contact your DataHub administrator.");
}

private Boolean updateDataProductName(
Urn targetUrn, UpdateNameInput input, QueryContext context) {
try {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -222,6 +222,7 @@ private void mapDatasetProperties(
properties.setQualifiedName(gmsProperties.getQualifiedName());
dataset.setProperties(properties);
dataset.setDescription(properties.getDescription());
dataset.setName(properties.getName());
if (gmsProperties.getUri() != null) {
dataset.setUri(gmsProperties.getUri().toString());
}
Expand All @@ -248,6 +249,9 @@ private void mapEditableDatasetProperties(@Nonnull Dataset dataset, @Nonnull Dat
new EditableDatasetProperties(dataMap);
final DatasetEditableProperties editableProperties = new DatasetEditableProperties();
editableProperties.setDescription(editableDatasetProperties.getDescription());
if (editableDatasetProperties.getName() != null) {
editableProperties.setName(editableDatasetProperties.getName());
}
dataset.setEditableProperties(editableProperties);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -111,8 +111,13 @@ public Collection<MetadataChangeProposal> apply(

if (datasetUpdateInput.getEditableProperties() != null) {
final EditableDatasetProperties editableDatasetProperties = new EditableDatasetProperties();
editableDatasetProperties.setDescription(
datasetUpdateInput.getEditableProperties().getDescription());
if (datasetUpdateInput.getEditableProperties().getDescription() != null) {
editableDatasetProperties.setDescription(
datasetUpdateInput.getEditableProperties().getDescription());
}
if (datasetUpdateInput.getEditableProperties().getName() != null) {
editableDatasetProperties.setName(datasetUpdateInput.getEditableProperties().getName());
}
editableDatasetProperties.setLastModified(auditStamp);
editableDatasetProperties.setCreated(auditStamp);
proposals.add(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,40 +15,49 @@ public class EntityTypeMapper {

static final Map<EntityType, String> ENTITY_TYPE_TO_NAME =
ImmutableMap.<EntityType, String>builder()
.put(EntityType.DOMAIN, Constants.DOMAIN_ENTITY_NAME)
.put(EntityType.DATASET, Constants.DATASET_ENTITY_NAME)
.put(EntityType.ROLE, Constants.ROLE_ENTITY_NAME)
.put(EntityType.CORP_USER, Constants.CORP_USER_ENTITY_NAME)
.put(EntityType.CORP_GROUP, Constants.CORP_GROUP_ENTITY_NAME)
.put(EntityType.DATA_PLATFORM, Constants.DATA_PLATFORM_ENTITY_NAME)
.put(EntityType.ER_MODEL_RELATIONSHIP, Constants.ER_MODEL_RELATIONSHIP_ENTITY_NAME)
.put(EntityType.DASHBOARD, Constants.DASHBOARD_ENTITY_NAME)
.put(EntityType.NOTEBOOK, Constants.NOTEBOOK_ENTITY_NAME)
.put(EntityType.CHART, Constants.CHART_ENTITY_NAME)
.put(EntityType.TAG, Constants.TAG_ENTITY_NAME)
.put(EntityType.DATA_FLOW, Constants.DATA_FLOW_ENTITY_NAME)
.put(EntityType.DATA_JOB, Constants.DATA_JOB_ENTITY_NAME)
.put(EntityType.DATA_PROCESS_INSTANCE, Constants.DATA_PROCESS_INSTANCE_ENTITY_NAME)
.put(EntityType.TAG, Constants.TAG_ENTITY_NAME)
.put(EntityType.GLOSSARY_TERM, Constants.GLOSSARY_TERM_ENTITY_NAME)
.put(EntityType.GLOSSARY_NODE, Constants.GLOSSARY_NODE_ENTITY_NAME)
.put(EntityType.CONTAINER, Constants.CONTAINER_ENTITY_NAME)
.put(EntityType.MLMODEL, Constants.ML_MODEL_ENTITY_NAME)
.put(EntityType.MLMODEL_GROUP, Constants.ML_MODEL_GROUP_ENTITY_NAME)
.put(EntityType.MLFEATURE_TABLE, Constants.ML_FEATURE_TABLE_ENTITY_NAME)
.put(EntityType.MLFEATURE, Constants.ML_FEATURE_ENTITY_NAME)
.put(EntityType.MLPRIMARY_KEY, Constants.ML_PRIMARY_KEY_ENTITY_NAME)
.put(EntityType.CONTAINER, Constants.CONTAINER_ENTITY_NAME)
.put(EntityType.DOMAIN, Constants.DOMAIN_ENTITY_NAME)
.put(EntityType.NOTEBOOK, Constants.NOTEBOOK_ENTITY_NAME)
.put(EntityType.INGESTION_SOURCE, Constants.INGESTION_SOURCE_ENTITY_NAME)
.put(EntityType.EXECUTION_REQUEST, Constants.EXECUTION_REQUEST_ENTITY_NAME)
.put(EntityType.ASSERTION, Constants.ASSERTION_ENTITY_NAME)
.put(EntityType.DATA_PROCESS_INSTANCE, Constants.DATA_PROCESS_INSTANCE_ENTITY_NAME)
.put(EntityType.DATA_PLATFORM_INSTANCE, Constants.DATA_PLATFORM_INSTANCE_ENTITY_NAME)
.put(EntityType.ACCESS_TOKEN, Constants.ACCESS_TOKEN_ENTITY_NAME)
.put(EntityType.TEST, Constants.TEST_ENTITY_NAME)
.put(EntityType.ER_MODEL_RELATIONSHIP, Constants.ER_MODEL_RELATIONSHIP_ENTITY_NAME)
.put(EntityType.DATAHUB_POLICY, Constants.POLICY_ENTITY_NAME)
.put(EntityType.DATAHUB_ROLE, Constants.DATAHUB_ROLE_ENTITY_NAME)
.put(EntityType.POST, Constants.POST_ENTITY_NAME)
.put(EntityType.SCHEMA_FIELD, Constants.SCHEMA_FIELD_ENTITY_NAME)
.put(EntityType.DATAHUB_VIEW, Constants.DATAHUB_VIEW_ENTITY_NAME)
.put(EntityType.QUERY, Constants.QUERY_ENTITY_NAME)
.put(EntityType.DATA_PRODUCT, Constants.DATA_PRODUCT_ENTITY_NAME)
.put(EntityType.SCHEMA_FIELD, Constants.SCHEMA_FIELD_ENTITY_NAME)
.put(EntityType.CUSTOM_OWNERSHIP_TYPE, Constants.OWNERSHIP_TYPE_ENTITY_NAME)
.put(EntityType.INCIDENT, Constants.INCIDENT_ENTITY_NAME)
.put(EntityType.ROLE, Constants.ROLE_ENTITY_NAME)
.put(EntityType.STRUCTURED_PROPERTY, Constants.STRUCTURED_PROPERTY_ENTITY_NAME)
.put(EntityType.ASSERTION, Constants.ASSERTION_ENTITY_NAME)
.put(EntityType.FORM, Constants.FORM_ENTITY_NAME)
.put(EntityType.DATA_TYPE, Constants.DATA_TYPE_ENTITY_NAME)
.put(EntityType.ENTITY_TYPE, Constants.ENTITY_TYPE_ENTITY_NAME)
.put(EntityType.RESTRICTED, Constants.RESTRICTED_ENTITY_NAME)
.put(EntityType.BUSINESS_ATTRIBUTE, Constants.BUSINESS_ATTRIBUTE_ENTITY_NAME)
.put(EntityType.QUERY, Constants.QUERY_ENTITY_NAME)
.put(EntityType.POST, Constants.POST_ENTITY_NAME)
.put(EntityType.FORM, Constants.FORM_ENTITY_NAME)
.build();

private static final Map<String, EntityType> ENTITY_NAME_TO_TYPE =
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,34 +20,63 @@ public class EntityTypeUrnMapper {

static final Map<String, String> ENTITY_NAME_TO_ENTITY_TYPE_URN =
ImmutableMap.<String, String>builder()
.put(Constants.DOMAIN_ENTITY_NAME, "urn:li:entityType:datahub.domain")
.put(Constants.DATASET_ENTITY_NAME, "urn:li:entityType:datahub.dataset")
.put(Constants.ROLE_ENTITY_NAME, "urn:li:entityType:datahub.role")
.put(Constants.CORP_USER_ENTITY_NAME, "urn:li:entityType:datahub.corpuser")
.put(Constants.CORP_GROUP_ENTITY_NAME, "urn:li:entityType:datahub.corpGroup")
.put(Constants.DATA_PLATFORM_ENTITY_NAME, "urn:li:entityType:datahub.dataPlatform")
.put(
Constants.ER_MODEL_RELATIONSHIP_ENTITY_NAME,
"urn:li:entityType:datahub.erModelRelationship")
.put(Constants.DASHBOARD_ENTITY_NAME, "urn:li:entityType:datahub.dashboard")
.put(Constants.NOTEBOOK_ENTITY_NAME, "urn:li:entityType:datahub.notebook")
.put(Constants.CHART_ENTITY_NAME, "urn:li:entityType:datahub.chart")
.put(Constants.TAG_ENTITY_NAME, "urn:li:entityType:datahub.tag")
.put(Constants.DATA_FLOW_ENTITY_NAME, "urn:li:entityType:datahub.dataFlow")
.put(Constants.DATA_JOB_ENTITY_NAME, "urn:li:entityType:datahub.dataJob")
.put(Constants.TAG_ENTITY_NAME, "urn:li:entityType:datahub.tag")
.put(Constants.GLOSSARY_TERM_ENTITY_NAME, "urn:li:entityType:datahub.glossaryTerm")
.put(Constants.GLOSSARY_NODE_ENTITY_NAME, "urn:li:entityType:datahub.glossaryNode")
.put(Constants.CONTAINER_ENTITY_NAME, "urn:li:entityType:datahub.container")
.put(Constants.ML_MODEL_ENTITY_NAME, "urn:li:entityType:datahub.mlModel")
.put(Constants.ML_MODEL_GROUP_ENTITY_NAME, "urn:li:entityType:datahub.mlModelGroup")
.put(Constants.ML_FEATURE_TABLE_ENTITY_NAME, "urn:li:entityType:datahub.mlFeatureTable")
.put(Constants.ML_FEATURE_ENTITY_NAME, "urn:li:entityType:datahub.mlFeature")
.put(Constants.ML_PRIMARY_KEY_ENTITY_NAME, "urn:li:entityType:datahub.mlPrimaryKey")
.put(Constants.CONTAINER_ENTITY_NAME, "urn:li:entityType:datahub.container")
.put(Constants.DOMAIN_ENTITY_NAME, "urn:li:entityType:datahub.domain")
.put(Constants.NOTEBOOK_ENTITY_NAME, "urn:li:entityType:datahub.notebook")
.put(
Constants.INGESTION_SOURCE_ENTITY_NAME,
"urn:li:entityType:datahub.dataHubIngestionSource")
.put(
Constants.EXECUTION_REQUEST_ENTITY_NAME,
"urn:li:entityType:datahub.dataHubExecutionRequest")
.put(Constants.ASSERTION_ENTITY_NAME, "urn:li:entityType:datahub.assertion")
.put(
Constants.DATA_PROCESS_INSTANCE_ENTITY_NAME,
"urn:li:entityType:datahub.dataProcessInstance")
.put(
Constants.DATA_PLATFORM_INSTANCE_ENTITY_NAME,
"urn:li:entityType:datahub.dataPlatformInstance")
.put(Constants.ACCESS_TOKEN_ENTITY_NAME, "urn:li:entityType:datahub.dataHubAccessToken")
.put(Constants.TEST_ENTITY_NAME, "urn:li:entityType:datahub.test")
.put(Constants.POLICY_ENTITY_NAME, "urn:li:entityType:datahub.dataHubPolicy")
.put(Constants.DATAHUB_ROLE_ENTITY_NAME, "urn:li:entityType:datahub.dataHubRole")
.put(Constants.POST_ENTITY_NAME, "urn:li:entityType:datahub.post")
.put(Constants.SCHEMA_FIELD_ENTITY_NAME, "urn:li:entityType:datahub.schemaField")
.put(Constants.DATAHUB_VIEW_ENTITY_NAME, "urn:li:entityType:datahub.dataHubView")
.put(Constants.QUERY_ENTITY_NAME, "urn:li:entityType:datahub.query")
.put(Constants.DATA_PRODUCT_ENTITY_NAME, "urn:li:entityType:datahub.dataProduct")
.put(Constants.ASSERTION_ENTITY_NAME, "urn:li:entityType:datahub.assertion")
.put(Constants.SCHEMA_FIELD_ENTITY_NAME, "urn:li:entityType:datahub.schemaField")
.put(Constants.OWNERSHIP_TYPE_ENTITY_NAME, "urn:li:entityType:datahub.ownershipType")
.put(Constants.INCIDENT_ENTITY_NAME, "urn:li:entityType:datahub.incident")
.put(Constants.ROLE_ENTITY_NAME, "urn:li:entityType:datahub.role")
.put(
Constants.STRUCTURED_PROPERTY_ENTITY_NAME,
"urn:li:entityType:datahub.structuredProperty")
.put(Constants.FORM_ENTITY_NAME, "urn:li:entityType:datahub.form")
.put(Constants.DATA_TYPE_ENTITY_NAME, "urn:li:entityType:datahub.dataType")
.put(Constants.ENTITY_TYPE_ENTITY_NAME, "urn:li:entityType:datahub.entityType")
.put(Constants.RESTRICTED_ENTITY_NAME, "urn:li:entityType:datahub.restricted")
.put(
Constants.BUSINESS_ATTRIBUTE_ENTITY_NAME,
"urn:li:entityType:datahub.businessAttribute")
.build();

private static final Map<String, String> ENTITY_TYPE_URN_TO_NAME =
Expand Down
5 changes: 5 additions & 0 deletions datahub-graphql-core/src/main/resources/app.graphql
Original file line number Diff line number Diff line change
Expand Up @@ -508,6 +508,11 @@ type FeatureFlagsConfig {
"""
dataContractsEnabled: Boolean!

"""
Whether dataset names are editable
"""
editableDatasetNameEnabled: Boolean!

"""
If turned on, all siblings will be separated with no way to get to a "combined" sibling view
"""
Expand Down
9 changes: 9 additions & 0 deletions datahub-graphql-core/src/main/resources/entity.graphql
Original file line number Diff line number Diff line change
Expand Up @@ -3482,6 +3482,11 @@ type DatasetEditableProperties {
Description of the Dataset
"""
description: String

"""
Editable name of the Dataset
"""
name: String
}

"""
Expand Down Expand Up @@ -4850,6 +4855,10 @@ input DatasetEditablePropertiesUpdate {
Writable description aka documentation for a Dataset
"""
description: String!
"""
Editable name of the Dataset
"""
name: String
}

"""
Expand Down
7 changes: 4 additions & 3 deletions datahub-web-react/src/app/entity/dataset/DatasetEntity.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -220,6 +220,7 @@ export class DatasetEntity implements Entity<Dataset> {
},
]}
sidebarSections={this.getSidebarSections()}
isNameEditable
/>
);

Expand Down Expand Up @@ -283,7 +284,7 @@ export class DatasetEntity implements Entity<Dataset> {
return (
<Preview
urn={data.urn}
name={data.properties?.name || data.name}
name={data.editableProperties?.name || data.properties?.name || data.name}
origin={data.origin}
subtype={data.subTypes?.typeNames?.[0]}
description={data.editableProperties?.description || data.properties?.description}
Expand Down Expand Up @@ -311,7 +312,7 @@ export class DatasetEntity implements Entity<Dataset> {
return (
<Preview
urn={data.urn}
name={data.properties?.name || data.name}
name={data.editableProperties?.name || data.properties?.name || data.name}
origin={data.origin}
description={data.editableProperties?.description || data.properties?.description}
platformName={
Expand Down Expand Up @@ -361,7 +362,7 @@ export class DatasetEntity implements Entity<Dataset> {
};

displayName = (data: Dataset) => {
return data?.properties?.name || data.name || data.urn;
return data?.editableProperties?.name || data?.properties?.name || data.name || data.urn;
};

platformLogoUrl = (data: Dataset) => {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import { capitalizeFirstLetterOnly } from '../../../../../shared/textUtil';
import { useUserContext } from '../../../../../context/useUserContext';
import { useEntityRegistry } from '../../../../../useEntityRegistry';
import EntityHeaderLoadingSection from './EntityHeaderLoadingSection';
import { useIsEditableDatasetNameEnabled } from '../../../../../useAppConfig';

const TitleWrapper = styled.div`
display: flex;
Expand Down Expand Up @@ -71,6 +72,8 @@ export function getCanEditName(
return true; // TODO: add permissions for data products
case EntityType.BusinessAttribute:
return privileges?.manageBusinessAttributes;
case EntityType.Dataset:
return entityData?.privileges?.canEditProperties;
default:
return false;
}
Expand All @@ -94,8 +97,11 @@ export const EntityHeader = ({ headerDropdownItems, headerActionItems, isNameEdi
const entityName = entityData?.name;
const subType = capitalizeFirstLetterOnly(entityData?.subTypes?.typeNames?.[0]) || undefined;

const isEditableDatasetNameEnabled = useIsEditableDatasetNameEnabled();
const canEditName =
isNameEditable && getCanEditName(entityType, entityData, me?.platformPrivileges as PlatformPrivileges);
isEditableDatasetNameEnabled &&
isNameEditable &&
getCanEditName(entityType, entityData, me?.platformPrivileges as PlatformPrivileges);
const entityRegistry = useEntityRegistry();

return (
Expand All @@ -106,7 +112,7 @@ export const EntityHeader = ({ headerDropdownItems, headerActionItems, isNameEdi
<>
<PlatformContent />
<TitleWrapper>
<EntityName isNameEditable={canEditName} />
<EntityName isNameEditable={canEditName || false} />
{entityData?.deprecation?.deprecated && (
<DeprecationPill
urn={urn}
Expand Down
5 changes: 5 additions & 0 deletions datahub-web-react/src/app/useAppConfig.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,11 @@ export function useIsAppConfigContextLoaded() {
return appConfig.loaded;
}

export function useIsEditableDatasetNameEnabled() {
const appConfig = useAppConfig();
return appConfig.config.featureFlags.editableDatasetNameEnabled;
}

export function useIsShowSeparateSiblingsEnabled() {
const appConfig = useAppConfig();
return appConfig.config.featureFlags.showSeparateSiblings;
Expand Down
Loading

0 comments on commit c2ff037

Please sign in to comment.