What this is about
A filter has three parts:
{ "key": "amount", "value": "10", "param": "SAMEORAFTER" }
| Part | Meaning |
|---|---|
key | the field, also across relations like company.companyname, see Filtering and sorting across relations |
value | the value to compare with, always as text, also for numbers and dates |
param | the operator: how the comparison works. If it is missing, LIKE applies |
Operators are written in upper case. "eq" is not a valid operator.
The operators
| Operator | reads as | SQL (simplified) | Example |
|---|---|---|---|
EQ | equal | = | { "key": "city", "value": "Köln", "param": "EQ" } |
NEQ | not equal | <> | { "key": "status", "value": "CLOSED", "param": "NEQ" } |
LIKE | matches pattern | LIKE | { "key": "name", "value": "Muster%", "param": "LIKE" } |
IN | one of | IN (…) | { "key": "amount", "value": "5,10,15", "param": "IN" } |
ISNULL | has no value | IS NULL | { "key": "note", "param": "ISNULL" } |
ISNOTNULL | has a value | IS NOT NULL | { "key": "note", "param": "ISNOTNULL" } |
BEFORE | less than, before | < | { "key": "dueOn", "value": "2026-02-01", "param": "BEFORE" } |
SAMEORBEFORE | less than or equal | <= | { "key": "amount", "value": "10", "param": "SAMEORBEFORE" } |
AFTER | greater than, after | > | { "key": "amount", "value": "10", "param": "AFTER" } |
SAMEORAFTER | greater than or equal | >= | { "key": "dueOn", "value": "2026-02-01", "param": "SAMEORAFTER" } |
MEMBEROF | list contains | EXISTS (…) | { "key": "employees", "value": "7f3…", "param": "MEMBEROF" } |
BEFORE, AFTER and their SAMEOR… variants are named after time, but they work the same way for numbers.
Which operator for which field?
| Text | Integer | Decimal number | Yes/No | Date, time | ID | Enum | List | Operator |
|---|---|---|---|---|---|---|---|---|
| yes | yes | yes | yes | yes | yes | yes | – | EQ, NEQ |
| yes | no | no | no | no | no | no | – | LIKE |
| yes | yes | yes | yes | yes | yes | yes | – | IN |
| no | yes | yes | no | yes | no | no | – | BEFORE, AFTER, SAMEORBEFORE, SAMEORAFTER |
| yes | yes | yes | yes | yes | yes | yes | – | ISNULL, ISNOTNULL |
| – | – | – | – | – | – | – | yes | MEMBEROF |
“Integer” means fields of type Integer and Long, “Decimal number” means fields of type Double, Float and Decimal. “ID” means the id of an object and paths like company.id. ISNULL and ISNOTNULL also work on a single reference: { "key": "company", "param": "ISNULL" } finds all employees without a company.
How the value is written
| Field type | How to write value | Example |
|---|---|---|
| Text | as it is | "Köln" |
| Integer | digits | "10" |
| Decimal number | with a dot | "2.5" |
| Yes/No | "true" or "false" (upper/lower case does not matter) | "true", "false" |
| Date, time | fixed format | "2026-02-10", "2026-02-10 08:00:00", see Date and time values |
| ID | UUID | "7f3a…-…" |
| Enum | name of the value | "OPEN" |
IN | values separated by commas, without spaces | "5,10,15" |
ISNULL, ISNOTNULL | no value needed | – |
All operators in action
When: exactly one value, or everything except one value
{ "key": "amount", "value": "10", "param": "EQ" } finds all with amount 10. NEQ finds all others, but not the ones without a value: in SQL an empty field is neither equal nor not equal.
Result: Exact comparison.
When: text search with placeholders
CDMS does not add any %. Everything about it is under Search patterns with LIKE: % and _.
Result: Only for text fields.
When: one of several values
{ "key": "label", "value": "Alpha,Beta", "param": "IN" }. The values are split at the comma, spaces are part of the value: "Alpha, Beta" searches for “Alpha” and “ Beta” (with a space).
Result: Matches whose value is in the list.
When: number and date ranges
For a range you combine two filters in an AND group, e.g. SAMEORAFTER 2026-01-01 and BEFORE 2026-02-01 for “in January”.
Result: Values in this range.
When: field empty or filled
value is not needed. { "key": "note", "param": "ISNULL" } finds all without a note.
Result: Empty means null in the database. An empty text "" is not null.
When: “which companies have this employee?”
Only for list fields. Separate page: Searching collections with MEMBEROF.
Result: Objects whose list contains the value.
When operator and field do not fit together
| Case | Example | Result |
|---|---|---|
| comparison on text or yes/no | label BEFORE Beta | 400 unsupported-operator|label|BEFORE |
| unknown field | lable EQ Beta | 400 unknown-search-key|lable |
| unknown enum value with EQ/NEQ | type EQ BOSS | 400 wrong-value-in-where|type|BOSS |
| yes/no with another word | active EQ yes | 400 wrong-value-in-where|active|yes |
| LIKE on a number | amount LIKE 1% | 400 like-needs-text|amount |
| value does not fit the type | amount EQ abc | 400 wrong-value-in-where|amount|abc |
| MEMBEROF on a non-list | label MEMBEROF x | 400 memberof-needs-collection|label |
| operator unknown or in lower case | "param": "eq" | 400 invalid-value|parameter.query.filter[0].param |
All error cases together are under When a filter does not fit.