@talend/react-faceted-search
Version:
173 lines • 7.54 kB
JavaScript
import { useEffect, useMemo, useState } from 'react';
import PropTypes from 'prop-types';
import { ButtonIcon, ButtonSecondary, Popover } from '@talend/design-system';
import { USAGE_TRACKING_TAGS } from '../../constants';
import { createBadgesDict, filterBadgeDefinitionsWithDictionary, getBadgesFromDict } from '../../dictionary/badge.dictionary';
import { createOperatorsDict, getOperatorsFromDict } from '../../dictionary/operator.dictionary';
import { BADGES_ACTIONS, useFacetedBadges } from '../../hooks/facetedBadges.hook';
import { AddFacetPopover } from '../AddFacetPopover';
import { BadgesGenerator } from '../BadgesGenerator';
import { BadgeFacetedProvider } from '../context/badgeFaceted.context';
import { useFacetedSearchContext } from '../context/facetedSearch.context';
import { badgesFacetedPropTypes, callbacksPropTypes, operatorsPropTypes } from '../facetedSearch.propTypes';
import { QuickSearchInput } from '../QuickSearchInput';
import { DEFAULT_QUICKSEARCH_OPERATOR } from '../QuickSearchInput/QuickSearchInput.component';
import { generateBadge } from '../types/badgeDefinition.type';
import styles from './BasicSearch.module.scss';
import { get, isEqual } from "lodash";
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
const isInCreation = badge => get(badge, 'metadata.isInCreation', true);
const BasicSearch = ({
badgesDefinitions = [],
badgesFaceted,
initialBadges = [],
customBadgesDictionary,
customOperatorsDictionary,
initialFilterValue,
onSubmit,
setBadgesFaceted,
callbacks,
badgesDefinitionsSort,
quickSearchPlaceholder,
quickSearchFacetsFilter,
quickSearchInputProps,
quickSearchTypeaheadProps,
disclosureProps
}) => {
const {
id,
t
} = useFacetedSearchContext();
const operatorsDictionary = useMemo(() => createOperatorsDict(t, customOperatorsDictionary), [t, customOperatorsDictionary]);
const badgesDictionary = useMemo(() => createBadgesDict(customBadgesDictionary), [customBadgesDictionary]);
const badges = useMemo(() => filterBadgeDefinitionsWithDictionary(badgesDictionary, badgesDefinitions), [badgesDictionary, badgesDefinitions]);
const [state, dispatch] = useFacetedBadges(badgesFaceted, setBadgesFaceted);
const quicksearchable = useMemo(() => badgesDefinitions.filter(({
metadata = {}
}) => metadata.isAvailableForQuickSearch), [badgesDefinitions]);
const [badgeState, setBadgeState] = useState(state.badges);
useEffect(() => {
if (!state.badges.some(isInCreation) && !isEqual(badgeState, state.badges)) {
setBadgeState(state.badges);
onSubmit({}, state.badges);
}
}, [state.badges, onSubmit]);
useEffect(() => {
initialBadges.forEach(initial => {
const facet = badges.find(({
properties
}) => properties.attribute === initial.attribute);
const operators = getOperatorsFromDict(operatorsDictionary, get(facet, 'metadata.operators'));
dispatch(BADGES_ACTIONS.addWithValue(generateBadge(operators)(facet), operatorsDictionary[initial.operator], initial.value));
});
// This is intended
// eslint-disable-next-line react-hooks/exhaustive-deps
}, []);
const onClickOverlayRow = (_, badgeDefinition) => {
const operators = getOperatorsFromDict(operatorsDictionary, get(badgeDefinition, 'metadata.operators'));
dispatch(BADGES_ACTIONS.add(generateBadge(operators)(badgeDefinition)));
};
const basicSearchId = `${id}-basic-search`;
const badgeFacetedContextValue = {
state,
dispatch,
onSubmit
};
// removable = undefined means badge can be removed (backward compatible change)
const hasRemovableBadge = state.badges.some(badge => badge.properties.removable !== false);
const quickSearchMinLength = Math.max(quicksearchable.map(quicksearchableItem => {
var _quicksearchableItem$;
return (_quicksearchableItem$ = quicksearchableItem.metadata) === null || _quicksearchableItem$ === void 0 ? void 0 : _quicksearchableItem$.minLength;
})) || 1;
return /*#__PURE__*/_jsxs("div", {
id: basicSearchId,
className: styles['tc-basic-search'],
children: [/*#__PURE__*/_jsx(QuickSearchInput, {
t: t,
className: styles['tc-basic-search-quicksearch'],
facets: quicksearchable,
placeholder: quickSearchPlaceholder,
facetsFilter: quickSearchFacetsFilter,
onSelect: (facet, value) => {
const operators = getOperatorsFromDict(operatorsDictionary, get(facet, 'metadata.operators'));
dispatch(BADGES_ACTIONS.addWithValue(generateBadge(operators)(facet), operators.find(({
name
}) => name === DEFAULT_QUICKSEARCH_OPERATOR) || operators[0], value));
},
inputProps: quickSearchInputProps,
minLength: quickSearchMinLength,
typeaheadProps: quickSearchTypeaheadProps
}), /*#__PURE__*/_jsxs("div", {
className: styles['tc-basic-search-content'],
children: [/*#__PURE__*/_jsx(BadgeFacetedProvider, {
value: badgeFacetedContextValue,
children: /*#__PURE__*/_jsx(BadgesGenerator, {
badges: state.badges,
badgesDictionary: badgesDictionary,
getBadgeFromDict: getBadgesFromDict,
id: basicSearchId,
callbacks: callbacks,
t: t
})
}), badgesDefinitions.length > 0 && /*#__PURE__*/_jsx("div", {
children: /*#__PURE__*/_jsx(Popover, {
position: "bottom",
isFixed: true,
disclosure: /*#__PURE__*/_jsx(ButtonSecondary, {
size: "S",
isDropdown: true,
"data-feature": USAGE_TRACKING_TAGS.BASIC_ADD,
...disclosureProps,
children: t('BASIC_SEARCH_ADD_FILTER', 'Add filter')
}),
children: popover => /*#__PURE__*/_jsx(AddFacetPopover, {
badges: state.badges,
badgesDefinitions: badges,
badgesDefinitionsSort: badgesDefinitionsSort,
id: basicSearchId,
initialFilterValue: initialFilterValue,
onClick: (...args) => {
onClickOverlayRow(...args);
popover === null || popover === void 0 ? void 0 : popover.hide();
},
t: t
})
})
})]
}), hasRemovableBadge && /*#__PURE__*/_jsx("div", {
className: styles['tc-basic-search-clear-content'],
children: /*#__PURE__*/_jsx(ButtonIcon, {
icon: "trash",
size: "S",
"data-feature": USAGE_TRACKING_TAGS.BASIC_CLEAR,
onClick: () => dispatch(BADGES_ACTIONS.deleteAll()),
children: t('FACETED_SEARCH_BASIC_CLEAR', 'Remove all filters')
})
})]
});
};
BasicSearch.propTypes = {
badgesDefinitions: badgesFacetedPropTypes,
badgesDefinitionsSort: PropTypes.func,
badgesFaceted: PropTypes.shape({
badges: badgesFacetedPropTypes
}),
initialBadges: PropTypes.arrayOf(PropTypes.shape({
attribute: PropTypes.string,
value: PropTypes.any,
operator: PropTypes.string
})),
customBadgesDictionary: PropTypes.object,
customOperatorsDictionary: operatorsPropTypes,
initialFilterValue: PropTypes.string,
quickSearchPlaceholder: PropTypes.string,
/* Can be used to filter facets displayed when input changes; (term, facets) => [facets] */
quickSearchFacetsFilter: PropTypes.func,
onSubmit: PropTypes.func.isRequired,
setBadgesFaceted: PropTypes.func,
callbacks: callbacksPropTypes,
quickSearchInputProps: PropTypes.object,
disclosureProps: PropTypes.object
};
export { BasicSearch };
//# sourceMappingURL=BasicSearch.component.js.map