diff --git a/wherehows-web/app/components/dataset-compliance-field-tag.ts b/wherehows-web/app/components/dataset-compliance-field-tag.ts index 9b3aa66189..d8e018ae33 100644 --- a/wherehows-web/app/components/dataset-compliance-field-tag.ts +++ b/wherehows-web/app/components/dataset-compliance-field-tag.ts @@ -10,6 +10,8 @@ import { } from 'wherehows-web/typings/app/dataset-compliance'; import { IComplianceDataType } from 'wherehows-web/typings/api/list/compliance-datatypes'; import { action } from 'ember-decorators/object'; +import { IComplianceEntity } from 'wherehows-web/typings/api/datasets/compliance'; +import { arrayFilter } from 'wherehows-web/utils/array'; /** * Constant definition for an unselected field format @@ -21,6 +23,16 @@ const unSelectedFieldFormatValue: IDropDownOption = { isDisabled: true }; +/** + * Creates a filter function that excludes options that are already included in other field tags + * @param {IComplianceEntity.identifierType} currentTagId + * @return {(fieldIdTypeTags: Array) => ({ value }: IComplianceFieldIdentifierOption) => boolean} + */ +const resolvedOptionsFilterFn = (currentTagId: IComplianceEntity['identifierType']) => ( + fieldIdTypeTags: Array +) => ({ value }: IComplianceFieldIdentifierOption): boolean => + !fieldIdTypeTags.includes(value) || value === currentTagId; + export default class DatasetComplianceFieldTag extends Component { tagName = 'tr'; @@ -54,6 +66,13 @@ export default class DatasetComplianceFieldTag extends Component { */ parentHasSingleTag: boolean; + /** + * List of identifierTypes for the parent field + * @type {Array} + * @memberof DatasetComplianceFieldTag + */ + fieldIdentifiers: Array; + /** * Reference to the compliance data types * @type {Array} @@ -67,25 +86,28 @@ export default class DatasetComplianceFieldTag extends Component { complianceFieldIdDropdownOptions: Array; /** - * Build the dropdown options available for this tag by filtering out options that are not applicable /available for this tag + * Build the drop down options available for this tag by filtering out options that are not applicable /available for this tag * @type {ComputedProperty>} * @memberof DatasetComplianceFieldTag */ - fieldIdDropDownOptions = computed('hasSingleTag', function( + fieldIdDropDownOptions = computed('hasSingleTag', 'fieldIdentifiers', function( this: DatasetComplianceFieldTag ): Array { - const { parentHasSingleTag, complianceFieldIdDropdownOptions: dropDownOptions } = getProperties(this, [ - 'parentHasSingleTag', - 'complianceFieldIdDropdownOptions' - ]); + const { parentHasSingleTag, fieldIdentifiers, complianceFieldIdDropdownOptions: allOptions, tag } = getProperties( + this, + ['parentHasSingleTag', 'fieldIdentifiers', 'complianceFieldIdDropdownOptions', 'tag'] + ); - // if the parent field does not have a single tag, then no field can be tagged as ComplianceFieldIdValue.None if (!parentHasSingleTag) { - const NoneOption = dropDownOptions.findBy('value', ComplianceFieldIdValue.None); - return dropDownOptions.without(NoneOption!); + const thisTagIdentifierType = get(tag, 'identifierType'); + const noneOption = allOptions.findBy('value', ComplianceFieldIdValue.None); + // if the parent field does not have a single tag, then no field can be tagged as ComplianceFieldIdValue.None + const options = allOptions.without(noneOption!); + + return arrayFilter(resolvedOptionsFilterFn(thisTagIdentifierType)(fieldIdentifiers))(options); } - return dropDownOptions; + return allOptions; }); /** diff --git a/wherehows-web/app/components/dataset-compliance-rollup-row.ts b/wherehows-web/app/components/dataset-compliance-rollup-row.ts index bf88f8350e..be0aac25d0 100644 --- a/wherehows-web/app/components/dataset-compliance-rollup-row.ts +++ b/wherehows-web/app/components/dataset-compliance-rollup-row.ts @@ -1,5 +1,5 @@ import Component from '@ember/component'; -import ComputedProperty, { alias, equal, bool } from '@ember/object/computed'; +import ComputedProperty, { alias, equal, bool, mapBy } from '@ember/object/computed'; import { get, set, getWithDefault, getProperties, computed } from '@ember/object'; import { action } from 'ember-decorators/object'; import { @@ -14,12 +14,15 @@ import { SuggestionIntent, fieldTagsRequiringReview, tagsHaveNoneAndNotNoneType, - tagsHaveNoneType + tagsHaveNoneType, + suggestedIdentifierTypesInList } from 'wherehows-web/constants'; import { getTagSuggestions } from 'wherehows-web/utils/datasets/compliance-suggestions'; import { IColumnFieldProps } from 'wherehows-web/typings/app/dataset-columns'; import { fieldTagsHaveIdentifierType } from 'wherehows-web/constants/dataset-compliance'; import { IComplianceDataType } from 'wherehows-web/typings/api/list/compliance-datatypes'; +import { arrayReduce } from 'wherehows-web/utils/array'; +import { IComplianceEntity } from 'wherehows-web/typings/api/datasets/compliance'; export default class DatasetComplianceRollupRow extends Component.extend({ tagName: '' @@ -199,23 +202,28 @@ export default class DatasetComplianceRollupRow extends Component.extend({ } }); + /** + * Lists the ComplianceFieldIdValue values this field is currently tagged with + * @type {ComputedProperty>} + * @memberof DatasetComplianceRollupRow + */ + taggedIdentifiers: ComputedProperty> = mapBy( + 'fieldChangeSet', + 'identifierType' + ); + /** * Lists the identifierTypes that are suggested values but are currently in the fields tags * @type {ComputedProperty>} * @memberof DatasetComplianceRollupRow * TODO: multi valued suggestions */ - suggestedValuesInChangeSet = computed('fieldChangeSet.@each.identifierType', 'suggestion', function( + suggestedValuesInChangeSet = computed('taggedIdentifiers', 'suggestion', function( this: DatasetComplianceRollupRow - ): Array { - const { fieldChangeSet, suggestion } = getProperties(this, ['fieldChangeSet', 'suggestion']); - return fieldChangeSet.mapBy('identifierType').reduce((list, identifierType) => { - if (suggestion && suggestion.identifierType === identifierType) { - return [...list, identifierType]; - } + ): Array { + const { taggedIdentifiers, suggestion } = getProperties(this, ['taggedIdentifiers', 'suggestion']); - return list; - }, []); + return arrayReduce(suggestedIdentifierTypesInList(suggestion), [])(taggedIdentifiers); }); /** diff --git a/wherehows-web/app/constants/dataset-compliance.ts b/wherehows-web/app/constants/dataset-compliance.ts index f9bcb2bda8..f04cf6de89 100644 --- a/wherehows-web/app/constants/dataset-compliance.ts +++ b/wherehows-web/app/constants/dataset-compliance.ts @@ -12,7 +12,8 @@ import { IIdentifierFieldWithFieldChangeSetObject, ISchemaFieldsToPolicy, ISchemaFieldsToSuggested, - IComplianceEntityWithMetadata + IComplianceEntityWithMetadata, + ISuggestedFieldTypeValues } from 'wherehows-web/typings/app/dataset-compliance'; import { IColumnFieldProps, @@ -162,6 +163,17 @@ const isRecentSuggestion = ( (!!suggestionModificationTime && suggestionModificationTime - parseInt(policyModificationTime) >= lastSeenSuggestionInterval); +/** + * Takes a suggestion and populates a list of ComplianceFieldIdValues if the suggestion matches the identifier + * @param {ISuggestedFieldTypeValues | void} suggestion + * @return {(list: Array, identifierType: ComplianceFieldIdValue) => Array} + */ +const suggestedIdentifierTypesInList = (suggestion: ISuggestedFieldTypeValues | void) => ( + list: Array, + identifierType: IComplianceEntity['identifierType'] +): Array => + suggestion && suggestion.identifierType === identifierType ? [...list, identifierType] : list; + /** * Checks if a compliance policy changeSet field requires user attention: if a suggestion * is available but the user has not indicated intent or a policy for the field does not currently exist remotely @@ -494,6 +506,7 @@ const sortFoldedChangeSetTuples = ( }; export { + suggestedIdentifierTypesInList, compliancePolicyStrings, getFieldIdentifierOption, getFieldIdentifierOptions, diff --git a/wherehows-web/app/templates/components/dataset-compliance-rollup-row.hbs b/wherehows-web/app/templates/components/dataset-compliance-rollup-row.hbs index 0e26a03053..02108d13b4 100644 --- a/wherehows-web/app/templates/components/dataset-compliance-rollup-row.hbs +++ b/wherehows-web/app/templates/components/dataset-compliance-rollup-row.hbs @@ -11,6 +11,7 @@ suggestion=suggestion isReadonly=isReadonlyField hasSingleTag=hasSingleTag + taggedIdentifiers=taggedIdentifiers isReviewRequested=isReviewRequested suggestionResolution=suggestionResolution suggestionMatchesCurrentValue=suggestionMatchesCurrentValue diff --git a/wherehows-web/app/templates/datasets/dataset-compliance/-dataset-compliance-entities.hbs b/wherehows-web/app/templates/datasets/dataset-compliance/-dataset-compliance-entities.hbs index a3c2cf3f7b..cba2bece3d 100644 --- a/wherehows-web/app/templates/datasets/dataset-compliance/-dataset-compliance-entities.hbs +++ b/wherehows-web/app/templates/datasets/dataset-compliance/-dataset-compliance-entities.hbs @@ -240,6 +240,7 @@ class="dataset-compliance-fields__tag-row" tag=tag parentHasSingleTag=row.hasSingleTag + fieldIdentifiers=row.taggedIdentifiers onTagIdentifierTypeChange=(action "tagIdentifierChanged") onTagLogicalTypeChange=(action "tagLogicalTypeChanged") onTagOwnerChange=(action "tagOwnerChanged")