(row: DbRow, rule: FilterRule, field: DbField | undefined)
| 33 | // --------------------------------------------------------------------------- |
| 34 | |
| 35 | function matchesRule(row: DbRow, rule: FilterRule, field: DbField | undefined): boolean { |
| 36 | if (!field) return true |
| 37 | const raw = cell(row, field.id) |
| 38 | const v = raw.trim() |
| 39 | const target = (rule.value ?? '').trim() |
| 40 | switch (rule.op) { |
| 41 | case 'is': |
| 42 | if (field.type === 'multiSelect') return splitMultiSelect(raw).includes(target) |
| 43 | return v.toLowerCase() === target.toLowerCase() |
| 44 | case 'isNot': |
| 45 | if (field.type === 'multiSelect') return !splitMultiSelect(raw).includes(target) |
| 46 | return v.toLowerCase() !== target.toLowerCase() |
| 47 | case 'contains': |
| 48 | return v.toLowerCase().includes(target.toLowerCase()) |
| 49 | case 'notContains': |
| 50 | return !v.toLowerCase().includes(target.toLowerCase()) |
| 51 | case 'isEmpty': |
| 52 | return v.length === 0 |
| 53 | case 'isNotEmpty': |
| 54 | return v.length > 0 |
| 55 | case 'gt': |
| 56 | return Number(v) > Number(target) |
| 57 | case 'lt': |
| 58 | return Number(v) < Number(target) |
| 59 | case 'before': |
| 60 | return v.length > 0 && v < target |
| 61 | case 'after': |
| 62 | return v.length > 0 && v > target |
| 63 | case 'checked': |
| 64 | return isCheckboxTrue(raw) |
| 65 | case 'unchecked': |
| 66 | return !isCheckboxTrue(raw) |
| 67 | default: |
| 68 | return true |
| 69 | } |
| 70 | } |
| 71 | |
| 72 | export function filterRows( |
| 73 | rows: DbRow[], |
no test coverage detected