Skip to content

Commit ea42603

Browse files
Add IN query to quick filters (#7)
1 parent 669b80f commit ea42603

File tree

4 files changed

+38
-2
lines changed

4 files changed

+38
-2
lines changed

src/components/QueryEditor/FilterEditor/index.tsx

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -130,7 +130,7 @@ export const FilterEditorRow = ({ value, onSubmit }: FilterEditorRowProps) => {
130130
}}
131131
/>
132132
</div>
133-
{!['exists', 'not exists'].includes(value.filter.operator) && (
133+
{['=', '!=', 'term', 'not term'].includes(value.filter.operator) && (
134134
<Input
135135
ref={valueInputRef}
136136
placeholder="Value"
@@ -143,6 +143,19 @@ export const FilterEditorRow = ({ value, onSubmit }: FilterEditorRowProps) => {
143143
}}
144144
/>
145145
)}
146+
{['in', 'not in'].includes(value.filter.operator) && (
147+
<Input
148+
ref={valueInputRef}
149+
placeholder="Space-delimited values"
150+
value={value.filter.value}
151+
onChange={(e) => dispatch(changeFilterValue({ id: value.id, value: e.currentTarget.value }))}
152+
onKeyUp={(e) => {
153+
if (e.key === 'Enter') {
154+
onSubmit();
155+
}
156+
}}
157+
/>
158+
)}
146159
</InlineSegmentGroup>
147160
</>
148161
);

src/datasource/base.ts

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -394,7 +394,10 @@ export class BaseQuickwitDataSource
394394
if (!adhocFilters) {
395395
return query;
396396
}
397-
let finalQuery = query;
397+
398+
// Surround the query with () to ensure that the filters are properly AND'd
399+
let finalQuery = '(' + query + ')';
400+
398401
adhocFilters.forEach((filter) => {
399402
finalQuery = addAddHocFilter(finalQuery, filter);
400403
});

src/modifyQuery.ts

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,24 @@ export function addAddHocFilter(query: string, filter: AdHocVariableFilter): str
5252
case 'not exists':
5353
addHocFilter = `-${key}:*`;
5454
break;
55+
case 'in':
56+
addHocFilter = createAdhocFilterIn(key, value);
57+
break;
58+
case 'not in':
59+
addHocFilter = `(NOT (${createAdhocFilterIn(key, value)}))`;
60+
break;
5561
}
5662
return concatenate(query, addHocFilter);
5763
}
64+
65+
function createAdhocFilterIn(key: string, value: string): string {
66+
const values = value.split(' ');
67+
68+
// OR is faster than IN for smaller number of values
69+
if (values.length < 10) {
70+
const conditions = values.map(v => `${key}:${v}`);
71+
return `(${conditions.join(' OR ')})`;
72+
}
73+
74+
return `${key}:IN [${value}]`;
75+
}

src/queryDef.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,8 @@ export const filterOperations = [
4444
{ label: 'not term', value: 'not term' },
4545
{ label: 'exists', value: 'exists' },
4646
{ label: 'not exists', value: 'not exists' },
47+
{ label: 'in', value: 'in' },
48+
{ label: 'not in', value: 'not in' },
4749
];
4850

4951
export function defaultFilter(id = newFilterId()): QueryFilter {

0 commit comments

Comments
 (0)