mirror of https://github.com/nocodb/nocodb
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
206 lines
5.6 KiB
206 lines
5.6 KiB
import { createSharedComposable } from '@vueuse/core' |
|
import type { SnapshotType } from 'nocodb-sdk' |
|
import { computed, ref } from 'vue' |
|
import dayjs from 'dayjs' |
|
|
|
export type SnapshotExtendedType = SnapshotType & { |
|
isNew?: boolean |
|
loading?: boolean |
|
error?: boolean |
|
created_display_name?: string |
|
} |
|
|
|
export const useBaseSettings = createSharedComposable(() => { |
|
const { $api, $poller } = useNuxtApp() |
|
|
|
const baseStore = useBase() |
|
const { base } = storeToRefs(baseStore) |
|
|
|
const basesStore = useBases() |
|
|
|
const { loadProjects } = basesStore |
|
|
|
const { navigateToProject } = useGlobal() |
|
|
|
const { refreshCommandPalette } = useCommandPalette() |
|
|
|
const _projectId = inject(ProjectIdInj, undefined) |
|
|
|
const isCreatingSnapshot = ref(false) |
|
|
|
const isRestoringSnapshot = ref(false) |
|
|
|
const baseId = computed(() => _projectId?.value ?? base.value?.id) |
|
|
|
const { basesUser, bases } = storeToRefs(basesStore) |
|
|
|
const baseUsers = computed(() => (baseId.value ? basesUser.value.get(baseId.value) || [] : [])) |
|
|
|
const snapshots = ref<SnapshotExtendedType[]>([] as SnapshotExtendedType[]) |
|
|
|
const updateSnapshot = async (snapshot: SnapshotExtendedType) => { |
|
try { |
|
snapshot.loading = true |
|
await $api.snapshot.update(baseId.value, snapshot.id!, { |
|
title: snapshot.title, |
|
}) |
|
snapshot.loading = false |
|
} catch (error) { |
|
message.error(await extractSdkResponseErrorMsg(error)) |
|
snapshot.loading = false |
|
console.error(error) |
|
} |
|
} |
|
|
|
const deleteSnapshot = async (snapshot: SnapshotExtendedType) => { |
|
if (!baseId.value) return |
|
try { |
|
await $api.snapshot.delete(baseId.value, snapshot.id!) |
|
snapshots.value = snapshots.value.filter((s) => s.id !== snapshot.id) |
|
} catch (error) { |
|
message.error(await extractSdkResponseErrorMsg(error)) |
|
console.error(error) |
|
} |
|
} |
|
|
|
const listSnapshots = async () => { |
|
try { |
|
const response = await $api.snapshot.list(baseId.value) |
|
snapshots.value = response.map((snapshot) => { |
|
const user = baseUsers.value.find((u) => u.id === snapshot.created_by) |
|
return { |
|
...snapshot, |
|
isNew: false, |
|
created_display_name: user?.display_name ?? (user?.email ?? '').split('@')[0], |
|
} |
|
}) |
|
} catch (error) { |
|
message.error(await extractSdkResponseErrorMsg(error)) |
|
console.error(error) |
|
} |
|
} |
|
|
|
const isUnsavedSnapshotsPending = computed(() => snapshots.value.some((s) => s.isNew)) |
|
|
|
const cancelNewSnapshot = () => { |
|
snapshots.value = snapshots.value.filter((s) => !s.isNew) |
|
} |
|
|
|
const createSnapshot = async (snapshot: Partial<SnapshotExtendedType>) => { |
|
if (!baseId.value) return |
|
try { |
|
const response = await $api.snapshot.create(baseId.value, snapshot) |
|
isCreatingSnapshot.value = true |
|
|
|
$poller.subscribe( |
|
{ id: response.id }, |
|
async (data: { |
|
id: string |
|
status?: string |
|
data?: { |
|
error?: { |
|
message: string |
|
} |
|
message?: string |
|
result?: any |
|
} |
|
}) => { |
|
if (data.status !== 'close') { |
|
if (data.status === JobStatus.COMPLETED) { |
|
// Table metadata recreated successfully |
|
message.info('Snapshot created successfully') |
|
await listSnapshots() |
|
isCreatingSnapshot.value = false |
|
} else if (status === JobStatus.FAILED) { |
|
message.error('Failed to create snapshot') |
|
isCreatingSnapshot.value = false |
|
} |
|
} |
|
}, |
|
) |
|
} catch (error) { |
|
message.error(await extractSdkResponseErrorMsg(error)) |
|
|
|
snapshot.error = true |
|
console.error(error) |
|
} |
|
} |
|
|
|
const restoreSnapshot = async (snapshot: SnapshotExtendedType, onRestoreSuccess?: () => void | Promise<void>) => { |
|
if (!baseId.value) return |
|
try { |
|
isRestoringSnapshot.value = true |
|
const response = await $api.snapshot.restore(baseId.value, snapshot.id!) |
|
|
|
$poller.subscribe( |
|
{ id: response.id! }, |
|
async (data: { |
|
id: string |
|
status?: string |
|
data?: { |
|
error?: { |
|
message: string |
|
} |
|
message?: string |
|
result?: any |
|
} |
|
}) => { |
|
if (data.status === JobStatus.COMPLETED) { |
|
await loadProjects('workspace') |
|
|
|
const base = bases.value.get(data.data?.result.id) |
|
|
|
isRestoringSnapshot.value = false |
|
|
|
// open project after snapshot success |
|
if (base) { |
|
await navigateToProject({ |
|
workspaceId: isEeUI ? base.fk_workspace_id : undefined, |
|
baseId: base.id, |
|
type: base.type, |
|
}) |
|
} |
|
message.info('Snapshot restored successfully') |
|
|
|
onRestoreSuccess?.() |
|
|
|
refreshCommandPalette() |
|
} else if (data.status === JobStatus.FAILED) { |
|
message.error('Failed to restore snapshot') |
|
await loadProjects('workspace') |
|
isRestoringSnapshot.value = false |
|
|
|
refreshCommandPalette() |
|
} |
|
}, |
|
) |
|
} catch (error) { |
|
message.error(await extractSdkResponseErrorMsg(error)) |
|
console.error(error) |
|
} |
|
} |
|
|
|
const addNewSnapshot = () => { |
|
snapshots.value = [ |
|
{ |
|
title: dayjs().format('D MMMM YYYY, h:mm A'), |
|
isNew: true, |
|
}, |
|
...snapshots.value, |
|
] |
|
} |
|
|
|
return { |
|
snapshots, |
|
createSnapshot, |
|
listSnapshots, |
|
updateSnapshot, |
|
deleteSnapshot, |
|
isUnsavedSnapshotsPending, |
|
cancelNewSnapshot, |
|
addNewSnapshot, |
|
isCreatingSnapshot, |
|
isRestoringSnapshot, |
|
restoreSnapshot, |
|
} |
|
})
|
|
|