diff --git a/packages/nc-gui/components/smartsheet/Grid.vue b/packages/nc-gui/components/smartsheet/Grid.vue index d20d4e02a8..bf84c99560 100644 --- a/packages/nc-gui/components/smartsheet/Grid.vue +++ b/packages/nc-gui/components/smartsheet/Grid.vue @@ -717,9 +717,9 @@ const saveOrUpdateRecords = async (args: { metaValue?: TableType; viewMetaValue? index++ /** if new record save row and save the LTAR cells */ if (currentRow.rowMeta.new) { - const syncLTARRefs = rowRefs[index]!.syncLTARRefs + const syncLTARRefs = rowRefs?.[index]?.syncLTARRefs const savedRow = await updateOrSaveRow(currentRow, '', {}, args) - await syncLTARRefs(savedRow, args) + await syncLTARRefs?.(savedRow, args) currentRow.rowMeta.changed = false continue } @@ -740,6 +740,9 @@ const saveOrUpdateRecords = async (args: { metaValue?: TableType; viewMetaValue? } async function reloadViewDataHandler(shouldShowLoading: boolean | void) { + // save any unsaved data before reload + await saveOrUpdateRecords(); + // set value if spinner should be hidden showLoading.value = !!shouldShowLoading await loadData() @@ -755,9 +758,21 @@ async function openNewRecordHandler() { reloadViewDataHook?.on(reloadViewDataHandler) openNewRecordFormHook?.on(openNewRecordHandler) -onBeforeUnmount(() => { +onBeforeUnmount(async () => { /** save/update records before unmounting the component */ - saveOrUpdateRecords() + const viewMetaValue = view.value + const dataValue = data.value + if (viewMetaValue) { + getMeta(viewMetaValue.fk_model_id).then((res) => { + const metaValue = res + if (!metaValue) return + saveOrUpdateRecords({ + metaValue, + viewMetaValue, + data: dataValue, + }) + }) + } // reset hooks reloadViewDataHook?.off(reloadViewDataHandler) diff --git a/packages/nc-gui/composables/useUIPermission/index.ts b/packages/nc-gui/composables/useUIPermission/index.ts index fcac173c89..806b006d02 100644 --- a/packages/nc-gui/composables/useUIPermission/index.ts +++ b/packages/nc-gui/composables/useUIPermission/index.ts @@ -24,14 +24,32 @@ export const useUIPermission = createSharedComposable(() => { const { previewAs } = useGlobal() const { allRoles } = useRoles() - const isUIAllowed = (permission: Permission | string, skipPreviewAs = false) => { + const isUIAllowed = ( + permission: Permission | string, + skipPreviewAs = false, + userRoles?: string | Record | string[], + ) => { if (previewAs.value && !skipPreviewAs) { return hasPermission(previewAs.value, true, permission) } - return Object.entries(allRoles.value).some(([role, hasRole]) => - hasPermission(role as Role | ProjectRole, hasRole, permission), - ) + let roles: Record = {} + + if (!userRoles) { + roles = allRoles.value + } else if (Array.isArray(userRoles) || typeof userRoles === 'string') { + roles = (Array.isArray(userRoles) ? userRoles : userRoles.split(',')) + // filter out any empty-string/null/undefined values + .filter(Boolean) + .reduce>((acc, role) => { + acc[role] = true + return acc + }, {}) + } else if (typeof userRoles === 'object') { + roles = userRoles + } + + return Object.entries(roles).some(([role, hasRole]) => hasPermission(role as Role | ProjectRole, hasRole, permission)) } return { isUIAllowed } diff --git a/packages/nc-gui/composables/useViewData.ts b/packages/nc-gui/composables/useViewData.ts index 0667742671..34bb78db9b 100644 --- a/packages/nc-gui/composables/useViewData.ts +++ b/packages/nc-gui/composables/useViewData.ts @@ -611,6 +611,11 @@ export function useViewData( .map((c) => row.row[c.title!]) .join('___') + const deleted = await deleteRowById(id as string) + if (!deleted) { + return + } + if (!undo) { addUndo({ redo: { @@ -648,11 +653,6 @@ export function useViewData( scope: defineViewScope({ view: viewMeta.value }), }) } - - const deleted = await deleteRowById(id as string) - if (!deleted) { - return - } } formattedData.value.splice(rowIndex, 1) diff --git a/packages/nc-gui/package-lock.json b/packages/nc-gui/package-lock.json index e4e6a11d5c..c988beb40a 100644 --- a/packages/nc-gui/package-lock.json +++ b/packages/nc-gui/package-lock.json @@ -30,7 +30,7 @@ "leaflet.markercluster": "^1.5.3", "locale-codes": "^1.3.1", "monaco-editor": "^0.33.0", - "nocodb-sdk": "0.109.0", + "nocodb-sdk": "file:../nocodb-sdk", "papaparse": "^5.3.2", "pinia": "^2.0.33", "qrcode": "^1.5.1", @@ -111,7 +111,6 @@ }, "../nocodb-sdk": { "version": "0.109.0", - "extraneous": true, "license": "AGPL-3.0-or-later", "dependencies": { "axios": "^0.21.1", @@ -8720,6 +8719,7 @@ "version": "1.15.1", "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.1.tgz", "integrity": "sha512-yLAMQs+k0b2m7cVxpS1VKJVvoz7SS9Td1zss3XRwXj+ZDH00RJgnuLx7E44wx02kQLrdM3aOOy+FpzS7+8OizA==", + "devOptional": true, "funding": [ { "type": "individual", @@ -12238,21 +12238,8 @@ } }, "node_modules/nocodb-sdk": { - "version": "0.109.0", - "resolved": "https://registry.npmjs.org/nocodb-sdk/-/nocodb-sdk-0.109.0.tgz", - "integrity": "sha512-5yKLiiDR0noHdhyOqqdF/+UWyTqU7em6QZouURRQSxC72qHU1KBrL1ig5JaIL0CX0pwlANq9hnQ0OzSH8J46fQ==", - "dependencies": { - "axios": "^0.21.1", - "jsep": "^1.3.6" - } - }, - "node_modules/nocodb-sdk/node_modules/axios": { - "version": "0.21.4", - "resolved": "https://registry.npmjs.org/axios/-/axios-0.21.4.tgz", - "integrity": "sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg==", - "dependencies": { - "follow-redirects": "^1.14.0" - } + "resolved": "../nocodb-sdk", + "link": true }, "node_modules/node-abi": { "version": "3.23.0", @@ -24729,7 +24716,8 @@ "follow-redirects": { "version": "1.15.1", "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.1.tgz", - "integrity": "sha512-yLAMQs+k0b2m7cVxpS1VKJVvoz7SS9Td1zss3XRwXj+ZDH00RJgnuLx7E44wx02kQLrdM3aOOy+FpzS7+8OizA==" + "integrity": "sha512-yLAMQs+k0b2m7cVxpS1VKJVvoz7SS9Td1zss3XRwXj+ZDH00RJgnuLx7E44wx02kQLrdM3aOOy+FpzS7+8OizA==", + "devOptional": true }, "form-data": { "version": "4.0.0", @@ -27279,22 +27267,22 @@ } }, "nocodb-sdk": { - "version": "0.109.0", - "resolved": "https://registry.npmjs.org/nocodb-sdk/-/nocodb-sdk-0.109.0.tgz", - "integrity": "sha512-5yKLiiDR0noHdhyOqqdF/+UWyTqU7em6QZouURRQSxC72qHU1KBrL1ig5JaIL0CX0pwlANq9hnQ0OzSH8J46fQ==", + "version": "file:../nocodb-sdk", "requires": { + "@typescript-eslint/eslint-plugin": "^4.0.1", + "@typescript-eslint/parser": "^4.0.1", "axios": "^0.21.1", - "jsep": "^1.3.6" - }, - "dependencies": { - "axios": { - "version": "0.21.4", - "resolved": "https://registry.npmjs.org/axios/-/axios-0.21.4.tgz", - "integrity": "sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg==", - "requires": { - "follow-redirects": "^1.14.0" - } - } + "cspell": "^4.1.0", + "eslint": "^7.8.0", + "eslint-config-prettier": "^6.11.0", + "eslint-plugin-eslint-comments": "^3.2.0", + "eslint-plugin-functional": "^3.0.2", + "eslint-plugin-import": "^2.22.0", + "eslint-plugin-prettier": "^4.0.0", + "jsep": "^1.3.6", + "npm-run-all": "^4.1.5", + "prettier": "^2.1.1", + "typescript": "^4.0.2" } }, "node-abi": { diff --git a/packages/nc-gui/package.json b/packages/nc-gui/package.json index 6f922a8b68..44f0905daf 100644 --- a/packages/nc-gui/package.json +++ b/packages/nc-gui/package.json @@ -54,7 +54,7 @@ "leaflet.markercluster": "^1.5.3", "locale-codes": "^1.3.1", "monaco-editor": "^0.33.0", - "nocodb-sdk": "0.109.0", + "nocodb-sdk": "file:../nocodb-sdk", "papaparse": "^5.3.2", "pinia": "^2.0.33", "qrcode": "^1.5.1", diff --git a/packages/nc-gui/pages/index/index/index.vue b/packages/nc-gui/pages/index/index/index.vue index 8aeedb8bc6..4a3b8789c2 100644 --- a/packages/nc-gui/pages/index/index/index.vue +++ b/packages/nc-gui/pages/index/index/index.vue @@ -247,9 +247,9 @@ const copyProjectMeta = async () => {