diff --git a/packages/nc-gui/composables/useKanbanViewStore.ts b/packages/nc-gui/composables/useKanbanViewStore.ts index b33ddd4f9c..a75009da56 100644 --- a/packages/nc-gui/composables/useKanbanViewStore.ts +++ b/packages/nc-gui/composables/useKanbanViewStore.ts @@ -21,7 +21,9 @@ import { useSharedView, useSmartsheetStoreOrThrow, useUIPermission, + useGlobal, } from '#imports' +import { AttachmentType, UITypes } from 'nocodb-sdk' type GroupingFieldColOptionsType = SelectOptionType & { collapsed: boolean } @@ -43,6 +45,8 @@ const [useProvideKanbanViewStore, useKanbanViewStore] = useInjectionState( const { $e, $api } = useNuxtApp() + const { appInfo } = useGlobal() + const { sorts, nestedFilters } = useSmartsheetStoreOrThrow() const { sharedView, fetchSharedViewData, fetchSharedViewGroupedData } = useSharedView() @@ -53,6 +57,10 @@ const [useProvideKanbanViewStore, useKanbanViewStore] = useInjectionState( const password = ref(null) + const attachmentColumns = computed(() => + (meta.value?.columns as ColumnType[])?.filter((c) => c.uidt === UITypes.Attachment).map((c) => c.title), + ) + provide(SharedViewPasswordInj, password) // kanban view meta data @@ -102,6 +110,27 @@ const [useProvideKanbanViewStore, useKanbanViewStore] = useInjectionState( rowMeta: {}, })) + async function getAttachmentUrl(item: AttachmentType) { + const path = item?.path + // if path doesn't exist, use `item.url` + if (path) { + // try ${appInfo.value.ncSiteUrl}/${item.path} first + const url = `${appInfo.value.ncSiteUrl}/${item.path}` + try { + const res = await fetch(url) + if (res.ok) { + // use `url` if it is accessible + return Promise.resolve(url) + } + } catch { + // for some cases, `url` is not accessible as expected + // do nothing here + } + } + // if it fails, use the original url + return Promise.resolve(item.url) + } + async function loadKanbanData() { if ((!project?.value?.id || !meta.value?.id || !viewMeta?.value?.id) && !isPublic.value) return @@ -128,9 +157,25 @@ const [useProvideKanbanViewStore, useKanbanViewStore] = useInjectionState( ) } + let records = [] for (const data of res) { const key = data.key - formattedData.value.set(key, formatData(data.value.list)) + // TODO: optimize + for (const record of data.value.list) { + for (const attachmentColumn of attachmentColumns.value) { + const oldAttachment = JSON.parse(record[attachmentColumn!]) + const newAttachment = [] + for (const attachmentObj of oldAttachment) { + newAttachment.push({ + ...attachmentObj, + url: await getAttachmentUrl(attachmentObj), + }) + } + record[attachmentColumn!] = newAttachment + } + records.push(record) + } + formattedData.value.set(key, formatData(records)) countByStack.value.set(key, data.value.pageInfo.totalRows || 0) } }