From 87554f86af9bb6b25682646e5a4a798778ef91da Mon Sep 17 00:00:00 2001 From: Prem Palanisamy Date: Wed, 8 Apr 2026 10:34:39 +0100 Subject: [PATCH] Fix duplicate import and gate overwrite/skip on database selection - Merge duplicate Layout/Typography import in table +page.svelte - Only show overwrite/skip checkboxes in migration wizard when Databases resource is selected --- .../table-[table]/+page.svelte | 64 +++++++++++++++++-- .../migrations/(import)/wizard.svelte | 46 +++++++++++-- 2 files changed, 101 insertions(+), 9 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/+page.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/+page.svelte index 6467241f2a..71ee820686 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/+page.svelte @@ -8,7 +8,7 @@ import { Container } from '$lib/layout'; import { preferences } from '$lib/stores/preferences'; import { canWriteTables, canWriteRows } from '$lib/stores/roles'; - import { Icon, Layout, Divider, Tooltip, Typography, Link } from '@appwrite.io/pink-svelte'; + import { Dialog, Icon, Layout, Divider, Selector, Tooltip, Typography, Link } from '@appwrite.io/pink-svelte'; import type { PageData } from './$types'; import { tableColumns, @@ -44,6 +44,7 @@ import { EmptySheet, EmptySheetCards, type Field } from '$database/(entity)'; import { invalidate } from '$app/navigation'; import { Dependencies } from '$lib/constants'; + import { Empty as SuggestionsEmptySheet, tableColumnSuggestions, @@ -57,6 +58,11 @@ let isRefreshing = false; let showImportCSV = false; + let showImportOptions = false; + let importOverwrite = false; + let importSkip = false; + let pendingFile: Models.File | null = null; + let pendingLocalFile = false; // todo: might need a type fix here. const filterColumns = writable([]); @@ -108,17 +114,30 @@ $: disableButton = canShowSuggestionsSheet; - async function onSelect(file: Models.File, localFile = false) { + function onSelect(file: Models.File, localFile = false) { + pendingFile = file; + pendingLocalFile = localFile; + importOverwrite = false; + importSkip = false; + showImportOptions = true; + } + + async function startImport() { + if (!pendingFile) return; + + showImportOptions = false; $isCsvImportInProgress = true; try { await sdk .forProject(page.params.region, page.params.project) .migrations.createCSVImport({ - bucketId: file.bucketId, - fileId: file.$id, + bucketId: pendingFile.bucketId, + fileId: pendingFile.$id, resourceId: `${page.params.database}:${page.params.table}`, - internalFile: localFile + internalFile: pendingLocalFile, + overwrite: importOverwrite, + skip: importSkip }); addNotification({ @@ -135,6 +154,7 @@ }); } finally { $isCsvImportInProgress = false; + pendingFile = null; } } @@ -424,6 +444,40 @@ }} /> {/if} + + + + Choose how to handle documents that already exist in this table. + + + { + importOverwrite = e.detail; + if (e.detail) importSkip = false; + }} + label="Overwrite existing documents" + description="Documents with matching IDs will be updated with the imported data." /> + { + importSkip = e.detail; + if (e.detail) importOverwrite = false; + }} + label="Skip existing documents" + description="Documents with matching IDs will be silently skipped." /> + + + + + + + + + + { resetImportStores(); }; @@ -46,6 +50,11 @@ try { const resources = migrationFormToResources($formData, $provider.provider); + const importOptions = { + overwrite: importOverwrite, + skip: importSkip + }; + switch ($provider.provider) { case 'appwrite': { await sdk @@ -54,7 +63,8 @@ resources: resources as AppwriteMigrationResource[], endpoint: $provider.endpoint, projectId: $provider.projectID, - apiKey: $provider.apiKey + apiKey: $provider.apiKey, + ...importOptions }); await invalidate(Dependencies.MIGRATIONS); @@ -70,7 +80,8 @@ databaseHost: $provider.host, username: $provider.username || 'postgres', password: $provider.password, - port: $provider.port || 5432 + port: $provider.port || 5432, + ...importOptions }); await invalidate(Dependencies.MIGRATIONS); break; @@ -80,7 +91,8 @@ .forProject(page.params.region, page.params.project) .migrations.createFirebaseMigration({ resources: resources as FirebaseMigrationResource[], - serviceAccount: $provider.serviceAccount + serviceAccount: $provider.serviceAccount, + ...importOptions }); await invalidate(Dependencies.MIGRATIONS); break; @@ -95,7 +107,8 @@ adminSecret: $provider.adminSecret, database: $provider.database || $provider.subdomain, username: $provider.username || 'postgres', - password: $provider.password + password: $provider.password, + ...importOptions }); await invalidate(Dependencies.MIGRATIONS); @@ -196,6 +209,31 @@ projectSdk={sdk.forProject(page.params.region, page.params.project)} /> + + {#if $formData.databases.root} +
+ + { + importOverwrite = e.detail; + if (e.detail) importSkip = false; + }} + label="Overwrite existing documents" + description="Documents with matching IDs will be updated with the imported data." /> + { + importSkip = e.detail; + if (e.detail) importOverwrite = false; + }} + label="Skip existing documents" + description="Documents with matching IDs will be silently skipped." /> + +
+ {/if} {/if}