Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature: "notIn" mode for Datatable filters #5460

Merged
merged 4 commits into from
Mar 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 12 additions & 12 deletions components/doc/common/apidoc/index.json
Original file line number Diff line number Diff line change
Expand Up @@ -13665,7 +13665,7 @@
"name": "matchMode",
"optional": false,
"readonly": false,
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"description": "Type of filter match."
}
],
Expand Down Expand Up @@ -16080,7 +16080,7 @@
},
{
"name": "mode",
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notContains\" | \"lt\" | \"lte\" | \"gt\" | \"gte\" | \"between\" | \"dateIs\" | \"dateIsNot\" | \"dateBefore\" | \"dateAfter\"",
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notContains\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\" | \"between\" | \"dateIs\" | \"dateIsNot\" | \"dateBefore\" | \"dateAfter\"",
"description": "Filter match mode"
},
{
Expand Down Expand Up @@ -16461,9 +16461,9 @@
"name": "globalFilterMatchMode",
"optional": true,
"readonly": false,
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"default": "contains",
"description": "Defines filterMatchMode; \"startsWith\", \"contains\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"lt\", \"lte\", \"gt\", \"gte\" and \"custom\"."
"description": "Defines filterMatchMode; \"startsWith\", \"contains\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"notIn\", \"lt\", \"lte\", \"gt\", \"gte\" and \"custom\"."
},
{
"name": "groupRowsBy",
Expand Down Expand Up @@ -18391,7 +18391,7 @@
"name": "matchMode",
"optional": false,
"readonly": false,
"type": "undefined | \"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notContains\" | \"lt\" | \"lte\" | \"gt\" | \"gte\" | \"between\" | \"dateIs\" | \"dateIsNot\" | \"dateBefore\" | \"dateAfter\"",
"type": "undefined | \"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notContains\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\" | \"between\" | \"dateIs\" | \"dateIsNot\" | \"dateBefore\" | \"dateAfter\"",
"description": "Type of filter match."
}
],
Expand Down Expand Up @@ -19361,8 +19361,8 @@
"name": "globalFilterMatchMode",
"optional": true,
"readonly": false,
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"description": "Defines filterMatchMode; \"startsWith\", \"contains\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"lt\", \"lte\", \"gt\", \"gte\" and \"custom\"."
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"description": "Defines filterMatchMode; \"startsWith\", \"contains\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"notIn\", \"lt\", \"lte\", \"gt\", \"gte\" and \"custom\"."
},
{
"name": "groupRowsBy",
Expand Down Expand Up @@ -40089,7 +40089,7 @@
"readonly": false,
"type": "string",
"default": "contains",
"description": "Defines how the items are filtered, valid values are \"contains\" (default) \"startsWith\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"lt\", \"lte\", \"gt\" and \"gte\"."
"description": "Defines how the items are filtered, valid values are \"contains\" (default) \"startsWith\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"notIn\", \"lt\", \"lte\", \"gt\" and \"gte\"."
},
{
"name": "id",
Expand Down Expand Up @@ -51991,7 +51991,7 @@
},
{
"name": "mode",
"type": "undefined | \"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"type": "undefined | \"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"description": "Filter match mode."
}
],
Expand Down Expand Up @@ -52181,9 +52181,9 @@
"name": "globalFilterMatchMode",
"optional": true,
"readonly": false,
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notContains\" | \"lt\" | \"lte\" | \"gt\" | \"gte\" | \"between\" | \"dateIs\" | \"dateIsNot\" | \"dateBefore\" | \"dateAfter\"",
"type": "\"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notContains\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\" | \"between\" | \"dateIs\" | \"dateIsNot\" | \"dateBefore\" | \"dateAfter\"",
"default": "contains",
"description": "Defines filterMatchMode; \"startsWith\", \"contains\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"lt\", \"lte\", \"gt\", \"gte\" and \"custom\"."
"description": "Defines filterMatchMode; \"startsWith\", \"contains\", \"endsWith\", \"equals\", \"notEquals\", \"in\", \"notIn\", \"lt\", \"lte\", \"gt\", \"gte\" and \"custom\"."
},
{
"name": "header",
Expand Down Expand Up @@ -53600,7 +53600,7 @@
"name": "matchMode",
"optional": false,
"readonly": false,
"type": "undefined | \"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"type": "undefined | \"endsWith\" | \"startsWith\" | \"custom\" | \"contains\" | \"in\" | \"equals\" | \"notEquals\" | \"notIn\" | \"lt\" | \"lte\" | \"gt\" | \"gte\"",
"description": "Type of filter match."
}
],
Expand Down
13 changes: 13 additions & 0 deletions components/lib/api/FilterService.js
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,19 @@ export const FilterService = {

return false;
},
notIn(value, filter) {
if (filter === undefined || filter === null || filter.length === 0) {
return true;
}

for (let i = 0; i < filter.length; i++) {
if (ObjectUtils.equals(value, filter[i])) {
return false;
}
}

return true;
},
between(value, filter) {
if (filter == null || filter[0] == null || filter[1] == null) {
return true;
Expand Down
44 changes: 39 additions & 5 deletions components/lib/api/test/FilterService.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,20 +8,20 @@ afterEach(() => {
});

const checkParametersNullOrUndefined = (filterType) => {
it('When value parameter is undefined', () => {
it('When filter parameter is undefined', () => {
expect(filters[filterType]('value', undefined)).toBeTruthy();
});

it('When value parameter is null', () => {
it('When filter parameter is null', () => {
expect(filters[filterType]('value', null)).toBeTruthy();
});

it('When filter parameter is undefined', () => {
it('When value parameter is undefined', () => {
expect(filters[filterType](undefined, 'filter')).toBeFalsy();
});

it('When filter parameter is null', () => {
expect(filters[filterType](undefined, 'filter')).toBeFalsy();
it('When value parameter is null', () => {
expect(filters[filterType](null, 'filter')).toBeFalsy();
});
};

Expand Down Expand Up @@ -141,6 +141,40 @@ describe('FilterService', () => {
});
});

describe('notIn filter test', () => {
it('When filter parameter is undefined', () => {
expect(filters.notIn('value', undefined)).toBeTruthy();
});

it('When filter parameter is null', () => {
expect(filters.notIn('value', null)).toBeTruthy();
});

it('When value parameter is undefined', () => {
expect(filters.notIn(undefined, 'filter')).toBeTruthy();
});

it('When value parameter is null', () => {
expect(filters.notIn(null, 'filter')).toBeTruthy();
});

it('When value parameter equal to any filter word', () => {
jest.spyOn(ObjectUtils, 'removeAccents').mockImplementation((value, filter) => value === filter);

const notInFilter = filters.notIn('e', 'filter');

expect(notInFilter).toBeFalsy();
});

it('When value parameter not equal to any filter word', () => {
jest.spyOn(ObjectUtils, 'removeAccents').mockImplementation((value, filter) => value === filter);

const notInFilter = filters.notIn('d', 'filter');

expect(notInFilter).toBeTruthy();
});
});

describe('between filter test', () => {
checkParametersNullOrUndefined('between');
it('When value has getTime func and smaller than filter[0]', () => {
Expand Down
2 changes: 1 addition & 1 deletion components/lib/column/column.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -682,7 +682,7 @@ interface ColumnFilterMetaData {
/**
* Type of filter match.
*/
matchMode: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom';
matchMode: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom';
}

interface ColumnFilterMetaDataWithConstraint {
Expand Down
10 changes: 5 additions & 5 deletions components/lib/datatable/datatable.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ interface DataTableFilterMetaData {
/**
* Type of filter match.
*/
matchMode: 'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom' | undefined;
matchMode: 'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom' | undefined;
}

/**
Expand Down Expand Up @@ -1165,10 +1165,10 @@ interface DataTableBaseProps<TValue extends DataTableValueArray> extends Omit<Re
*/
globalFilterFields?: string[] | undefined;
/**
* Defines filterMatchMode; "startsWith", "contains", "endsWith", "equals", "notEquals", "in", "lt", "lte", "gt", "gte" and "custom".
* Defines filterMatchMode; "startsWith", "contains", "endsWith", "equals", "notEquals", "in", "notIn", "lt", "lte", "gt", "gte" and "custom".
* @defaultValue contains
*/
globalFilterMatchMode?: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom' | undefined;
globalFilterMatchMode?: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom' | undefined;
/**
* Used for either be grouped by a separate grouping row or using rowspan.
*/
Expand Down Expand Up @@ -1796,7 +1796,7 @@ export declare class DataTable<TValue extends DataTableValueArray> extends React
* Filters the data.
* @param {T} value - The filter value
* @param {string} field - The filter field
* @param {'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom'} mode - Filter match mode
* @param {'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom'} mode - Filter match mode
* @param {number} index - Index of the filter
*/
public filter<T>(
Expand All @@ -1811,7 +1811,7 @@ export declare class DataTable<TValue extends DataTableValueArray> extends React
/**
* Filter match mode.
*/
mode: 'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom',
mode: 'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom',
/**
* Index of the filter.
*/
Expand Down
2 changes: 1 addition & 1 deletion components/lib/picklist/picklist.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -358,7 +358,7 @@ export interface PickListProps {
*/
filterBy?: string | undefined;
/**
* Defines how the items are filtered, valid values are "contains" (default) "startsWith", "endsWith", "equals", "notEquals", "in", "lt", "lte", "gt" and "gte".
* Defines how the items are filtered, valid values are "contains" (default) "startsWith", "endsWith", "equals", "notEquals", "in", "notIn", "lt", "lte", "gt" and "gte".
* @defaultValue contains
*/
filterMatchMode?: string | undefined;
Expand Down
8 changes: 4 additions & 4 deletions components/lib/treetable/treetable.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -396,7 +396,7 @@ interface TreeTableFilterMetaData {
/**
* Type of filter match.
*/
matchMode: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom' | undefined;
matchMode: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom' | undefined;
}

/**
Expand Down Expand Up @@ -676,10 +676,10 @@ export interface TreeTableProps extends Omit<React.DetailedHTMLProps<React.Input
*/
globalFilter?: string | undefined | null;
/**
* Defines filterMatchMode; "startsWith", "contains", "endsWith", "equals", "notEquals", "in", "lt", "lte", "gt", "gte" and "custom".
* Defines filterMatchMode; "startsWith", "contains", "endsWith", "equals", "notEquals", "in", "notIn", "lt", "lte", "gt", "gte" and "custom".
* @defaultValue contains
*/
globalFilterMatchMode?: 'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom' | undefined;
globalFilterMatchMode?: 'startsWith' | 'contains' | 'notContains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'between' | 'dateIs' | 'dateIsNot' | 'dateBefore' | 'dateAfter' | 'custom' | undefined;
/**
* Header content of the table.
*/
Expand Down Expand Up @@ -998,7 +998,7 @@ export declare class TreeTable extends React.Component<TreeTableProps, any> {
/**
* Filter match mode.
*/
mode: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom' | undefined
mode: 'startsWith' | 'contains' | 'endsWith' | 'equals' | 'notEquals' | 'in' | 'notIn' | 'lt' | 'lte' | 'gt' | 'gte' | 'custom' | undefined
): void;
/**
* Used to get container element.
Expand Down
Loading