From 8694b8d772d0d6ac855a2167080400bc16dda3fb Mon Sep 17 00:00:00 2001
From: melohagan <101575380+melohagan@users.noreply.github.com>
Date: Tue, 5 Mar 2024 09:03:19 +0000
Subject: [PATCH] Relationship picker incorrectly renders selections (#13175)
* Ensure _id is decoded for external search
* Fetch initial value for 'Update' type forms
* test didn't run locally - might run on github workflow
* Tested and appears to be as before
* Null-pointer fix
* undo type change
* update modules
* add test
* update modules
---
.../app/forms/RelationshipField.svelte | 27 +++-
.../src/sdk/app/rows/search/external.ts | 18 ++-
.../app/rows/search/tests/external.spec.ts | 115 ++++++++++--------
.../server/src/sdk/app/rows/search/utils.ts | 1 -
4 files changed, 102 insertions(+), 59 deletions(-)
diff --git a/packages/client/src/components/app/forms/RelationshipField.svelte b/packages/client/src/components/app/forms/RelationshipField.svelte
index 7cd571f6d9..1fbd0df522 100644
--- a/packages/client/src/components/app/forms/RelationshipField.svelte
+++ b/packages/client/src/components/app/forms/RelationshipField.svelte
@@ -1,7 +1,7 @@
{
+ const ids = breakRowIdField(row)
+ return ids[0]
+ })
+ }
+
try {
const table = await sdk.tables.getTable(tableId)
options = searchInputMapping(table, options)
@@ -119,9 +131,7 @@ export async function exportRows(
requestQuery = {
oneOf: {
_id: rowIds.map((row: string) => {
- const ids = JSON.parse(
- decodeURI(row).replace(/'/g, `"`).replace(/%2C/g, ",")
- )
+ const ids = breakRowIdField(row)
if (ids.length > 1) {
throw new HTTPError(
"Export data does not support composite keys.",
diff --git a/packages/server/src/sdk/app/rows/search/tests/external.spec.ts b/packages/server/src/sdk/app/rows/search/tests/external.spec.ts
index 1aaea8e258..bae84592ca 100644
--- a/packages/server/src/sdk/app/rows/search/tests/external.spec.ts
+++ b/packages/server/src/sdk/app/rows/search/tests/external.spec.ts
@@ -21,10 +21,11 @@ jest.unmock("mysql2/promise")
jest.setTimeout(30000)
-describe.skip("external", () => {
+describe("external search", () => {
const config = new TestConfiguration()
let externalDatasource: Datasource, tableData: Table
+ const rows: Row[] = []
beforeAll(async () => {
const container = await new GenericContainer("mysql")
@@ -89,67 +90,81 @@ describe.skip("external", () => {
},
},
}
+
+ const table = await config.createExternalTable({
+ ...tableData,
+ sourceId: externalDatasource._id,
+ })
+ for (let i = 0; i < 10; i++) {
+ rows.push(
+ await config.createRow({
+ tableId: table._id,
+ name: generator.first(),
+ surname: generator.last(),
+ age: generator.age(),
+ address: generator.address(),
+ })
+ )
+ }
})
- describe("search", () => {
- const rows: Row[] = []
- beforeAll(async () => {
- const table = await config.createExternalTable({
- ...tableData,
- sourceId: externalDatasource._id,
- })
- for (let i = 0; i < 10; i++) {
- rows.push(
- await config.createRow({
- tableId: table._id,
- name: generator.first(),
- surname: generator.last(),
- age: generator.age(),
- address: generator.address(),
- })
- )
+ it("default search returns all the data", async () => {
+ await config.doInContext(config.appId, async () => {
+ const tableId = config.table!._id!
+
+ const searchParams: SearchParams = {
+ tableId,
+ query: {},
}
+ const result = await search(searchParams)
+
+ expect(result.rows).toHaveLength(10)
+ expect(result.rows).toEqual(
+ expect.arrayContaining(rows.map(r => expect.objectContaining(r)))
+ )
})
+ })
- it("default search returns all the data", async () => {
- await config.doInContext(config.appId, async () => {
- const tableId = config.table!._id!
+ it("querying by fields will always return data attribute columns", async () => {
+ await config.doInContext(config.appId, async () => {
+ const tableId = config.table!._id!
- const searchParams: SearchParams = {
- tableId,
- query: {},
- }
- const result = await search(searchParams)
+ const searchParams: SearchParams = {
+ tableId,
+ query: {},
+ fields: ["name", "age"],
+ }
+ const result = await search(searchParams)
- expect(result.rows).toHaveLength(10)
- expect(result.rows).toEqual(
- expect.arrayContaining(rows.map(r => expect.objectContaining(r)))
+ expect(result.rows).toHaveLength(10)
+ expect(result.rows).toEqual(
+ expect.arrayContaining(
+ rows.map(r => ({
+ ...expectAnyExternalColsAttributes,
+ name: r.name,
+ age: r.age,
+ }))
)
- })
+ )
})
+ })
- it("querying by fields will always return data attribute columns", async () => {
- await config.doInContext(config.appId, async () => {
- const tableId = config.table!._id!
+ it("will decode _id in oneOf query", async () => {
+ await config.doInContext(config.appId, async () => {
+ const tableId = config.table!._id!
- const searchParams: SearchParams = {
- tableId,
- query: {},
- fields: ["name", "age"],
- }
- const result = await search(searchParams)
+ const searchParams: SearchParams = {
+ tableId,
+ query: {
+ oneOf: {
+ _id: ["%5B1%5D", "%5B4%5D", "%5B8%5D"],
+ },
+ },
+ }
+ const result = await search(searchParams)
- expect(result.rows).toHaveLength(10)
- expect(result.rows).toEqual(
- expect.arrayContaining(
- rows.map(r => ({
- ...expectAnyExternalColsAttributes,
- name: r.name,
- age: r.age,
- }))
- )
- )
- })
+ expect(result.rows).toHaveLength(3)
+ expect(result.rows.map(row => row.id)).toEqual([1, 4, 8])
})
})
})
diff --git a/packages/server/src/sdk/app/rows/search/utils.ts b/packages/server/src/sdk/app/rows/search/utils.ts
index 4eee3cea41..5d93dcaca2 100644
--- a/packages/server/src/sdk/app/rows/search/utils.ts
+++ b/packages/server/src/sdk/app/rows/search/utils.ts
@@ -1,6 +1,5 @@
import {
FieldType,
- FieldTypeSubtypes,
SearchParams,
Table,
DocumentType,