From 34432d586277f5af647f56f8add2739e73d5600c Mon Sep 17 00:00:00 2001 From: mike12345567 Date: Thu, 28 Jul 2022 13:39:11 +0100 Subject: [PATCH] Fixing some issues with automations + lucene filtering (with string templating on the backend) as well as type coercion in the query rows action. --- packages/frontend-core/src/utils/lucene.js | 5 +++- .../server/src/automations/steps/queryRows.js | 23 ++++++++++++++++++- 2 files changed, 26 insertions(+), 2 deletions(-) diff --git a/packages/frontend-core/src/utils/lucene.js b/packages/frontend-core/src/utils/lucene.js index 1001ec26a8..9554c2201a 100644 --- a/packages/frontend-core/src/utils/lucene.js +++ b/packages/frontend-core/src/utils/lucene.js @@ -1,6 +1,8 @@ import { Helpers } from "@budibase/bbui" import { OperatorOptions, SqlNumberTypeRangeMap } from "../constants" +const HBS_REGEX = /{{([^{].*?)}}/g + /** * Returns the valid operator options for a certain data type * @param type the data type @@ -98,6 +100,7 @@ export const buildLuceneQuery = filter => { if (Array.isArray(filter)) { filter.forEach(expression => { let { operator, field, type, value, externalType } = expression + const isHbs = typeof value === "string" && value.match(HBS_REGEX)?.length > 0 // Parse all values into correct types if (type === "datetime" && value) { value = new Date(value).toISOString() @@ -105,7 +108,7 @@ export const buildLuceneQuery = filter => { if (type === "number" && !Array.isArray(value)) { if (operator === "oneOf") { value = value.split(",").map(item => parseFloat(item)) - } else { + } else if (!isHbs) { value = parseFloat(value) } } diff --git a/packages/server/src/automations/steps/queryRows.js b/packages/server/src/automations/steps/queryRows.js index b6d1938995..58e7313dd2 100644 --- a/packages/server/src/automations/steps/queryRows.js +++ b/packages/server/src/automations/steps/queryRows.js @@ -82,6 +82,27 @@ async function getTable(appId, tableId) { return ctx.body } +function typeCoercion(filters, table) { + if (!filters || !table) { + return filters + } + for (let key of Object.keys(filters)) { + if (typeof filters[key] === "object") { + for (let [property, value] of Object.entries(filters[key])) { + const column = table.schema[property] + // convert string inputs + if (!column || typeof value !== "string") { + continue + } + if (column.type === FieldTypes.NUMBER) { + filters[key][property] = parseFloat(value) + } + } + } + } + return filters +} + exports.run = async function ({ inputs, appId }) { const { tableId, filters, sortColumn, sortOrder, limit } = inputs const table = await getTable(appId, tableId) @@ -99,7 +120,7 @@ exports.run = async function ({ inputs, appId }) { sortType, limit, sort: sortColumn, - query: filters || {}, + query: typeCoercion(filters || {}, table), // default to ascending, like data tab sortOrder: sortOrder || SortOrders.ASCENDING, },