Merge pull request #3104 from Budibase/view-not-set
Handle nulls / empty in views and tables
This commit is contained in:
commit
547bb8ba80
|
@ -42,6 +42,14 @@
|
|||
name: "Contains",
|
||||
key: "CONTAINS",
|
||||
},
|
||||
{
|
||||
name: "Is Not Empty",
|
||||
key: "NOT_EMPTY",
|
||||
},
|
||||
{
|
||||
name: "Is Empty",
|
||||
key: "EMPTY",
|
||||
},
|
||||
]
|
||||
|
||||
const CONJUNCTIONS = [
|
||||
|
@ -112,6 +120,10 @@
|
|||
|
||||
const getOptionLabel = x => x.name
|
||||
const getOptionValue = x => x.key
|
||||
|
||||
const showValue = filter => {
|
||||
return !(filter.condition === "EMPTY" || filter.condition === "NOT_EMPTY")
|
||||
}
|
||||
</script>
|
||||
|
||||
<ModalContent title="Filter" confirmText="Save" onConfirm={saveView} size="L">
|
||||
|
@ -140,30 +152,36 @@
|
|||
{getOptionLabel}
|
||||
{getOptionValue}
|
||||
/>
|
||||
{#if filter.key && isMultipleChoice(filter.key)}
|
||||
<Select
|
||||
bind:value={filter.value}
|
||||
options={fieldOptions(filter.key)}
|
||||
getOptionLabel={x => x.toString()}
|
||||
/>
|
||||
{:else if filter.key && isDate(filter.key)}
|
||||
<DatePicker
|
||||
bind:value={filter.value}
|
||||
placeholder={filter.key || fields[0]}
|
||||
/>
|
||||
{:else if filter.key && isNumber(filter.key)}
|
||||
<Input
|
||||
bind:value={filter.value}
|
||||
placeholder={filter.key || fields[0]}
|
||||
type="number"
|
||||
/>
|
||||
{#if showValue(filter)}
|
||||
{#if filter.key && isMultipleChoice(filter.key)}
|
||||
<Select
|
||||
bind:value={filter.value}
|
||||
options={fieldOptions(filter.key)}
|
||||
getOptionLabel={x => x.toString()}
|
||||
/>
|
||||
{:else if filter.key && isDate(filter.key)}
|
||||
<DatePicker
|
||||
bind:value={filter.value}
|
||||
placeholder={filter.key || fields[0]}
|
||||
/>
|
||||
{:else if filter.key && isNumber(filter.key)}
|
||||
<Input
|
||||
bind:value={filter.value}
|
||||
placeholder={filter.key || fields[0]}
|
||||
type="number"
|
||||
/>
|
||||
{:else}
|
||||
<Input
|
||||
placeholder={filter.key || fields[0]}
|
||||
bind:value={filter.value}
|
||||
/>
|
||||
{/if}
|
||||
<Icon hoverable name="Close" on:click={() => removeFilter(idx)} />
|
||||
{:else}
|
||||
<Input
|
||||
placeholder={filter.key || fields[0]}
|
||||
bind:value={filter.value}
|
||||
/>
|
||||
<Icon hoverable name="Close" on:click={() => removeFilter(idx)} />
|
||||
<!-- empty div to preserve spacing -->
|
||||
<div />
|
||||
{/if}
|
||||
<Icon hoverable name="Close" on:click={() => removeFilter(idx)} />
|
||||
{/each}
|
||||
</div>
|
||||
{:else}
|
||||
|
|
|
@ -10,6 +10,15 @@ const TOKEN_MAP = {
|
|||
OR: "||",
|
||||
}
|
||||
|
||||
const isEmptyExpression = key => {
|
||||
return `(
|
||||
doc["${key}"] === undefined ||
|
||||
doc["${key}"] === null ||
|
||||
doc["${key}"] === "" ||
|
||||
(Array.isArray(doc["${key}"]) && doc["${key}"].length === 0)
|
||||
)`
|
||||
}
|
||||
|
||||
const GROUP_PROPERTY = {
|
||||
group: {
|
||||
type: "string",
|
||||
|
@ -72,6 +81,10 @@ function parseFilterExpression(filters) {
|
|||
expression.push(
|
||||
`doc["${filter.key}"].${TOKEN_MAP[filter.condition]}("${filter.value}")`
|
||||
)
|
||||
} else if (filter.condition === "EMPTY") {
|
||||
expression.push(isEmptyExpression(filter.key))
|
||||
} else if (filter.condition === "NOT_EMPTY") {
|
||||
expression.push(`!${isEmptyExpression(filter.key)}`)
|
||||
} else {
|
||||
const value =
|
||||
typeof filter.value == "string" ? `"${filter.value}"` : filter.value
|
||||
|
|
Loading…
Reference in New Issue