From 3bd606473a7200a69e41bb9bdb13cd28e6b86756 Mon Sep 17 00:00:00 2001
From: Petr Kachanovsky
Date: Fri, 14 Mar 2025 09:31:05 +0200
Subject: [PATCH 1/2] feat: add support for foreign resource array columns
---
adminforth/modules/configValidator.ts | 4 ++--
adminforth/modules/restApi.ts | 21 ++++++++++++++++---
.../spa/src/components/ValueRenderer.vue | 20 ++++++++++++++++--
dev-demo/resources/apartments.ts | 9 +++++++-
4 files changed, 46 insertions(+), 8 deletions(-)
diff --git a/adminforth/modules/configValidator.ts b/adminforth/modules/configValidator.ts
index 0c5fbbc86..c960ebbdc 100644
--- a/adminforth/modules/configValidator.ts
+++ b/adminforth/modules/configValidator.ts
@@ -515,8 +515,8 @@ export default class ConfigValidator implements IConfigValidator {
if (col.masked) {
errors.push(`Resource "${res.resourceId}" column "${col.name}" isArray cannot be used for a masked column`);
}
- if (col.foreignResource) {
- errors.push(`Resource "${res.resourceId}" column "${col.name}" isArray cannot be used for a foreignResource column`);
+ if (col.foreignResource && col.foreignResource.polymorphicResources) {
+ errors.push(`Resource "${res.resourceId}" column "${col.name}" isArray cannot be used for a polymorphic foreignResource column`);
}
if (!col.type || col.type !== AdminForthDataTypes.JSON) {
diff --git a/adminforth/modules/restApi.ts b/adminforth/modules/restApi.ts
index da4024cac..29d881738 100644
--- a/adminforth/modules/restApi.ts
+++ b/adminforth/modules/restApi.ts
@@ -675,13 +675,22 @@ export default class AdminForthRestAPI implements IAdminForthRestAPI {
const targetResource = this.adminforth.config.resources.find((res) => res.resourceId == col.foreignResource.resourceId);
const targetConnector = this.adminforth.connectors[targetResource.dataSource];
const targetResourcePkField = targetResource.columns.find((col) => col.primaryKey).name;
- const pksUnique = [...new Set(data.data.map((item) => item[col.name]))];
+ const pksUnique = [...new Set(data.data.reduce((pks, item) => {
+ if (col.isArray?.enabled) {
+ if (item[col.name]?.length) {
+ pks = pks.concat(item[col.name]);
+ }
+ } else {
+ pks.push(item[col.name]);
+ }
+ return pks;
+ }, []))];
if (pksUnique.length === 0) {
return;
}
const targetData = await targetConnector.getData({
resource: targetResource,
- limit: limit,
+ limit: pksUnique.length,
offset: 0,
filters: [
{
@@ -755,7 +764,13 @@ export default class AdminForthRestAPI implements IAdminForthRestAPI {
}
data.data.forEach((item) => {
- item[col.name] = targetDataMap[item[col.name]];
+ if (col.isArray?.enabled) {
+ if (item[col.name]?.length) {
+ item[col.name] = item[col.name].map((i) => targetDataMap[i]);
+ }
+ } else {
+ item[col.name] = targetDataMap[item[col.name]];
+ }
if (!item[col.name]) {
if (col.foreignResource && col.foreignResource.polymorphicResources) {
diff --git a/adminforth/spa/src/components/ValueRenderer.vue b/adminforth/spa/src/components/ValueRenderer.vue
index b996f5d73..cb864ef07 100644
--- a/adminforth/spa/src/components/ValueRenderer.vue
+++ b/adminforth/spa/src/components/ValueRenderer.vue
@@ -1,7 +1,23 @@
-
{e.stopPropagation()}" v-if="column.foreignResource">
- {e.stopPropagation()}"
+ >
+
+
+
+
{{ record[column.name].label }}
diff --git a/dev-demo/resources/apartments.ts b/dev-demo/resources/apartments.ts
index ddd0adddf..05b3a1daf 100644
--- a/dev-demo/resources/apartments.ts
+++ b/dev-demo/resources/apartments.ts
@@ -223,9 +223,16 @@ export default {
{
name: "room_sizes",
type: AdminForthDataTypes.JSON,
+ // isArray: {
+ // enabled: true,
+ // itemType: AdminForthDataTypes.FLOAT,
+ // },
isArray: {
enabled: true,
- itemType: AdminForthDataTypes.FLOAT,
+ itemType: AdminForthDataTypes.STRING,
+ },
+ foreignResource: {
+ resourceId: "users",
},
},
{
From cb61d3bed279f850ce0a8ee349f0be4c0d22129c Mon Sep 17 00:00:00 2001
From: Petr Kachanovsky
Date: Mon, 17 Mar 2025 09:01:28 +0200
Subject: [PATCH 2/2] fix: fix foreign resource array display on edit page
---
adminforth/spa/src/views/EditView.vue | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/adminforth/spa/src/views/EditView.vue b/adminforth/spa/src/views/EditView.vue
index afc3bef47..82bfb508e 100644
--- a/adminforth/spa/src/views/EditView.vue
+++ b/adminforth/spa/src/views/EditView.vue
@@ -107,7 +107,11 @@ const editableRecord = computed(() => {
}
coreStore.resource.columns.forEach(column => {
if (column.foreignResource) {
- newRecord[column.name] = newRecord[column.name]?.pk
+ if (column.isArray?.enabled) {
+ newRecord[column.name] = newRecord[column.name]?.map(fr => fr.pk);
+ } else {
+ newRecord[column.name] = newRecord[column.name]?.pk;
+ }
}
});
return newRecord;