feat(ui) - assist filters wip

This commit is contained in:
Shekar Siri 2022-06-15 16:20:35 +02:00
parent 2fe2406d0c
commit aa669d6a86
5 changed files with 70 additions and 64 deletions

View file

@ -4,8 +4,8 @@ import LiveSessionSearch from 'Shared/LiveSessionSearch';
import cn from 'classnames'
import withPageTitle from 'HOCs/withPageTitle';
import withPermissions from 'HOCs/withPermissions'
import SessionSearch from '../shared/SessionSearch';
import MainSearchBar from '../shared/MainSearchBar';
// import SessionSearch from '../shared/SessionSearch';
// import MainSearchBar from '../shared/MainSearchBar';
import AssistSearchField from './AssistSearchField';
function Assist() {
@ -13,11 +13,8 @@ function Assist() {
<div className="page-margin container-90 flex relative">
<div className="flex-1 flex">
<div className={cn("w-full mx-auto")} style={{ maxWidth: '1300px'}}>
{/* <MainSearchBar /> */}
<AssistSearchField />
<LiveSessionSearch />
{/* <SessionSearch /> */}
<div className="my-4" />
<LiveSessionList />
</div>

View file

@ -20,7 +20,7 @@ interface Props {
params?: any;
headerText?: string;
placeholder?: string;
onSelect: (e, item) => void;
onSelect: (e: any, item: any) => void;
value: any;
icon?: string;
}
@ -44,17 +44,17 @@ function FilterAutoComplete(props: Props) {
const [options, setOptions] = useState<any>([]);
const [query, setQuery] = useState(value);
const requestValues = (q) => {
const requestValues = (q: any) => {
setLoading(true);
return new APIClient()[method?.toLocaleLowerCase()](endpoint, { ...params, q })
.then(response => {
.then((response: any) => {
if (response.ok) {
return response.json();
}
throw new Error(response.statusText);
})
.then(({ data }) => {
.then(({ data }: any) => {
setOptions(data);
})
.finally(() => setLoading(false));
@ -62,7 +62,7 @@ function FilterAutoComplete(props: Props) {
const debouncedRequestValues = React.useCallback(debounce(requestValues, 1000), [params]);
const onInputChange = ({ target: { value } }) => {
const onInputChange = ({ target: { value } }: any) => {
setQuery(value);
if (!showModal) {
setShowModal(true);
@ -85,7 +85,7 @@ function FilterAutoComplete(props: Props) {
}
}
const onItemClick = (e, item) => {
const onItemClick = (e: any, item: any) => {
e.stopPropagation();
e.preventDefault();
@ -132,7 +132,7 @@ function FilterAutoComplete(props: Props) {
) : (
<div>
{
options.map((item, i) => (
options.map((item: any, i: any) => (
<div
key={item.value + '_' + i}
className={ cn(stl.filterItem) }

View file

@ -5,10 +5,13 @@ import { FilterKey, FilterCategory, FilterType } from 'Types/filter/filterType';
import FilterValueDropdown from '../FilterValueDropdown';
import FilterDuration from '../FilterDuration';
import { debounce } from 'App/utils';
import { assist as assistRoute, isRoute } from "App/routes";
const ASSIST_ROUTE = assistRoute();
interface Props {
filter: any;
onUpdate: (filter) => void;
onUpdate: (filter: any) => void;
}
function FilterValue(props: Props) {
const { filter } = props;
@ -21,13 +24,13 @@ function FilterValue(props: Props) {
props.onUpdate({ ...filter, value: newValue });
}
const onRemoveValue = (valueIndex) => {
const newValue = filter.value.filter((_, index) => index !== valueIndex);
const onRemoveValue = (valueIndex: any) => {
const newValue = filter.value.filter((_: any, index: any) => index !== valueIndex);
props.onUpdate({ ...filter, value: newValue });
}
const onChange = (e, item, valueIndex) => {
const newValues = filter.value.map((_, _index) => {
const onChange = (e: any, item: any, valueIndex: any) => {
const newValues = filter.value.map((_: any, _index: any) => {
if (_index === valueIndex) {
return item.value;
}
@ -38,11 +41,11 @@ function FilterValue(props: Props) {
const debounceOnSelect = React.useCallback(debounce(onChange, 500), [onChange]);
const onDurationChange = (newValues) => {
const onDurationChange = (newValues: any) => {
setDurationValues({ ...durationValues, ...newValues });
}
const handleBlur = (e) => {
const handleBlur = (e: any) => {
if (filter.type === FilterType.DURATION) {
const { maxDuration, minDuration, key } = filter;
if (maxDuration || minDuration) return;
@ -53,16 +56,22 @@ function FilterValue(props: Props) {
}
}
const getParms = (key) => {
const getParms = (key: any) => {
let params = {};
switch (filter.category) {
case FilterCategory.METADATA:
return { type: FilterKey.METADATA, key: key };
params = { type: FilterKey.METADATA, key: key };
default:
return { type: filter.key };
params = { type: filter.key };
}
if (isRoute(ASSIST_ROUTE, window.location.pathname)) {
params = { ...params, live: true };
}
return params;
}
const renderValueFiled = (value, valueIndex) => {
const renderValueFiled = (value: any, valueIndex: any) => {
const showOrButton = valueIndex === lastIndex && filter.type !== FilterType.NUMBER;
switch(filter.type) {
case FilterType.STRING:
@ -85,7 +94,7 @@ function FilterValue(props: Props) {
filter={filter}
options={filter.options}
onChange={({ value }) => onChange(null, { value }, valueIndex)}
/>
/>
)
case FilterType.ISSUE:
case FilterType.MULTIPLE_DROPDOWN:
@ -174,7 +183,7 @@ function FilterValue(props: Props) {
{ filter.type === FilterType.DURATION ? (
renderValueFiled(filter.value, 0)
) : (
filter.value && filter.value.map((value, valueIndex) => (
filter.value && filter.value.map((value: any, valueIndex: any) => (
<div key={valueIndex}>
{renderValueFiled(value, valueIndex)}
</div>

View file

@ -1,8 +1,8 @@
import React, { useEffect } from 'react';
import { fetchLiveList } from 'Duck/sessions';
import { connect } from 'react-redux';
import { NoContent, Loader, LoadMoreButton, Pagination } from 'UI';
import { List, Map } from 'immutable';
import { NoContent, Loader, Pagination } from 'UI';
import { List } from 'immutable';
import SessionItem from 'Shared/SessionItem';
import withPermissions from 'HOCs/withPermissions'
import { KEYS } from 'Types/filter/customFilter';
@ -23,7 +23,7 @@ interface Props {
fetchLiveList: () => Promise<void>,
applyFilter: () => void,
filters: any,
addAttribute: (obj) => void,
addAttribute: (obj: any) => void,
addFilterByKeyAndValue: (key: FilterKey, value: string) => void,
updateCurrentPage: (page: number) => void,
currentPage: number,
@ -34,16 +34,13 @@ interface Props {
function LiveSessionList(props: Props) {
const { loading, filters, list, currentPage, metaList = [], sort } = props;
var timeoutId;
const hasUserFilter = filters.map(i => i.key).includes(KEYS.USERID);
var timeoutId: any;
const hasUserFilter = filters.map((i: any) => i.key).includes(KEYS.USERID);
const [sessions, setSessions] = React.useState(list);
const sortOptions = metaList.map(i => ({
const sortOptions = metaList.map((i: any) => ({
text: capitalize(i), label: i
})).toJS();
// const displayedCount = Math.min(currentPage * PER_PAGE, sessions.size);
// const addPage = () => props.updateCurrentPage(props.currentPage + 1)
// useEffect(() => {
// if (filters.size === 0) {
// props.addFilterByKeyAndValue(FilterKey.USERID, '');
@ -53,31 +50,31 @@ function LiveSessionList(props: Props) {
useEffect(() => {
if (metaList.size === 0 || !!sort.field) return;
if ( sortOptions[0]) {
if (sortOptions[0]) {
props.updateSort({ field: sortOptions[0].value });
}
}, [metaList]);
useEffect(() => {
const filteredSessions = filters.size > 0 ? props.list.filter(session => {
let hasValidFilter = true;
filters.forEach(filter => {
if (!hasValidFilter) return;
// useEffect(() => {
// const filteredSessions = filters.size > 0 ? props.list.filter(session => {
// let hasValidFilter = true;
// filters.forEach(filter => {
// if (!hasValidFilter) return;
const _values = filter.value.filter(i => i !== '' && i !== null && i !== undefined).map(i => i.toLowerCase());
if (filter.key === FilterKey.USERID) {
const _userId = session.userId ? session.userId.toLowerCase() : '';
hasValidFilter = _values.length > 0 ? (_values.includes(_userId) && hasValidFilter) || _values.some(i => _userId.includes(i)) : hasValidFilter;
}
if (filter.category === FilterCategory.METADATA) {
const _source = session.metadata[filter.key] ? session.metadata[filter.key].toLowerCase() : '';
hasValidFilter = _values.length > 0 ? (_values.includes(_source) && hasValidFilter) || _values.some(i => _source.includes(i)) : hasValidFilter;
}
})
return hasValidFilter;
}) : props.list;
setSessions(filteredSessions);
}, [filters, list]);
// const _values = filter.value.filter(i => i !== '' && i !== null && i !== undefined).map(i => i.toLowerCase());
// if (filter.key === FilterKey.USERID) {
// const _userId = session.userId ? session.userId.toLowerCase() : '';
// hasValidFilter = _values.length > 0 ? (_values.includes(_userId) && hasValidFilter) || _values.some(i => _userId.includes(i)) : hasValidFilter;
// }
// if (filter.category === FilterCategory.METADATA) {
// const _source = session.metadata[filter.key] ? session.metadata[filter.key].toLowerCase() : '';
// hasValidFilter = _values.length > 0 ? (_values.includes(_source) && hasValidFilter) || _values.some(i => _source.includes(i)) : hasValidFilter;
// }
// })
// return hasValidFilter;
// }) : props.list;
// setSessions(filteredSessions);
// }, [filters, list]);
useEffect(() => {
props.fetchLiveList();
@ -95,7 +92,8 @@ function LiveSessionList(props: Props) {
}
}
const onSortChange = (e, { value }) => {
const onSortChange = ({ value }: any) => {
value = value.value
props.updateSort({ field: value });
}
@ -145,9 +143,7 @@ function LiveSessionList(props: Props) {
show={ !loading && sessions && sessions.size === 0}
>
<Loader loading={ loading }>
{sessions && sliceListPerPage(sessions.sortBy(i => i.metadata[sort.field]).update(list => {
return sort.order === 'desc' ? list.reverse() : list;
}), currentPage - 1).map(session => (
{sessions.map(session => (
<SessionItem
key={ session.sessionId }
session={ session }
@ -162,7 +158,7 @@ function LiveSessionList(props: Props) {
<Pagination
page={currentPage}
totalPages={Math.ceil(sessions.size / PER_PAGE)}
onPageChange={(page) => props.updateCurrentPage(page)}
onPageChange={(page: any) => props.updateCurrentPage(page)}
limit={PER_PAGE}
/>
</div>
@ -173,12 +169,12 @@ function LiveSessionList(props: Props) {
}
export default withPermissions(['ASSIST_LIVE'])(connect(
(state) => ({
(state: any) => ({
list: state.getIn(['liveSearch', 'list']),
loading: state.getIn([ 'liveSearch', 'fetchList', 'loading' ]),
filters: state.getIn([ 'liveSearch', 'instance', 'filters' ]),
currentPage: state.getIn(["liveSearch", "currentPage"]),
metaList: state.getIn(['customFields', 'list']).map(i => i.key),
metaList: state.getIn(['customFields', 'list']).map((i: any) => i.key),
sort: state.getIn(['liveSearch', 'sort']),
}),
{

View file

@ -53,14 +53,18 @@ export const filters = [
{ key: FilterKey.FETCH_FAILED, type: FilterType.MULTIPLE, category: FilterCategory.PERFORMANCE, label: 'Failed Request', operator: 'isAny', operatorOptions: filterOptions.stringOperatorsPerformance, icon: 'filters/fetch-failed', isEvent: true },
{ key: FilterKey.ISSUE, type: FilterType.ISSUE, category: FilterCategory.JAVASCRIPT, label: 'Issue', operator: 'is', operatorOptions: filterOptions.getOperatorsByKeys(['is', 'isAny', 'isNot']), icon: 'filters/click', options: filterOptions.issueOptions },
];
export const filtersMap = filters.reduce((acc, filter) => {
acc[filter.key] = filter;
return acc;
}, {});
export const liveFiltersMap = filters.reduce((acc, filter) => {
if (filter.category !== FilterCategory.INTERACTIONS && filter.category !== FilterCategory.JAVASCRIPT) {
if (
filter.category !== FilterCategory.INTERACTIONS &&
filter.category !== FilterCategory.JAVASCRIPT &&
filter.category !== FilterCategory.PERFORMANCE
) {
acc[filter.key] = filter;
}
return acc