From f182f7d83ea6c7d735ee44086f4973ee3ce11566 Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Sun, 4 Jan 2026 18:25:20 +0530 Subject: [PATCH 01/45] responsiveness for add records screen --- .../domains/domain-[domain]/+page.svelte | 100 +++++++++++++----- 1 file changed, 72 insertions(+), 28 deletions(-) diff --git a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte index d6ce25571..37c3eb109 100644 --- a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte +++ b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte @@ -13,9 +13,16 @@ } from '@appwrite.io/pink-svelte'; import DomainMetrics from './domainMetrics.svelte'; import { base } from '$app/paths'; + import { isSmallViewport } from '$lib/stores/viewport'; import { app } from '$lib/stores/app'; import { Button } from '$lib/elements/forms'; - import { IconDownload, IconPlus, IconUpload } from '@appwrite.io/pink-icons-svelte'; + import { + IconDownload, + IconPlus, + IconUpload, + IconAdjustments + } from '@appwrite.io/pink-icons-svelte'; + import DisplaySettingsModal from '$lib/layout/displaySettingsModal.svelte'; import { ViewSelector } from '$lib/components'; import { View } from '$lib/helpers/load'; import { columns, presets } from './store'; @@ -33,6 +40,7 @@ let showCreate = false; let showPresetModal = false; let showImportModal = false; + let showDisplaySettingsModal = false; let selectedPreset = ''; async function downloadRecords() { @@ -70,8 +78,8 @@ {#if data.recordList.total} - - +
+
- - - {#each presets as preset} - { - toggle(e); - selectedPreset = preset; - showPresetModal = true; - }}>{preset} - {/each} - - - - - - - +
+ + + + + {#each presets as preset} + { + toggle(e); + selectedPreset = preset; + showPresetModal = true; + }}>{preset} + {/each} + + + +
+ +
+ {#if $isSmallViewport} + + {:else} + + {/if} +
+ +
+
+ +
+
+ {:else} {/if} + +{#if showDisplaySettingsModal} + +{/if} + + From ff37a87fd00f9cc8c60d9ac312ba15053801774f Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Sun, 4 Jan 2026 18:33:22 +0530 Subject: [PATCH 02/45] few fixes --- .../domains/domain-[domain]/+page.svelte | 82 +++++++++++++------ 1 file changed, 59 insertions(+), 23 deletions(-) diff --git a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte index 37c3eb109..c3e65b537 100644 --- a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte +++ b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte @@ -78,8 +78,18 @@ {#if data.recordList.total} -
-
+ + + + + {#each presets as preset} + { + toggle(e); + selectedPreset = preset; + showPresetModal = true; + }}>{preset} + {/each} + + + +
+ {/if} + + + {#if $isSmallViewport} + + {:else} + + {/if} + + {#if !$isSmallViewport} - + {#each presets as preset} @@ -107,30 +154,19 @@ -
- -
- {#if $isSmallViewport} - - {:else} - {/if} -
+ +
-
-
+
+
From 394cb0679916cd960d4f222f91a2e09028783b13 Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Sun, 4 Jan 2026 18:45:33 +0530 Subject: [PATCH 03/45] final design --- .../domains/domain-[domain]/+page.svelte | 112 +++++++++++------- 1 file changed, 66 insertions(+), 46 deletions(-) diff --git a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte index c3e65b537..2494116ba 100644 --- a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte +++ b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte @@ -78,32 +78,12 @@ {#if data.recordList.total} - - - - - - - - Export as .txt - - {#if $isSmallViewport} + {#if $isSmallViewport} + +
- @@ -119,14 +99,22 @@
- {/if} - - - {#if $isSmallViewport} + + + + + + Export as .txt + - {:else} +
+ +
+ {:else} + + + + + + + + Export as .txt + + + - {/if} - {#if !$isSmallViewport} @@ -154,19 +177,16 @@ - {/if} -
- -
+
+ +
+
-
+ {/if}
From d7b51679538a5cb86fa9a93505360a62e59fe66c Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Tue, 6 Jan 2026 12:54:29 +0530 Subject: [PATCH 04/45] use stack --- .../domains/domain-[domain]/+page.svelte | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte index 2494116ba..f9c04af1f 100644 --- a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte +++ b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte @@ -80,7 +80,7 @@ {#if data.recordList.total} {#if $isSmallViewport} -
+
-
+
- +
{:else} {/if} - - diff --git a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/table.svelte b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/table.svelte index ab71bb13d..32494fbb4 100644 --- a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/table.svelte +++ b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/table.svelte @@ -50,7 +50,10 @@ - + {#each $columns as { id, title } (id)} diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte index 571542d06..4514cd368 100644 --- a/src/routes/+layout.svelte +++ b/src/routes/+layout.svelte @@ -309,4 +309,11 @@ background-color: var(--color-mid-neutral-70, #56565c); } } + + .responsive-table { + overflow: hidden; + width: 100%; + scrollbar-width: thin; + position: relative; + } From 01a7cdc9267464db2841726f79bd50f71cc7daf9 Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Tue, 6 Jan 2026 15:27:04 +0530 Subject: [PATCH 06/45] pink version bump --- package.json | 6 ++++-- pnpm-lock.yaml | 39 +++++++++++++++++++++++++++++---------- 2 files changed, 33 insertions(+), 12 deletions(-) diff --git a/package.json b/package.json index 6ab1ae55d..120ca71ca 100644 --- a/package.json +++ b/package.json @@ -24,9 +24,9 @@ "@ai-sdk/svelte": "^1.1.24", "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f", "@appwrite.io/pink-icons": "0.25.0", - "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cb016bd", + "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920", "@appwrite.io/pink-legacy": "^1.0.3", - "@appwrite.io/pink-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cb016bd", + "@appwrite.io/pink-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920", "@faker-js/faker": "^9.9.0", "@popperjs/core": "^2.11.8", "@sentry/sveltekit": "^8.38.0", @@ -40,9 +40,11 @@ "deep-equal": "^2.2.3", "echarts": "^5.6.0", "ignore": "^6.0.2", + "install": "^0.13.0", "nanoid": "^5.1.5", "nanotar": "^0.1.1", "plausible-tracker": "^0.3.9", + "pnpm": "^10.27.0", "pretty-bytes": "^6.1.1", "prismjs": "^1.30.0", "remarkable": "^2.0.1", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index baa5c2e8c..40ef93c38 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -18,14 +18,14 @@ importers: specifier: 0.25.0 version: 0.25.0 '@appwrite.io/pink-icons-svelte': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cb016bd - version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cb016bd(svelte@5.25.3) + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920 + version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920(svelte@5.25.3) '@appwrite.io/pink-legacy': specifier: ^1.0.3 version: 1.0.3 '@appwrite.io/pink-svelte': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cb016bd - version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cb016bd(svelte@5.25.3) + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920 + version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920(svelte@5.25.3) '@faker-js/faker': specifier: ^9.9.0 version: 9.9.0 @@ -65,6 +65,9 @@ importers: ignore: specifier: ^6.0.2 version: 6.0.2 + install: + specifier: ^0.13.0 + version: 0.13.0 nanoid: specifier: ^5.1.5 version: 5.1.5 @@ -74,6 +77,9 @@ importers: plausible-tracker: specifier: ^0.3.9 version: 0.3.9 + pnpm: + specifier: ^10.27.0 + version: 10.27.0 pretty-bytes: specifier: ^6.1.1 version: 6.1.1 @@ -281,8 +287,8 @@ packages: peerDependencies: svelte: ^4.0.0 - '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cb016bd': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cb016bd} + '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920} version: 2.0.0-RC.1 peerDependencies: svelte: ^4.0.0 @@ -296,8 +302,8 @@ packages: '@appwrite.io/pink-legacy@1.0.3': resolution: {integrity: sha512-GGde5fmPhs+s6/3aFeMPc/kKADG/gTFkYQSy6oBN8pK0y0XNCLrZZgBv+EBbdhwdtqVEWXa0X85Mv9w7jcIlwQ==} - '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cb016bd': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cb016bd} + '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920} version: 2.0.0-RC.2 peerDependencies: svelte: ^4.0.0 @@ -2470,6 +2476,10 @@ packages: resolution: {integrity: sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==} engines: {node: '>=8'} + install@0.13.0: + resolution: {integrity: sha512-zDml/jzr2PKU9I8J/xyZBQn8rPCAY//UOYNmR01XwNwyfhEWObo2SWfSl1+0tm1u6PhxLwDnfsT/6jB7OUxqFA==} + engines: {node: '>= 0.10'} + internal-slot@1.1.0: resolution: {integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==} engines: {node: '>= 0.4'} @@ -2914,6 +2924,11 @@ packages: engines: {node: '>=18'} hasBin: true + pnpm@10.27.0: + resolution: {integrity: sha512-ctaZ2haxF5wUup5k3HHJpAmIy9xlwmTLDkidt96RfyDc9NZNhyNiXylpulLUt+KhFwaC2awqXcrqq3MrfhbwSg==} + engines: {node: '>=18.12'} + hasBin: true + popmotion@11.0.5: resolution: {integrity: sha512-la8gPM1WYeFznb/JqF4GiTkRRPZsfaj2+kCxqQgr2MJylMmIKUwBfWW8Wa5fml/8gmtlD5yI01MP1QCZPWmppA==} @@ -3829,7 +3844,7 @@ snapshots: dependencies: svelte: 5.25.3 - '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cb016bd(svelte@5.25.3)': + '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920(svelte@5.25.3)': dependencies: svelte: 5.25.3 @@ -3842,7 +3857,7 @@ snapshots: '@appwrite.io/pink-icons': 1.0.0 the-new-css-reset: 1.11.3 - '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cb016bd(svelte@5.25.3)': + '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920(svelte@5.25.3)': dependencies: '@appwrite.io/pink-icons-svelte': 2.0.0-RC.1(svelte@5.25.3) '@floating-ui/dom': 1.6.13 @@ -6272,6 +6287,8 @@ snapshots: indent-string@4.0.0: {} + install@0.13.0: {} + internal-slot@1.1.0: dependencies: es-errors: 1.3.0 @@ -6685,6 +6702,8 @@ snapshots: optionalDependencies: fsevents: 2.3.2 + pnpm@10.27.0: {} + popmotion@11.0.5: dependencies: framesync: 6.1.2 From bb769727f92f5ec401f9efeb62bfccd1f7138a60 Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Tue, 6 Jan 2026 15:45:17 +0530 Subject: [PATCH 07/45] use base css --- src/lib/profiles/css/base.css | 6 ++++++ src/routes/+layout.svelte | 8 +------- 2 files changed, 7 insertions(+), 7 deletions(-) create mode 100644 src/lib/profiles/css/base.css diff --git a/src/lib/profiles/css/base.css b/src/lib/profiles/css/base.css new file mode 100644 index 000000000..ae0218c27 --- /dev/null +++ b/src/lib/profiles/css/base.css @@ -0,0 +1,6 @@ +.responsive-table { + overflow: hidden; + width: 100%; + scrollbar-width: thin; + position: relative; +} diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte index 4514cd368..c1d724892 100644 --- a/src/routes/+layout.svelte +++ b/src/routes/+layout.svelte @@ -17,6 +17,7 @@ import { ThemeDark, ThemeLight, ThemeDarkCloud, ThemeLightCloud } from '../themes'; import { isSmallViewport, updateViewport } from '$lib/stores/viewport'; import { feedback } from '$lib/stores/feedback'; + import '$lib/profiles/css/base.css'; function resolveTheme(theme: AppStore['themeInUse']) { switch (theme) { @@ -309,11 +310,4 @@ background-color: var(--color-mid-neutral-70, #56565c); } } - - .responsive-table { - overflow: hidden; - width: 100%; - scrollbar-width: thin; - position: relative; - } From 6003039f1df1df6cf78a1946bbb919fea70c22aa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Tue, 6 Jan 2026 15:05:30 +0100 Subject: [PATCH 08/45] Project labels UI --- package.json | 2 +- pnpm-lock.yaml | 12 +- src/lib/actions/analytics.ts | 1 + .../organization-[organization]/+page.ts | 29 +++-- .../settings/+page.svelte | 4 +- .../settings/updateLabels.svelte | 103 ++++++++++++++++++ 6 files changed, 131 insertions(+), 20 deletions(-) create mode 100644 src/routes/(console)/project-[region]-[project]/settings/updateLabels.svelte diff --git a/package.json b/package.json index a2e1778fe..f460aa71a 100644 --- a/package.json +++ b/package.json @@ -22,7 +22,7 @@ }, "dependencies": { "@ai-sdk/svelte": "^1.1.24", - "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f", + "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56", "@appwrite.io/pink-icons": "0.25.0", "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc", "@appwrite.io/pink-legacy": "^1.0.3", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 9a968c01e..057668c3a 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -12,8 +12,8 @@ importers: specifier: ^1.1.24 version: 1.1.24(svelte@5.25.3)(zod@3.24.3) '@appwrite.io/console': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f - version: https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56 + version: https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56 '@appwrite.io/pink-icons': specifier: 0.25.0 version: 0.25.0 @@ -272,9 +272,9 @@ packages: '@analytics/type-utils@0.6.2': resolution: {integrity: sha512-TD+xbmsBLyYy/IxFimW/YL/9L2IEnM7/EoV9Aeh56U64Ify8o27HJcKjo38XY9Tcn0uOq1AX3thkKgvtWvwFQg==} - '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f} - version: 1.10.0 + '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56} + version: 2.1.0 '@appwrite.io/pink-icons-svelte@2.0.0-RC.1': resolution: {integrity: sha512-iLFlV55hj8mGuAbmxJGenxN5RaZMmVT4GJb9dv/MP1xBAtYibFq7JvBcxm18qV2KU8c31Rntf+Ub4GL7HwqTYg==} @@ -3823,7 +3823,7 @@ snapshots: '@analytics/type-utils@0.6.2': {} - '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f': {} + '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56': {} '@appwrite.io/pink-icons-svelte@2.0.0-RC.1(svelte@5.25.3)': dependencies: diff --git a/src/lib/actions/analytics.ts b/src/lib/actions/analytics.ts index dea8860b5..d5ceb1c3e 100644 --- a/src/lib/actions/analytics.ts +++ b/src/lib/actions/analytics.ts @@ -247,6 +247,7 @@ export enum Submit { ProjectDelete = 'submit_project_delete', ProjectUpdateName = 'submit_project_update_name', ProjectUpdateTeam = 'submit_project_update_team', + ProjectUpdateLabels = 'submit_project_update_labels', ProjectService = 'submit_project_service', ProjectUpdateSMTP = 'submit_project_update_smtp', MemberCreate = 'submit_member_create', diff --git a/src/routes/(console)/organization-[organization]/+page.ts b/src/routes/(console)/organization-[organization]/+page.ts index b236341d9..a0e3ccc3c 100644 --- a/src/routes/(console)/organization-[organization]/+page.ts +++ b/src/routes/(console)/organization-[organization]/+page.ts @@ -23,6 +23,11 @@ export const load: PageLoad = async ({ params, url, route, depends, parent }) => const archivedPage = Number.isFinite(archivedPageRaw) && archivedPageRaw > 0 ? archivedPageRaw : 1; const archivedOffset = pageToOffset(archivedPage, limit); + + const searchQueries = search + ? [Query.or([Query.search('search', search), Query.contains('labels', search)])] + : []; + const [activeProjects, archivedProjects, activeTotal, archivedTotal] = await Promise.all([ sdk.forConsole.projects.list({ queries: [ @@ -30,9 +35,9 @@ export const load: PageLoad = async ({ params, url, route, depends, parent }) => Query.equal('teamId', params.organization), Query.or([Query.equal('status', 'active'), Query.isNull('status')]), Query.limit(limit), - Query.orderDesc('') - ], - search: search || undefined + Query.orderDesc(''), + ...searchQueries + ] }), sdk.forConsole.projects.list({ queries: [ @@ -40,23 +45,23 @@ export const load: PageLoad = async ({ params, url, route, depends, parent }) => Query.equal('teamId', params.organization), Query.equal('status', 'archived'), Query.limit(limit), - Query.orderDesc('') - ], - search: search || undefined + Query.orderDesc(''), + ...searchQueries + ] }), sdk.forConsole.projects.list({ queries: [ Query.equal('teamId', params.organization), - Query.or([Query.equal('status', 'active'), Query.isNull('status')]) - ], - search: search || undefined + Query.or([Query.equal('status', 'active'), Query.isNull('status')]), + ...searchQueries + ] }), sdk.forConsole.projects.list({ queries: [ Query.equal('teamId', params.organization), - Query.equal('status', 'archived') - ], - search: search || undefined + Query.equal('status', 'archived'), + ...searchQueries + ] }) ]); diff --git a/src/routes/(console)/project-[region]-[project]/settings/+page.svelte b/src/routes/(console)/project-[region]-[project]/settings/+page.svelte index edf09b92f..8c427cc23 100644 --- a/src/routes/(console)/project-[region]-[project]/settings/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/settings/+page.svelte @@ -15,6 +15,7 @@ import ChangeOrganization from './changeOrganization.svelte'; import UpdateVariables from '../updateVariables.svelte'; import { page } from '$app/state'; + import UpdateLabels from './updateLabels.svelte'; export let data; @@ -84,8 +85,9 @@ {#if $project} - {#if $canWriteProjects} + + + import { onMount } from 'svelte'; + import { invalidate } from '$app/navigation'; + import { Submit, trackEvent, trackError } from '$lib/actions/analytics'; + import { CardGrid } from '$lib/components'; + import { Dependencies } from '$lib/constants'; + import { Button, Form, InputTags } from '$lib/elements/forms'; + import { symmetricDifference } from '$lib/helpers/array'; + import { addNotification } from '$lib/stores/notifications'; + import { sdk } from '$lib/stores/sdk'; + import { project } from '../store'; + import { Tag, Input, Layout, Icon } from '@appwrite.io/pink-svelte'; + import { IconPlus } from '@appwrite.io/pink-icons-svelte'; + + const alphaNumericRegExp = /^[a-zA-Z0-9]+$/; + let suggestedLabels = ['live', 'stage', 'internal']; + let labels: string[] = []; + let error = ''; + + onMount(async () => { + labels = [...$project.labels]; + }); + + async function updateLabels() { + try { + await sdk.forConsole.projects.updateLabels({ projectId: $project.$id, labels }); + await invalidate(Dependencies.PROJECT); + await invalidate(Dependencies.ORGANIZATION); + isDisabled = true; + addNotification({ + type: 'success', + message: 'Project labels have been updated' + }); + trackEvent(Submit.ProjectUpdateLabels); + } catch (error) { + addNotification({ + message: error.message, + type: 'error' + }); + trackError(error, Submit.ProjectUpdateLabels); + } + } + + $: isDisabled = !!error || !symmetricDifference(labels, $project.labels).length; + + $: if (labels) { + const invalidLabels = []; + + labels.forEach((label) => { + if (!alphaNumericRegExp.test(label)) { + invalidLabels.push(label); + } + }); + + if (invalidLabels.length) { + error = `Invalid labels: ${invalidLabels.join(', ')}`; + } else { + error = ''; + } + } + + +
+ + Labels + Categorize and manage your projects for easy searching based on specific criteria by assigning + them customizable labels. + + + {#key labels.length} + + {/key} + + {#each suggestedLabels as suggestedLabel} + { + if (!labels.includes(suggestedLabel)) { + labels = [...labels, suggestedLabel]; + } else { + labels = labels.filter((e) => e !== suggestedLabel); + } + }}> + + {suggestedLabel} + + {/each} + + {error ? error : 'Only alphanumeric characters are allowed'} + + + + + + + + From 169373d653b4b8eb61782f4c1c0b5a8cc62edb8e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Tue, 6 Jan 2026 15:10:08 +0100 Subject: [PATCH 09/45] Improve copy --- src/routes/(console)/organization-[organization]/+page.svelte | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/routes/(console)/organization-[organization]/+page.svelte b/src/routes/(console)/organization-[organization]/+page.svelte index 83c40623c..37ef03204 100644 --- a/src/routes/(console)/organization-[organization]/+page.svelte +++ b/src/routes/(console)/organization-[organization]/+page.svelte @@ -170,7 +170,7 @@ - + {#if $canWriteProjects} {#if projectCreationDisabled && reachedProjectLimit} From 38781499571084582f17cab3164c27d43cebd54d Mon Sep 17 00:00:00 2001 From: Darshan Date: Wed, 7 Jan 2026 15:48:26 +0530 Subject: [PATCH 10/45] bump: plausible. --- package.json | 2 +- pnpm-lock.yaml | 17 ++++++++--------- src/lib/actions/analytics.ts | 30 +++++++++++++++--------------- 3 files changed, 24 insertions(+), 25 deletions(-) diff --git a/package.json b/package.json index a2e1778fe..32ae8fd57 100644 --- a/package.json +++ b/package.json @@ -28,6 +28,7 @@ "@appwrite.io/pink-legacy": "^1.0.3", "@appwrite.io/pink-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc", "@faker-js/faker": "^9.9.0", + "@plausible-analytics/tracker": "^0.4.4", "@popperjs/core": "^2.11.8", "@sentry/sveltekit": "^8.38.0", "@stripe/stripe-js": "^3.5.0", @@ -42,7 +43,6 @@ "ignore": "^6.0.2", "nanoid": "^5.1.5", "nanotar": "^0.1.1", - "plausible-tracker": "^0.3.9", "pretty-bytes": "^6.1.1", "prismjs": "^1.30.0", "remarkable": "^2.0.1", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 9a968c01e..ec391183b 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -29,6 +29,9 @@ importers: '@faker-js/faker': specifier: ^9.9.0 version: 9.9.0 + '@plausible-analytics/tracker': + specifier: ^0.4.4 + version: 0.4.4 '@popperjs/core': specifier: ^2.11.8 version: 2.11.8 @@ -71,9 +74,6 @@ importers: nanotar: specifier: ^0.1.1 version: 0.1.1 - plausible-tracker: - specifier: ^0.3.9 - version: 0.3.9 pretty-bytes: specifier: ^6.1.1 version: 6.1.1 @@ -1008,6 +1008,9 @@ packages: resolution: {integrity: sha512-dfUnCxiN9H4ap84DvD2ubjw+3vUNpstxa0TneY/Paat8a3R4uQZDLSvWjmznAY/DoahqTHl9V46HF/Zs3F29pg==} engines: {node: '>= 10.0.0'} + '@plausible-analytics/tracker@0.4.4': + resolution: {integrity: sha512-fz0NOYUEYXtg1TBaPEEvtcBq3FfmLFuTe1VZw4M8sTWX129br5dguu3M15+plOQnc181ShYe67RfwhKgK89VnA==} + '@playwright/test@1.56.1': resolution: {integrity: sha512-vSMYtL/zOcFpvJCW71Q/OEGQb7KYBPAdKh35WNSkaZA75JlAO8ED8UN6GUNTm3drWomcbcqRPFqQbLae8yBTdg==} engines: {node: '>=18'} @@ -2900,10 +2903,6 @@ packages: resolution: {integrity: sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==} engines: {node: '>=12'} - plausible-tracker@0.3.9: - resolution: {integrity: sha512-hMhneYm3GCPyQon88SZrVJx+LlqhM1kZFQbuAgXPoh/Az2YvO1B6bitT9qlhpiTdJlsT5lsr3gPmzoVjb5CDXA==} - engines: {node: '>=10'} - playwright-core@1.56.1: resolution: {integrity: sha512-hutraynyn31F+Bifme+Ps9Vq59hKuUCz7H1kDOcBs+2oGguKkWTU50bBWrtz34OUWmIwpBTWDxaRPXrIXkgvmQ==} engines: {node: '>=18'} @@ -4575,6 +4574,8 @@ snapshots: '@parcel/watcher-win32-x64': 2.5.1 optional: true + '@plausible-analytics/tracker@0.4.4': {} + '@playwright/test@1.56.1': dependencies: playwright: 1.56.1 @@ -6675,8 +6676,6 @@ snapshots: picomatch@4.0.3: {} - plausible-tracker@0.3.9: {} - playwright-core@1.56.1: {} playwright@1.56.1: diff --git a/src/lib/actions/analytics.ts b/src/lib/actions/analytics.ts index dea8860b5..dbd2cae8b 100644 --- a/src/lib/actions/analytics.ts +++ b/src/lib/actions/analytics.ts @@ -1,5 +1,5 @@ import Analytics, { type AnalyticsPlugin } from 'analytics'; -import Plausible from 'plausible-tracker'; +import { init, track } from '@plausible-analytics/tracker'; import { get } from 'svelte/store'; import { page } from '$app/state'; import { user } from '$lib/stores/user'; @@ -11,30 +11,30 @@ import { getReferrerAndUtmSource, getTrackedQueryParams } from '$lib/helpers/utm function plausible(domain: string): AnalyticsPlugin { if (!browser) return { name: 'analytics-plugin-plausible' }; - const instance = Plausible({ - domain + init({ + domain, + autoCapturePageviews: false, }); return { name: 'analytics-plugin-plausible', page: ({ payload }) => { - instance.trackPageview({ + track('pageview', { url: payload.properties.path, - referrer: payload.properties.referrer, - deviceWidth: payload.properties.width + props: { + referrer: payload.properties.referrer, + deviceWidth: String(payload.properties.width) + } }); }, track: ({ payload }) => { - instance.trackEvent( - payload.event, - { - props: payload.properties - }, - { - url: payload.properties.path, - deviceWidth: payload.properties.width + track(payload.event, { + url: payload.properties.path, + props: { + ...payload.properties, + deviceWidth: String(payload.properties.width) } - ); + }); }, loaded: () => true }; From 81ec4eb8e14044e01ba59a6f880637d07c91a9a0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Wed, 7 Jan 2026 15:35:11 +0100 Subject: [PATCH 11/45] Fix build tests --- package.json | 2 +- pnpm-lock.yaml | 10 +++++----- src/routes/(console)/+layout.ts | 2 +- .../(guest)/register/invite/[slug]/+page.svelte | 2 +- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/package.json b/package.json index f460aa71a..bb9984abc 100644 --- a/package.json +++ b/package.json @@ -22,7 +22,7 @@ }, "dependencies": { "@ai-sdk/svelte": "^1.1.24", - "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56", + "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755", "@appwrite.io/pink-icons": "0.25.0", "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc", "@appwrite.io/pink-legacy": "^1.0.3", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 057668c3a..530d6444a 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -12,8 +12,8 @@ importers: specifier: ^1.1.24 version: 1.1.24(svelte@5.25.3)(zod@3.24.3) '@appwrite.io/console': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56 - version: https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56 + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755 + version: https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755 '@appwrite.io/pink-icons': specifier: 0.25.0 version: 0.25.0 @@ -272,8 +272,8 @@ packages: '@analytics/type-utils@0.6.2': resolution: {integrity: sha512-TD+xbmsBLyYy/IxFimW/YL/9L2IEnM7/EoV9Aeh56U64Ify8o27HJcKjo38XY9Tcn0uOq1AX3thkKgvtWvwFQg==} - '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56} + '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755} version: 2.1.0 '@appwrite.io/pink-icons-svelte@2.0.0-RC.1': @@ -3823,7 +3823,7 @@ snapshots: '@analytics/type-utils@0.6.2': {} - '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@5372e56': {} + '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755': {} '@appwrite.io/pink-icons-svelte@2.0.0-RC.1(svelte@5.25.3)': dependencies: diff --git a/src/routes/(console)/+layout.ts b/src/routes/(console)/+layout.ts index 44956eb5d..af48c0671 100644 --- a/src/routes/(console)/+layout.ts +++ b/src/routes/(console)/+layout.ts @@ -18,7 +18,7 @@ export const load: LayoutLoad = async ({ depends, parent }) => { sdk.forConsole.account.getPrefs(), isCloud ? sdk.forConsole.billing.getPlansInfo() : null, fetch(`${endpoint}/health/version`, { - headers: { 'X-Appwrite-Project': project } + headers: { 'X-Appwrite-Project': project as string } }).then((response) => response.json() as { version?: string }), sdk.forConsole.console.variables() ]); diff --git a/src/routes/(public)/(guest)/register/invite/[slug]/+page.svelte b/src/routes/(public)/(guest)/register/invite/[slug]/+page.svelte index 898d16358..fdd6c247a 100644 --- a/src/routes/(public)/(guest)/register/invite/[slug]/+page.svelte +++ b/src/routes/(public)/(guest)/register/invite/[slug]/+page.svelte @@ -57,7 +57,7 @@ const res = await fetch(`${endpoint}/account/invite`, { method: 'POST', headers: { - 'X-Appwrite-Project': project, + 'X-Appwrite-Project': project as string, 'Content-Type': 'application/json' }, body: JSON.stringify({ From 125110fd3d965d24207273864d00772a6ddf352a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Wed, 7 Jan 2026 15:43:02 +0100 Subject: [PATCH 12/45] Fix merge conflict --- src/routes/(console)/organization-[organization]/+page.ts | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/routes/(console)/organization-[organization]/+page.ts b/src/routes/(console)/organization-[organization]/+page.ts index d05d1945e..ba65f833a 100644 --- a/src/routes/(console)/organization-[organization]/+page.ts +++ b/src/routes/(console)/organization-[organization]/+page.ts @@ -24,9 +24,10 @@ export const load: PageLoad = async ({ params, url, route, depends, parent }) => const archivedPage = Number.isFinite(archivedPageRaw) && archivedPageRaw > 0 ? archivedPageRaw : 1; const archivedOffset = pageToOffset(archivedPage, limit); - + const searchQueries = search - ? [Query.or([Query.search('search', search), Query.contains('labels', search)])]; + ? [Query.or([Query.search('search', search), Query.contains('labels', search)])] + : []; const commonQueries = [Query.equal('teamId', params.organization)]; const activeQueries = isCloud ? [Query.or([Query.equal('status', 'active'), Query.isNull('status')])] From 1b159060511bf42a844d158ee86c39cf13bcbc5a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Wed, 7 Jan 2026 15:44:03 +0100 Subject: [PATCH 13/45] leftover --- src/routes/(console)/organization-[organization]/+page.ts | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/routes/(console)/organization-[organization]/+page.ts b/src/routes/(console)/organization-[organization]/+page.ts index ba65f833a..fc4256b03 100644 --- a/src/routes/(console)/organization-[organization]/+page.ts +++ b/src/routes/(console)/organization-[organization]/+page.ts @@ -61,8 +61,7 @@ export const load: PageLoad = async ({ params, url, route, depends, parent }) => }), isCloud ? sdk.forConsole.projects.list({ - queries: [...commonQueries, ...searchQueries, Query.equal('status', 'archived')], - search: search || undefined + queries: [...commonQueries, ...searchQueries, Query.equal('status', 'archived')] }) : Promise.resolve({ projects: [], total: 0 }) ]); From 8ce59356a864ed7a039cd65c638f6dc92308b493 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Wed, 7 Jan 2026 15:59:12 +0100 Subject: [PATCH 14/45] Update updateLabels.svelte --- .../project-[region]-[project]/settings/updateLabels.svelte | 1 - 1 file changed, 1 deletion(-) diff --git a/src/routes/(console)/project-[region]-[project]/settings/updateLabels.svelte b/src/routes/(console)/project-[region]-[project]/settings/updateLabels.svelte index 9b9782c4d..21d324ec4 100644 --- a/src/routes/(console)/project-[region]-[project]/settings/updateLabels.svelte +++ b/src/routes/(console)/project-[region]-[project]/settings/updateLabels.svelte @@ -25,7 +25,6 @@ try { await sdk.forConsole.projects.updateLabels({ projectId: $project.$id, labels }); await invalidate(Dependencies.PROJECT); - await invalidate(Dependencies.ORGANIZATION); isDisabled = true; addNotification({ type: 'success', From dfffe3487eb71b393e4c099daf9be9ee917f8a2c Mon Sep 17 00:00:00 2001 From: Darshan Date: Thu, 8 Jan 2026 14:06:03 +0530 Subject: [PATCH 15/45] update: move away from hardcoded sdk. --- src/lib/components/backupRestoreBox.svelte | 8 +- src/lib/sdk/backups.ts | 332 ------------------ src/lib/stores/sdk.ts | 2 +- .../databases/+page.svelte | 6 +- .../databases/+page.ts | 6 +- .../database-[database]/backups/+page.ts | 12 +- .../database-[database]/backups/policy.svelte | 6 +- .../database-[database]/backups/table.svelte | 10 +- .../databases/table.svelte | 33 +- 9 files changed, 49 insertions(+), 366 deletions(-) delete mode 100644 src/lib/sdk/backups.ts diff --git a/src/lib/components/backupRestoreBox.svelte b/src/lib/components/backupRestoreBox.svelte index f1de9d3ba..05cb96e8f 100644 --- a/src/lib/components/backupRestoreBox.svelte +++ b/src/lib/components/backupRestoreBox.svelte @@ -5,7 +5,6 @@ import { isCloud, isSelfHosted } from '$lib/system'; import { organization } from '$lib/stores/organization'; import { BillingPlan, Dependencies } from '$lib/constants'; - import type { BackupArchive, BackupRestoration } from '$lib/sdk/backups'; import { goto, invalidate } from '$app/navigation'; import { page } from '$app/state'; import { addNotification } from '$lib/stores/notifications'; @@ -13,10 +12,11 @@ import { getProjectId } from '$lib/helpers/project'; import { toLocaleDate } from '$lib/helpers/date'; import { Typography } from '@appwrite.io/pink-svelte'; + import { type Models } from '@appwrite.io/console'; const backupRestoreItems: { - archives: Map; - restorations: Map; + archives: Map; + restorations: Map; } = { archives: new Map(), restorations: new Map() @@ -117,7 +117,7 @@ if (which === 'restorations') lastDatabaseRestorationId = null; } - function backupName(item: BackupArchive | BackupRestoration, key: string) { + function backupName(item: Models.BackupArchive | Models.BackupRestoration, key: string) { const column = key === 'archives' ? '$createdAt' : 'startedAt'; return toLocaleDate(item[column]); diff --git a/src/lib/sdk/backups.ts b/src/lib/sdk/backups.ts deleted file mode 100644 index 43cb6eb8b..000000000 --- a/src/lib/sdk/backups.ts +++ /dev/null @@ -1,332 +0,0 @@ -import { AppwriteException, Client, type Payload } from '@appwrite.io/console'; - -export type BackupPolicyList = { - total: number; - policies: BackupPolicy[]; -}; - -export type BackupArchiveList = { - total: number; - archives: BackupArchive[]; -}; - -export type BackupRestorationList = { - total: number; - restorations: BackupRestoration[]; -}; - -export type BackupPolicy = { - $id: string; - name: string; - $createdAt: string; - $updatedAt: string; - services: string[]; - resources: string[]; - resourceId?: string; - resourceType?: string; - retention: number; - schedule: string; - enabled: boolean; -}; - -export type BackupArchive = { - $id: string; - $createdAt: string; - $updatedAt: string; - policyId: string; - size: number; - status: string; - startedAt: string; - migrationId: string; - services: string[]; - resources: string[]; - resourceId?: string; - resourceType?: string; -}; - -export type BackupRestoration = { - $id: string; - $createdAt: string; - $updatedAt: string; - archiveId: string; - policyId: string; - status: string; - startedAt: string; - migrationId: string; - services: string[]; - resources: string[]; - options: string; -}; - -export class Backups { - client: Client; - - constructor(client: Client) { - this.client = client; - } - - async createArchive(services: string[], resourceId?: string): Promise { - if (typeof services === 'undefined') { - throw new AppwriteException('Missing required parameter: "services"'); - } - const apiPath = '/backups/archives'; - const payload: Payload = {}; - if (typeof services !== 'undefined') { - payload['services'] = services; - } - if (typeof resourceId !== 'undefined') { - payload['resourceId'] = resourceId; - } - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('post', uri, apiHeaders, payload); - } - - async deleteArchive(archiveId: string): Promise { - if (typeof archiveId === 'undefined') { - throw new AppwriteException('Missing required parameter: "archiveId"'); - } - const apiPath = '/backups/archives/{archiveId}'.replace('{archiveId}', archiveId); - const payload: Payload = {}; - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('delete', uri, apiHeaders, payload); - } - - async listArchives(queries?: string[]): Promise { - const apiPath = '/backups/archives'; - const payload: Payload = {}; - if (typeof queries !== 'undefined') { - payload['queries'] = queries; - } - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('get', uri, apiHeaders, payload); - } - - async getArchive(archiveId: string): Promise { - if (typeof archiveId === 'undefined') { - throw new AppwriteException('Missing required parameter: "archiveId"'); - } - const apiPath = '/backups/archives/{archiveId}'.replace('{archiveId}', archiveId); - const payload: Payload = {}; - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('get', uri, apiHeaders, payload); - } - - async listPolicies(queries?: string[]): Promise { - const apiPath = '/backups/policies'; - const payload: Payload = {}; - if (typeof queries !== 'undefined') { - payload['queries'] = queries; - } - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('get', uri, apiHeaders, payload); - } - - async createPolicy( - policyId: string, - services: string[], - retention: number, - schedule: string, - name?: string, - resourceId?: string, - enabled?: boolean - ): Promise { - if (typeof policyId === 'undefined') { - throw new AppwriteException('Missing required parameter: "policyId"'); - } - if (typeof services === 'undefined') { - throw new AppwriteException('Missing required parameter: "services"'); - } - if (typeof retention === 'undefined') { - throw new AppwriteException('Missing required parameter: "retention"'); - } - if (typeof schedule === 'undefined') { - throw new AppwriteException('Missing required parameter: "schedule"'); - } - const apiPath = '/backups/policies'; - const payload: Payload = {}; - if (typeof policyId !== 'undefined') { - payload['policyId'] = policyId; - } - if (typeof name !== 'undefined') { - payload['name'] = name; - } - if (typeof services !== 'undefined') { - payload['services'] = services; - } - if (typeof resourceId !== 'undefined') { - payload['resourceId'] = resourceId; - } - if (typeof enabled !== 'undefined') { - payload['enabled'] = enabled; - } - if (typeof retention !== 'undefined') { - payload['retention'] = retention; - } - if (typeof schedule !== 'undefined') { - payload['schedule'] = schedule; - } - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('post', uri, apiHeaders, payload); - } - - async getPolicy(policyId: string): Promise { - if (typeof policyId === 'undefined') { - throw new AppwriteException('Missing required parameter: "policyId"'); - } - const apiPath = '/backups/policies/{policyId}'.replace('{policyId}', policyId); - const payload: Payload = {}; - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('get', uri, apiHeaders, payload); - } - - async updatePolicy( - policyId: string, - name?: string, - retention?: number, - schedule?: string, - enabled?: boolean - ): Promise { - if (typeof policyId === 'undefined') { - throw new AppwriteException('Missing required parameter: "policyId"'); - } - const apiPath = '/backups/policies/{policyId}'.replace('{policyId}', policyId); - const payload: Payload = {}; - if (typeof name !== 'undefined') { - payload['name'] = name; - } - if (typeof retention !== 'undefined') { - payload['retention'] = retention; - } - if (typeof schedule !== 'undefined') { - payload['schedule'] = schedule; - } - if (typeof enabled !== 'undefined') { - payload['enabled'] = enabled; - } - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('patch', uri, apiHeaders, payload); - } - - async deletePolicy(policyId: string): Promise { - if (typeof policyId === 'undefined') { - throw new AppwriteException('Missing required parameter: "policyId"'); - } - const apiPath = '/backups/policies/{policyId}'.replace('{policyId}', policyId); - const payload: Payload = {}; - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('delete', uri, apiHeaders, payload); - } - - async createRestoration( - archiveId: string, - services: string[], - newResourceId?: string, - newResourceName?: string - ): Promise { - if (typeof archiveId === 'undefined') { - throw new AppwriteException('Missing required parameter: "archiveId"'); - } - if (typeof services === 'undefined') { - throw new AppwriteException('Missing required parameter: "services"'); - } - const apiPath = '/backups/restoration'; - const payload: Payload = {}; - if (typeof archiveId !== 'undefined') { - payload['archiveId'] = archiveId; - } - if (typeof services !== 'undefined') { - payload['services'] = services; - } - if (typeof newResourceId !== 'undefined') { - payload['newResourceId'] = newResourceId; - } - if (typeof newResourceName !== 'undefined') { - payload['newResourceName'] = newResourceName; - } - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('post', uri, apiHeaders, payload); - } - - async listRestorations(queries?: string[]): Promise { - const apiPath = '/backups/restorations'; - const payload: Payload = {}; - if (typeof queries !== 'undefined') { - payload['queries'] = queries; - } - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('get', uri, apiHeaders, payload); - } - - async getRestoration(restorationId: string): Promise { - if (typeof restorationId === 'undefined') { - throw new AppwriteException('Missing required parameter: "restorationId"'); - } - const apiPath = '/backups/restorations/{restorationId}'.replace( - '{restorationId}', - restorationId - ); - const payload: Payload = {}; - const uri = new URL(this.client.config.endpoint + apiPath); - - const apiHeaders: { [header: string]: string } = { - 'content-type': 'application/json' - }; - - return await this.client.call('get', uri, apiHeaders, payload); - } -} diff --git a/src/lib/stores/sdk.ts b/src/lib/stores/sdk.ts index 05f9f54db..d7e0cc7b9 100644 --- a/src/lib/stores/sdk.ts +++ b/src/lib/stores/sdk.ts @@ -3,6 +3,7 @@ import { Account, Assistant, Avatars, + Backups, Client, Console, Functions, @@ -26,7 +27,6 @@ import { Organizations } from '@appwrite.io/console'; import { Billing } from '../sdk/billing'; -import { Backups } from '../sdk/backups'; import { Sources } from '$lib/sdk/sources'; import { REGION_FRA, diff --git a/src/routes/(console)/project-[region]-[project]/databases/+page.svelte b/src/routes/(console)/project-[region]-[project]/databases/+page.svelte index e413399e8..adba24b05 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/+page.svelte @@ -77,7 +77,11 @@ {#if data.view === 'grid'} {:else} -
+
{/if} , policies: Record; + let lastBackups: Record = {}; + let policies: Record = {}; if (isCloud && backupsEnabled) { [policies, lastBackups] = await Promise.all([ @@ -86,7 +86,7 @@ async function fetchDatabasesAndBackups( async function fetchPolicies(databases: Models.DatabaseList, params: RouteParams) { if (isSelfHosted) return {}; - const databasePolicies: Record = {}; + const databasePolicies: Record = {}; await Promise.all( databases.databases.map(async (database) => { diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts index 52d9e65c9..1f88254c7 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts @@ -2,8 +2,8 @@ import { getLimit, getPage, getView, pageToOffset, View } from '$lib/helpers/loa import { Dependencies, PAGE_LIMIT } from '$lib/constants'; import { sdk } from '$lib/stores/sdk'; import { Query } from '@appwrite.io/console'; -import type { BackupArchive, BackupArchiveList, BackupPolicyList } from '$lib/sdk/backups'; import { isCloud } from '$lib/system'; +import { type Models } from '@appwrite.io/console'; export const load = async ({ params, url, route, depends, parent }) => { depends(Dependencies.BACKUPS); @@ -13,8 +13,8 @@ export const load = async ({ params, url, route, depends, parent }) => { const view = getView(url, route, View.Grid); const offset = pageToOffset(page, limit); - let backups: BackupArchiveList = { total: 0, archives: [] }; - let policies: BackupPolicyList = { total: 0, policies: [] }; + let backups: Models.BackupArchiveList = { total: 0, archives: [] }; + let policies: Models.BackupPolicyList = { total: 0, policies: [] }; // already loaded by parent. const { currentPlan } = await parent(); @@ -59,17 +59,17 @@ export const load = async ({ params, url, route, depends, parent }) => { }; }; -const groupArchivesByPolicy = (archives: BackupArchive[]) => { +const groupArchivesByPolicy = (archives: Models.BackupArchive[]) => { return archives.reduce((acc, archive) => { if (!acc.has(archive.policyId)) { acc.set(archive.policyId, []); } acc.get(archive.policyId)!.push(archive); return acc; - }, new Map()); + }, new Map()); }; -const getLatestBackupForPolicies = (policyIdMap: Map) => { +const getLatestBackupForPolicies = (policyIdMap: Map) => { const latestBackups = new Map(); for (const [policyId, archives] of policyIdMap) { const latestBackup = archives.sort( diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte index e4ccd8b91..a8f4cb252 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte @@ -11,7 +11,6 @@ import { toLocaleDateTime } from '$lib/helpers/date'; import EmptyDark from '$lib/images/backups/backups-dark.png'; import EmptyLight from '$lib/images/backups/backups-light.png'; - import type { BackupPolicy, BackupPolicyList } from '$lib/sdk/backups'; import { backupFrequencies } from '$lib/helpers/backups'; import { Click, trackEvent } from '$lib/actions/analytics'; import { @@ -27,14 +26,15 @@ import { Confirm } from '$lib/components/index.js'; import Ellipse from './components/Ellipse.svelte'; import { page } from '$app/state'; + import { type Models } from '@appwrite.io/console'; let showDelete = false; - let selectedPolicy: BackupPolicy = null; + let selectedPolicy: Models.BackupPolicy = null; let showEveryPolicy = false; export let showCreatePolicy = false; - export let policies: BackupPolicyList; + export let policies: Models.BackupPolicyList; export let lastBackupDates: Record; async function deletePolicy() { diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte index 7cee5aacc..eb23d4da6 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte @@ -18,7 +18,6 @@ import { ID } from '@appwrite.io/console'; import { columns } from './store'; import { database } from '../store'; - import type { BackupArchive, BackupPolicy } from '$lib/sdk/backups'; import { Click, Submit, trackError, trackEvent } from '$lib/actions/analytics'; import { copy } from '$lib/helpers/copy'; import { LabelCard } from '$lib/components/index.js'; @@ -45,6 +44,7 @@ import { capitalize } from '$lib/helpers/string'; import Ellipse from './components/Ellipse.svelte'; import { page } from '$app/state'; + import { type Models } from '@appwrite.io/console'; const { data @@ -53,7 +53,7 @@ } = $props(); let showDelete = $state(false); - let selectedBackup: BackupArchive | null = $state(null); + let selectedBackup: Models.BackupArchive | null = $state(null); let showDropdown = []; @@ -87,15 +87,15 @@ ); }); - function getPolicyDetails(policyId: string | null): BackupPolicy | null { + function getPolicyDetails(policyId: string | null): Models.BackupPolicy | null { return data.policies.policies.find((policy) => policy.$id === policyId); } - function getCleanBackupName(backup: BackupArchive): string { + function getCleanBackupName(backup: Models.BackupArchive): string { return toLocaleDateTime(backup.$createdAt).replaceAll(',', ''); } - function getBackupStatus(backup: BackupArchive) { + function getBackupStatus(backup: Models.BackupArchive) { switch (backup.status) { case 'pending': return 'pending'; diff --git a/src/routes/(console)/project-[region]-[project]/databases/table.svelte b/src/routes/(console)/project-[region]-[project]/databases/table.svelte index 0f88682d9..0764bf9ea 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/table.svelte @@ -6,10 +6,19 @@ import { columns } from './store'; import { IconExclamation } from '@appwrite.io/pink-icons-svelte'; import { Layout, Tooltip, Table, Icon } from '@appwrite.io/pink-svelte'; - import type { BackupPolicy } from '$lib/sdk/backups'; + import { type Models } from '@appwrite.io/console'; - export let data; - const tables = data.tables; + let { + tables, + policies, + databases, + lastBackups + }: { + tables: Record; + databases: Models.DatabaseList; + lastBackups: Record; + policies: Record; + } = $props(); function getPolicyDescription(cron: string): string { const [minute, hour, dayOfMonth, , dayOfWeek] = cron.split(' '); @@ -19,6 +28,10 @@ if (minute !== '*' && hour === '*') return 'Hourly'; if (hour !== '*') return 'Daily'; } + + function getPoliciesDescription(policies: Models.BackupPolicy[] | null): string { + return policies?.map((policy) => getPolicyDescription(policy.schedule)).join(', ') ?? ''; + } @@ -27,7 +40,7 @@ {title} {/each} - {#each data.databases.databases as database (database.$id)} + {#each databases.databases as database (database.$id)} {@const tableId = tables[database?.$id] ?? null} {@const tableHref = tableId ? `/table-${tableId}` : ''} @@ -45,18 +58,16 @@ {:else if column.id === 'name'} {database.name} {:else if column.id === 'backup'} - {@const policies = data.policies?.[database.$id] ?? null} - {@const lastBackup = data.lastBackups?.[database.$id] ?? null} - {@const description = policies - ?.map((policy: BackupPolicy) => getPolicyDescription(policy.schedule)) - .join(', ')} + {@const backupPolicies = policies?.[database.$id] ?? null} + {@const lastBackup = lastBackups?.[database.$id] ?? null} + {@const description = getPoliciesDescription(backupPolicies)} - {#if !policies} + {#if !backupPolicies} Date: Thu, 8 Jan 2026 14:10:19 +0530 Subject: [PATCH 16/45] update: object params from positional params. --- src/lib/stores/database.ts | 6 ++-- .../databases/+page.ts | 28 +++++++++++-------- .../databases/create.svelte | 18 ++++++------ .../database-[database]/backups/+page.svelte | 25 ++++++++--------- .../database-[database]/backups/+page.ts | 16 +++++------ .../database-[database]/backups/policy.svelte | 6 ++-- .../database-[database]/backups/table.svelte | 18 ++++++------ 7 files changed, 60 insertions(+), 57 deletions(-) diff --git a/src/lib/stores/database.ts b/src/lib/stores/database.ts index 4c93859ce..648708bd0 100644 --- a/src/lib/stores/database.ts +++ b/src/lib/stores/database.ts @@ -27,9 +27,9 @@ export async function checkForDatabaseBackupPolicies( if (isCloud && backupsEnabled) { try { - const policies = await sdk - .forProject(region, projectId) - .backups.listPolicies([Query.limit(1), Query.equal('resourceId', database.$id)]); + const policies = await sdk.forProject(region, projectId).backups.listPolicies({ + queries: [Query.limit(1), Query.equal('resourceId', database.$id)] + }); total = policies.total; } catch (e) { diff --git a/src/routes/(console)/project-[region]-[project]/databases/+page.ts b/src/routes/(console)/project-[region]-[project]/databases/+page.ts index 30405ec37..cec0eda64 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/+page.ts +++ b/src/routes/(console)/project-[region]-[project]/databases/+page.ts @@ -93,12 +93,14 @@ async function fetchPolicies(databases: Models.DatabaseList, params: RouteParams try { const { policies } = await sdk .forProject(params.region, params.project) - .backups.listPolicies([ - // TODO: are all needed!? - // Query.limit(3), - Query.equal('resourceType', 'database'), - Query.equal('resourceId', database.$id) - ]); + .backups.listPolicies({ + queries: [ + // TODO: are all needed!? + // Query.limit(3), + Query.equal('resourceType', 'database'), + Query.equal('resourceId', database.$id) + ] + }); if (policies.length > 0) { databasePolicies[database.$id] = policies; @@ -122,12 +124,14 @@ async function fetchLastBackups(databases: Models.DatabaseList, params: RoutePar try { const { archives } = await sdk .forProject(params.region, params.project) - .backups.listArchives([ - Query.limit(1), - Query.orderDesc('$createdAt'), - Query.equal('resourceType', 'database'), - Query.equal('resourceId', database.$id) - ]); + .backups.listArchives({ + queries: [ + Query.limit(1), + Query.orderDesc('$createdAt'), + Query.equal('resourceType', 'database'), + Query.equal('resourceId', database.$id) + ] + }); if (archives.length > 0) { lastBackups[database.$id] = timeFromNow(archives[0].$createdAt); diff --git a/src/routes/(console)/project-[region]-[project]/databases/create.svelte b/src/routes/(console)/project-[region]-[project]/databases/create.svelte index f00b68e59..3fc1736dd 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/create.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/create.svelte @@ -61,16 +61,14 @@ const totalPoliciesPromise = totalPolicies.map((policy) => { cronExpression(policy); - return sdk - .forProject(page.params.region, page.params.project) - .backups.createPolicy( - ID.unique(), - ['databases'], - policy.retained, - policy.schedule, - policy.label, - resourceId - ); + return sdk.forProject(page.params.region, page.params.project).backups.createPolicy({ + policyId: ID.unique(), + services: ['databases'], + retention: policy.retained, + schedule: policy.schedule, + name: policy.label, + resourceId + }); }); await Promise.all(totalPoliciesPromise); diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.svelte index 99521078d..e64490541 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.svelte @@ -66,9 +66,10 @@ const createManualBackup = async () => { try { - await sdk - .forProject(page.params.region, page.params.project) - .backups.createArchive(['databases'], data.database.$id); + await sdk.forProject(page.params.region, page.params.project).backups.createArchive({ + services: ['databases'], + resourceId: data.database.$id + }); await invalidate(Dependencies.BACKUPS); addNotification({ type: 'success', @@ -119,16 +120,14 @@ const totalPoliciesPromise = totalPolicies.map((policy) => { cronExpression(policy); - return sdk - .forProject(page.params.region, page.params.project) - .backups.createPolicy( - ID.unique(), - ['databases'], - policy.retained, - policy.schedule, - policy.label, - data.database.$id - ); + return sdk.forProject(page.params.region, page.params.project).backups.createPolicy({ + policyId: ID.unique(), + services: ['databases'], + retention: policy.retained, + schedule: policy.schedule, + name: policy.label, + resourceId: data.database.$id + }); }); try { diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts index 1f88254c7..60d9bfb21 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/+page.ts @@ -23,23 +23,23 @@ export const load = async ({ params, url, route, depends, parent }) => { if (isCloud && backupsEnabled) { try { [backups, policies] = await Promise.all([ - sdk - .forProject(params.region, params.project) - .backups.listArchives([ + sdk.forProject(params.region, params.project).backups.listArchives({ + queries: [ Query.limit(limit), Query.offset(offset), Query.orderDesc('$createdAt'), Query.equal('resourceType', 'database'), Query.equal('resourceId', params.database) - ]), + ] + }), - sdk - .forProject(params.region, params.project) - .backups.listPolicies([ + sdk.forProject(params.region, params.project).backups.listPolicies({ + queries: [ Query.orderDesc('$createdAt'), Query.equal('resourceType', 'database'), Query.equal('resourceId', params.database) - ]) + ] + }) ]); } catch (e) { // ignore diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte index a8f4cb252..f73fc68a9 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/policy.svelte @@ -39,9 +39,9 @@ async function deletePolicy() { try { - await sdk - .forProject(page.params.region, page.params.project) - .backups.deletePolicy(selectedPolicy.$id); + await sdk.forProject(page.params.region, page.params.project).backups.deletePolicy({ + policyId: selectedPolicy.$id + }); addNotification({ type: 'success', message: 'Backup policy has been deleted' diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte index eb23d4da6..12f13bd45 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte @@ -115,7 +115,7 @@ try { await sdk .forProject(page.params.region, page.params.project) - .backups.deleteArchive(archiveId); + .backups.deleteArchive({ archiveId }); addNotification({ type: 'success', @@ -135,7 +135,9 @@ async function deleteBackups(batchDelete: DeleteOperation): Promise { const result = await batchDelete((archiveId) => - sdk.forProject(page.params.region, page.params.project).backups.deleteArchive(archiveId) + sdk + .forProject(page.params.region, page.params.project) + .backups.deleteArchive({ archiveId }) ); try { @@ -160,12 +162,12 @@ try { await sdk .forProject(page.params.region, page.params.project) - .backups.createRestoration( - selectedBackup.$id, - ['databases'], - newDatabaseInfo.id ?? ID.unique(), - newDatabaseInfo.name - ); + .backups.createRestoration({ + archiveId: selectedBackup.$id, + services: ['databases'], + newResourceId: newDatabaseInfo.id ?? ID.unique(), + newResourceName: newDatabaseInfo.name + }); await invalidate(Dependencies.BACKUPS); addNotification({ From 0f029d599ad5507246da4de2a89c2469910706e2 Mon Sep 17 00:00:00 2001 From: Darshan Date: Thu, 8 Jan 2026 14:28:35 +0530 Subject: [PATCH 17/45] address comment. --- .../databases/database-[database]/backups/table.svelte | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte index 12f13bd45..5cd807592 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/backups/table.svelte @@ -15,7 +15,7 @@ import { addNotification } from '$lib/stores/notifications'; import { invalidate } from '$app/navigation'; import { calculateSize } from '$lib/helpers/sizeConvertion'; - import { ID } from '@appwrite.io/console'; + import { ID, type Models } from '@appwrite.io/console'; import { columns } from './store'; import { database } from '../store'; import { Click, Submit, trackError, trackEvent } from '$lib/actions/analytics'; @@ -44,7 +44,6 @@ import { capitalize } from '$lib/helpers/string'; import Ellipse from './components/Ellipse.svelte'; import { page } from '$app/state'; - import { type Models } from '@appwrite.io/console'; const { data From d38f16a3e59e5997f99025d97cfceb6ed1c82338 Mon Sep 17 00:00:00 2001 From: Darshan Date: Thu, 8 Jan 2026 16:45:51 +0530 Subject: [PATCH 18/45] lint. --- src/lib/actions/analytics.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/lib/actions/analytics.ts b/src/lib/actions/analytics.ts index dbd2cae8b..790a1423a 100644 --- a/src/lib/actions/analytics.ts +++ b/src/lib/actions/analytics.ts @@ -13,7 +13,7 @@ function plausible(domain: string): AnalyticsPlugin { init({ domain, - autoCapturePageviews: false, + autoCapturePageviews: false }); return { From 5985a501f9a241b4ced261ba1f2d6ca042e7e01a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Thu, 8 Jan 2026 16:50:05 +0100 Subject: [PATCH 19/45] Prevnet early dpeloynt success screen --- .../sites/create-site/deploying/+page.svelte | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index 3cb100543..c2a6b960c 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -25,7 +25,13 @@ ) ) { deployment = response.payload as Models.Deployment; - if (deployment.status === 'ready') { + + const isReady = + deployment.status === 'ready' && + deployment.screenshotLight && + deployment.screenshotDark; + + if (isReady) { const resolvedUrl = resolve( '/(console)/project-[region]-[project]/sites/create-site/finish', { From a8f4ae87e1b5ecba91323b89a357a14a68c28070 Mon Sep 17 00:00:00 2001 From: kylewhirl Date: Thu, 8 Jan 2026 20:25:30 -1000 Subject: [PATCH 20/45] Fix null relationship update comparison --- .../database-[database]/table-[table]/rows/edit.svelte | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/edit.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/edit.svelte index bfa9e7b4c..3f1faea38 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/edit.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/edit.svelte @@ -118,6 +118,10 @@ if (isRelationship(column)) { if (isRelationshipToMany(column as Models.ColumnRelationship)) { + if (!Array.isArray(workColumn) || !Array.isArray(currentColumn)) { + return workColumn === currentColumn; + } + const workIds = workColumn.map((doc: string | Record) => typeof doc === 'string' ? doc : doc.$id ); From ac756b480240f42beb8b0460938c20c410f9c421 Mon Sep 17 00:00:00 2001 From: kylewhirl Date: Thu, 8 Jan 2026 20:29:56 -1000 Subject: [PATCH 21/45] Fix relationship required and partial update --- .../rows/columns/types/relationship.svelte | 8 ++++---- .../table-[table]/rows/edit.svelte | 11 +++++++++- .../table-[table]/rows/editRelated.svelte | 20 +++++++++++++++++-- 3 files changed, 32 insertions(+), 7 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte index f790579c5..fccc94df4 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte @@ -297,7 +297,7 @@ { + if (!compareColumns(column, $work, row)) { + acc[column.key] = $work?.[column.key]; + } + return acc; + }, {} as Record) + : { ...$work }; + await sdk.forProject(page.params.region, page.params.project).tablesDB.updateRow({ databaseId, tableId, rowId: row.$id, - data: $work, + data, permissions: $work.$permissions }); diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte index 501149348..12abfdc5d 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte @@ -213,6 +213,19 @@ return workColumn === currentColumn; } + function buildUpdateData(workValue: Models.Row, originalRow: Models.Row) { + if (!relatedTable?.columns?.length) { + return { ...workValue }; + } + + return relatedTable.columns.reduce((acc, column) => { + if (!compareColumns(column, workValue, originalRow)) { + acc[column.key] = workValue?.[column.key]; + } + return acc; + }, {} as Record); + } + function calculateAndCompareDisabledState() { if (!relatedTable?.columns?.length || !fetchedRows.length) return true; @@ -245,11 +258,13 @@ const work = workData.get(rowId); const workValue = get(work); + const originalRow = fetchedRows.find((row) => row.$id === rowId); + const data = originalRow ? buildUpdateData(workValue, originalRow) : { ...workValue }; await sdk.forProject(page.params.region, page.params.project).tablesDB.updateRow({ databaseId, tableId: relatedTable.$id, rowId: rowId, - data: workValue, + data, permissions: workValue.$permissions }); @@ -263,13 +278,14 @@ if (!work) return; const workValue = get(work); + const data = buildUpdateData(workValue, row); return sdk .forProject(page.params.region, page.params.project) .tablesDB.updateRow({ databaseId, tableId: relatedTable.$id, rowId: row.$id, - data: workValue, + data, permissions: workValue.$permissions }); }); From a30efd64f88b0e23985286820ee31a244fcf83df Mon Sep 17 00:00:00 2001 From: kylewhirl Date: Thu, 8 Jan 2026 22:11:38 -1000 Subject: [PATCH 22/45] Make relationship inputs strictly optional --- .../rows/columns/types/relationship.svelte | 12 +++++------ .../table-[table]/rows/edit.svelte | 15 +------------- .../table-[table]/rows/editRelated.svelte | 20 ++----------------- 3 files changed, 9 insertions(+), 38 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte index fccc94df4..9cc4bd868 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte @@ -297,7 +297,7 @@ ) => typeof doc === 'string' ? doc : doc.$id ); @@ -146,20 +142,11 @@ if (!row || !work) return; try { - const data = $table?.columns?.length - ? $table.columns.reduce((acc, column) => { - if (!compareColumns(column, $work, row)) { - acc[column.key] = $work?.[column.key]; - } - return acc; - }, {} as Record) - : { ...$work }; - await sdk.forProject(page.params.region, page.params.project).tablesDB.updateRow({ databaseId, tableId, rowId: row.$id, - data, + data: $work, permissions: $work.$permissions }); diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte index 12abfdc5d..501149348 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/editRelated.svelte @@ -213,19 +213,6 @@ return workColumn === currentColumn; } - function buildUpdateData(workValue: Models.Row, originalRow: Models.Row) { - if (!relatedTable?.columns?.length) { - return { ...workValue }; - } - - return relatedTable.columns.reduce((acc, column) => { - if (!compareColumns(column, workValue, originalRow)) { - acc[column.key] = workValue?.[column.key]; - } - return acc; - }, {} as Record); - } - function calculateAndCompareDisabledState() { if (!relatedTable?.columns?.length || !fetchedRows.length) return true; @@ -258,13 +245,11 @@ const work = workData.get(rowId); const workValue = get(work); - const originalRow = fetchedRows.find((row) => row.$id === rowId); - const data = originalRow ? buildUpdateData(workValue, originalRow) : { ...workValue }; await sdk.forProject(page.params.region, page.params.project).tablesDB.updateRow({ databaseId, tableId: relatedTable.$id, rowId: rowId, - data, + data: workValue, permissions: workValue.$permissions }); @@ -278,14 +263,13 @@ if (!work) return; const workValue = get(work); - const data = buildUpdateData(workValue, row); return sdk .forProject(page.params.region, page.params.project) .tablesDB.updateRow({ databaseId, tableId: relatedTable.$id, rowId: row.$id, - data, + data: workValue, permissions: workValue.$permissions }); }); From 748856ffb1d89b0c8eb4095d08f540975eab2ec4 Mon Sep 17 00:00:00 2001 From: kylewhirl Date: Thu, 8 Jan 2026 22:43:32 -1000 Subject: [PATCH 23/45] Fix spatial JSON parsing in spreadsheet editor --- .../rows/columns/types/string.svelte | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/string.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/string.svelte index 491d8ceda..1e7c5f8d0 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/string.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/string.svelte @@ -95,9 +95,20 @@ value = newArray as string[] | number[] | boolean[]; } } else { - const parsedValue = isSpatialType(column) - ? JSON.parse(stringValue) - : parseValue(stringValue); + let parsedValue = parseValue(stringValue); + + if (isSpatialType(column)) { + if (!stringValue?.trim()) { + parsedValue = null; + } else { + try { + parsedValue = JSON.parse(stringValue); + } catch { + return; + } + } + } + if (JSON.stringify(parsedValue) !== JSON.stringify(value)) { value = parsedValue; } From aa0c425cd4ffaefd7a0de6418bb5f2fdb262d780 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Fri, 9 Jan 2026 13:06:00 +0100 Subject: [PATCH 24/45] Improve UX of finalazing step --- src/lib/helpers/buildTimeout.ts | 18 +++++++++ .../(components)/deploymentCard.svelte | 7 +++- .../deployment-[deployment]/+page.svelte | 1 + .../function-[function]/table.svelte | 1 + .../(components)/deploymentActionMenu.svelte | 1 + .../sites/(components)/logs.svelte | 8 +++- .../sites/(components)/logsTimer.svelte | 9 ++++- .../sites/(components)/siteCard.svelte | 7 +++- .../sites/create-site/deploying/+page.svelte | 40 ++++++++++++------- .../deployment-[deployment]/+page.svelte | 7 +++- .../site-[site]/deployments/table.svelte | 1 + .../site-[site]/deploymentsOverview.svelte | 1 + 12 files changed, 81 insertions(+), 20 deletions(-) diff --git a/src/lib/helpers/buildTimeout.ts b/src/lib/helpers/buildTimeout.ts index 3915811c2..08e2707da 100644 --- a/src/lib/helpers/buildTimeout.ts +++ b/src/lib/helpers/buildTimeout.ts @@ -24,12 +24,30 @@ function isBuildTimedOut(createdAt: string, status: string, timeoutSeconds: numb export function getEffectiveBuildStatus( originalStatus: string, createdAt: string, + screenshots: Array, consoleVariables: Models.ConsoleVariables | undefined ): string { const timeoutSeconds = getBuildTimeoutSeconds(consoleVariables); if (isBuildTimedOut(createdAt, originalStatus, timeoutSeconds)) { return 'failed'; } + + const isReady = originalStatus === 'ready'; + let hasScreenshot = true; + if (screenshots.length === 0) { + hasScreenshot = false; + } + for (const screenshot of screenshots) { + if (!screenshot) { + hasScreenshot = false; + break; + } + } + + if (isReady && !hasScreenshot) { + return 'finalizing'; + } + return originalStatus; } diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte index 237610720..1d18ee85b 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte @@ -39,7 +39,12 @@ } = $props(); let effectiveStatus = $derived( - getEffectiveBuildStatus(deployment.status, deployment.$createdAt, $regionalConsoleVariables) + getEffectiveBuildStatus( + deployment.status, + deployment.$createdAt, + [deployment.screenshotLight, deployment.screenshotDark], + $regionalConsoleVariables + ) ); let totalSize = $derived(humanFileSize(deployment?.totalSize ?? 0)); diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte index 9a9b47b2e..9676c3302 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte @@ -44,6 +44,7 @@ getEffectiveBuildStatus( data.deployment.status, data.deployment.$createdAt, + [data.deployment.screenshotLight, data.deployment.screenshotDark], $regionalConsoleVariables ) ); diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte index 94672a8d6..a6355710d 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte @@ -97,6 +97,7 @@ {@const effectiveStatus = getEffectiveBuildStatus( deployment.status, deployment.$createdAt, + [deployment.screenshotLight, deployment.screenshotDark], $regionalConsoleVariables )} - {#if ['processing', 'building'].includes(effectiveStatus)} + {#if ['processing', 'building', 'finalizing'].includes(effectiveStatus)}

diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte index 78ad644f4..93696adb7 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte @@ -43,7 +43,12 @@ } = $props(); let effectiveStatus = $derived( - getEffectiveBuildStatus(deployment.status, deployment.$createdAt, $regionalConsoleVariables) + getEffectiveBuildStatus( + deployment.status, + deployment.$createdAt, + [deployment.screenshotLight, deployment.screenshotDark], + $regionalConsoleVariables + ) ); let show = $state(false); diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index c2a6b960c..ec8fddf06 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -16,6 +16,7 @@ let { data } = $props(); let deployment = $state(data.deployment); + let skipScreenshotInterval = $state(null); onMount(() => { return realtime.forConsole(page.params.region, 'console', async (response) => { @@ -26,24 +27,35 @@ ) { deployment = response.payload as Models.Deployment; - const isReady = - deployment.status === 'ready' && - deployment.screenshotLight && - deployment.screenshotDark; + const isReady = deployment.status === 'ready'; - if (isReady) { - const resolvedUrl = resolve( - '/(console)/project-[region]-[project]/sites/create-site/finish', - { - region: page.params.region, - project: page.params.project - } - ); - await goto(`${resolvedUrl}?site=${data.site.$id}`); + const isFinished = + isReady && deployment.screenshotLight && deployment.screenshotDark; + + // Fallback mechanism + // If ready but not finished for over 30 seconds, go anyway + if (isReady && isFinished) { + clearInterval(skipScreenshotInterval); + goToFinishScreen(); + } else if (isReady) { + skipScreenshotInterval = setInterval(async () => { + goToFinishScreen(); + }, 30000); } } }); }); + + async function goToFinishScreen() { + const resolvedUrl = resolve( + '/(console)/project-[region]-[project]/sites/create-site/finish', + { + region: page.params.region, + project: page.params.project + } + ); + await goto(`${resolvedUrl}?site=${data.site.$id}`); + } - {#if ['processing', 'building'].includes(data.deployment.status)} + {#if ['processing', 'building', 'finalizing'].includes(data.deployment.status)} Deployment will continue in the background diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte index 1d418842f..3f95bd737 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte @@ -27,7 +27,12 @@ let deployment = $derived(data.deployment); let effectiveStatus = $derived( - getEffectiveBuildStatus(deployment.status, deployment.$createdAt, $regionalConsoleVariables) + getEffectiveBuildStatus( + deployment.status, + deployment.$createdAt, + [deployment.screenshotLight, deployment.screenshotDark], + $regionalConsoleVariables + ) ); let showRedeploy = $state(false); diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte index d135498a6..1752e31c3 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte @@ -84,6 +84,7 @@ {@const effectiveStatus = getEffectiveBuildStatus( deployment.status, deployment.$createdAt, + [deployment.screenshotLight, deployment.screenshotDark], $regionalConsoleVariables )} Date: Fri, 9 Jan 2026 13:32:28 +0100 Subject: [PATCH 25/45] PR review fixes --- src/lib/helpers/buildTimeout.ts | 4 +- .../sites/create-site/deploying/+page.svelte | 70 +++++++++++++------ 2 files changed, 52 insertions(+), 22 deletions(-) diff --git a/src/lib/helpers/buildTimeout.ts b/src/lib/helpers/buildTimeout.ts index 08e2707da..9b2544df9 100644 --- a/src/lib/helpers/buildTimeout.ts +++ b/src/lib/helpers/buildTimeout.ts @@ -24,7 +24,9 @@ function isBuildTimedOut(createdAt: string, status: string, timeoutSeconds: numb export function getEffectiveBuildStatus( originalStatus: string, createdAt: string, - screenshots: Array, + screenshots: Array< + Models.Deployment['screenshotLight'] | Models.Deployment['screenshotDark'] | undefined + >, consoleVariables: Models.ConsoleVariables | undefined ): string { const timeoutSeconds = getBuildTimeoutSeconds(consoleVariables); diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index ec8fddf06..b70984418 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -12,38 +12,66 @@ import { onMount } from 'svelte'; import { getFrameworkIcon } from '$lib/stores/sites'; import type { Models } from '@appwrite.io/console'; + import { getEffectiveBuildStatus } from '$lib/helpers/buildTimeout'; + import { regionalConsoleVariables } from '$routes/(console)/project-[region]-[project]/store'; let { data } = $props(); let deployment = $state(data.deployment); - let skipScreenshotInterval = $state(null); + let skipScreenshotInterval: ReturnType | null = $state(null); + + let effectiveStatus = $derived( + getEffectiveBuildStatus( + deployment.status, + deployment.$createdAt, + [deployment.screenshotLight, deployment.screenshotDark], + $regionalConsoleVariables + ) + ); onMount(() => { - return realtime.forConsole(page.params.region, 'console', async (response) => { - if ( - response.events.includes( - `sites.${data.site.$id}.deployments.${data.deployment.$id}.update` - ) - ) { - deployment = response.payload as Models.Deployment; + const intervalCleanup = () => { + if (skipScreenshotInterval) { + clearInterval(skipScreenshotInterval); + } + }; - const isReady = deployment.status === 'ready'; + const realtimeUnsubscribe = realtime.forConsole( + page.params.region, + 'console', + async (response) => { + if ( + response.events.includes( + `sites.${data.site.$id}.deployments.${data.deployment.$id}.update` + ) + ) { + deployment = response.payload as Models.Deployment; - const isFinished = - isReady && deployment.screenshotLight && deployment.screenshotDark; + const isReady = deployment.status === 'ready'; - // Fallback mechanism - // If ready but not finished for over 30 seconds, go anyway - if (isReady && isFinished) { - clearInterval(skipScreenshotInterval); - goToFinishScreen(); - } else if (isReady) { - skipScreenshotInterval = setInterval(async () => { + const isFinished = + isReady && deployment.screenshotLight && deployment.screenshotDark; + + // Fallback mechanism + // If ready but not finished for over 30 seconds, go anyway + if (isReady && !skipScreenshotInterval) { + skipScreenshotInterval = setInterval(async () => { + goToFinishScreen(); + }, 30000); + } + + if (isReady && isFinished) { + clearInterval(skipScreenshotInterval); goToFinishScreen(); - }, 30000); + } } } - }); + ); + + return () => { + realtimeUnsubscribe(); + intervalCleanup(); + }; }); async function goToFinishScreen() { @@ -95,7 +123,7 @@ - {#if ['processing', 'building', 'finalizing'].includes(data.deployment.status)} + {#if ['processing', 'building', 'finalizing'].includes(effectiveStatus)} Deployment will continue in the background From bb6df5e074e48af5664fb79b640ad1ecc4097443 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Fri, 9 Jan 2026 13:42:46 +0100 Subject: [PATCH 26/45] Simplify method signature --- src/lib/helpers/buildTimeout.ts | 10 +++++----- .../(components)/deploymentCard.svelte | 9 +-------- .../deployment-[deployment]/+page.svelte | 7 +------ .../functions/function-[function]/table.svelte | 4 +--- .../sites/(components)/deploymentActionMenu.svelte | 4 +--- .../sites/(components)/logs.svelte | 9 +-------- .../sites/(components)/logsTimer.svelte | 11 ++--------- .../sites/(components)/siteCard.svelte | 9 +-------- .../sites/create-site/deploying/+page.svelte | 9 +-------- .../deployments/deployment-[deployment]/+page.svelte | 9 +-------- .../sites/site-[site]/deployments/table.svelte | 4 +--- .../sites/site-[site]/deploymentsOverview.svelte | 5 +---- 12 files changed, 17 insertions(+), 73 deletions(-) diff --git a/src/lib/helpers/buildTimeout.ts b/src/lib/helpers/buildTimeout.ts index 9b2544df9..724f82a6a 100644 --- a/src/lib/helpers/buildTimeout.ts +++ b/src/lib/helpers/buildTimeout.ts @@ -22,13 +22,13 @@ function isBuildTimedOut(createdAt: string, status: string, timeoutSeconds: numb * Gets the effective status for a build, considering timeout */ export function getEffectiveBuildStatus( - originalStatus: string, - createdAt: string, - screenshots: Array< - Models.Deployment['screenshotLight'] | Models.Deployment['screenshotDark'] | undefined - >, + deployment: Models.Deployment, consoleVariables: Models.ConsoleVariables | undefined ): string { + const originalStatus = deployment.status; + const createdAt = deployment.$createdAt; + const screenshots = [deployment.screenshotLight, deployment.screenshotDark]; + const timeoutSeconds = getBuildTimeoutSeconds(consoleVariables); if (isBuildTimedOut(createdAt, originalStatus, timeoutSeconds)) { return 'failed'; diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte index 1d18ee85b..bb2f3fda1 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/(components)/deploymentCard.svelte @@ -38,14 +38,7 @@ footer?: Snippet; } = $props(); - let effectiveStatus = $derived( - getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], - $regionalConsoleVariables - ) - ); + let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); let totalSize = $derived(humanFileSize(deployment?.totalSize ?? 0)); diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte index 9676c3302..140524354 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/deployment-[deployment]/+page.svelte @@ -41,12 +41,7 @@ let { data } = $props(); let effectiveStatus = $derived( - getEffectiveBuildStatus( - data.deployment.status, - data.deployment.$createdAt, - [data.deployment.screenshotLight, data.deployment.screenshotDark], - $regionalConsoleVariables - ) + getEffectiveBuildStatus(data.deployment, $regionalConsoleVariables) ); let showDelete = $state(false); let showCancel = $state(false); diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte index a6355710d..a70bf52d5 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/table.svelte @@ -95,9 +95,7 @@ {#snippet children(root)} {#each data.deploymentList.deployments as deployment (deployment.$id)} {@const effectiveStatus = getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], + deployment, $regionalConsoleVariables )} {@const effectiveStatus = getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], + deployment, $regionalConsoleVariables )} {#if !inCard} diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte index ca0e0f62d..03e5a9b49 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte @@ -41,14 +41,7 @@ emptyCopy?: string; } = $props(); - let effectiveStatus = $derived( - getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], - $regionalConsoleVariables - ) - ); + let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); function setCopy() { if (effectiveStatus === 'failed') { diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte index 417da666a..2fa4c6185 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte @@ -7,16 +7,9 @@ import { Layout, Spinner, Typography } from '@appwrite.io/pink-svelte'; - let { status, deployment }: { status: string; deployment: Models.Deployment } = $props(); + let { deployment }: { status: string; deployment: Models.Deployment } = $props(); - let effectiveStatus = $derived( - getEffectiveBuildStatus( - status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], - $regionalConsoleVariables - ) - ); + let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte index 93696adb7..eb392282a 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/siteCard.svelte @@ -42,14 +42,7 @@ footer?: Snippet; } = $props(); - let effectiveStatus = $derived( - getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], - $regionalConsoleVariables - ) - ); + let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); let show = $state(false); const totalSize = $derived(humanFileSize(deployment?.totalSize ?? 0)); diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index b70984418..14dab773d 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -20,14 +20,7 @@ let deployment = $state(data.deployment); let skipScreenshotInterval: ReturnType | null = $state(null); - let effectiveStatus = $derived( - getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], - $regionalConsoleVariables - ) - ); + let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); onMount(() => { const intervalCleanup = () => { diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte index 3f95bd737..23883b059 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte @@ -26,14 +26,7 @@ let { data }: PageProps = $props(); let deployment = $derived(data.deployment); - let effectiveStatus = $derived( - getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], - $regionalConsoleVariables - ) - ); + let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); let showRedeploy = $state(false); let showActivate = $state(false); diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte index 1752e31c3..92c82f8fb 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte @@ -82,9 +82,7 @@ {#snippet children(root)} {#each data.deploymentList.deployments as deployment (deployment.$id)} {@const effectiveStatus = getEffectiveBuildStatus( - deployment.status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], + deployment, $regionalConsoleVariables )} {deployment.$id} - {@const status = deployment.status} {@const effectiveStatus = getEffectiveBuildStatus( - status, - deployment.$createdAt, - [deployment.screenshotLight, deployment.screenshotDark], + deployment, $regionalConsoleVariables )} {#if activeDeployment?.$id === deployment?.$id} From de58db560ed6dab8b3df9d617858fffbf4e1133b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Fri, 9 Jan 2026 13:46:29 +0100 Subject: [PATCH 27/45] use timeout methods correctly --- .../sites/create-site/deploying/+page.svelte | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index 14dab773d..05bd9bee0 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -18,14 +18,14 @@ let { data } = $props(); let deployment = $state(data.deployment); - let skipScreenshotInterval: ReturnType | null = $state(null); + let skipScreenshotTimeout: ReturnType | null = $state(null); let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); onMount(() => { - const intervalCleanup = () => { - if (skipScreenshotInterval) { - clearInterval(skipScreenshotInterval); + const timeoutCleanup = () => { + if (skipScreenshotTimeout) { + clearTimeout(skipScreenshotTimeout); } }; @@ -47,14 +47,14 @@ // Fallback mechanism // If ready but not finished for over 30 seconds, go anyway - if (isReady && !skipScreenshotInterval) { - skipScreenshotInterval = setInterval(async () => { + if (isReady && !skipScreenshotTimeout) { + skipScreenshotTimeout = setTimeout(async () => { goToFinishScreen(); }, 30000); } if (isReady && isFinished) { - clearInterval(skipScreenshotInterval); + clearInterval(skipScreenshotTimeout); goToFinishScreen(); } } @@ -63,7 +63,7 @@ return () => { realtimeUnsubscribe(); - intervalCleanup(); + timeoutCleanup(); }; }); From 71010d8de677d11761a3d72ba62f3bc225956ccc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Fri, 9 Jan 2026 13:50:01 +0100 Subject: [PATCH 28/45] Update logsTimer.svelte --- .../sites/(components)/logsTimer.svelte | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte index 2fa4c6185..79a00f541 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte @@ -7,7 +7,7 @@ import { Layout, Spinner, Typography } from '@appwrite.io/pink-svelte'; - let { deployment }: { status: string; deployment: Models.Deployment } = $props(); + let { deployment }: { deployment: Models.Deployment } = $props(); let effectiveStatus = $derived(getEffectiveBuildStatus(deployment, $regionalConsoleVariables)); From a6f1094ba85f87b16016a0202382b2cc2978ab63 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Fri, 9 Jan 2026 13:54:07 +0100 Subject: [PATCH 29/45] Update +page.svelte --- .../sites/create-site/deploying/+page.svelte | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index 05bd9bee0..aef47d86d 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -54,7 +54,7 @@ } if (isReady && isFinished) { - clearInterval(skipScreenshotTimeout); + clearTimeout(skipScreenshotTimeout); goToFinishScreen(); } } From 9189d006799502f906f085b2fc57b8d440f60a9f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Fri, 9 Jan 2026 13:57:25 +0100 Subject: [PATCH 30/45] Bug fixing --- .../project-[region]-[project]/sites/(components)/logs.svelte | 2 +- .../deployments/deployment-[deployment]/+page.svelte | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte index 03e5a9b49..51c407652 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte @@ -72,7 +72,7 @@ variant="secondary" type={badgeTypeDeployment(effectiveStatus)} /> - + {/if} diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte index 23883b059..c28f5f50b 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/deployment-[deployment]/+page.svelte @@ -88,7 +88,7 @@ hideDivider> - + From 7ab92afc4ace69b697a85d774facd8f66bb41d0f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Matej=20Ba=C4=8Do?= Date: Fri, 9 Jan 2026 14:15:05 +0100 Subject: [PATCH 31/45] AI review fixes --- src/lib/helpers/buildTimeout.ts | 12 +----------- .../sites/create-site/deploying/+page.svelte | 7 ++++++- 2 files changed, 7 insertions(+), 12 deletions(-) diff --git a/src/lib/helpers/buildTimeout.ts b/src/lib/helpers/buildTimeout.ts index 724f82a6a..df10478ee 100644 --- a/src/lib/helpers/buildTimeout.ts +++ b/src/lib/helpers/buildTimeout.ts @@ -27,7 +27,6 @@ export function getEffectiveBuildStatus( ): string { const originalStatus = deployment.status; const createdAt = deployment.$createdAt; - const screenshots = [deployment.screenshotLight, deployment.screenshotDark]; const timeoutSeconds = getBuildTimeoutSeconds(consoleVariables); if (isBuildTimedOut(createdAt, originalStatus, timeoutSeconds)) { @@ -35,16 +34,7 @@ export function getEffectiveBuildStatus( } const isReady = originalStatus === 'ready'; - let hasScreenshot = true; - if (screenshots.length === 0) { - hasScreenshot = false; - } - for (const screenshot of screenshots) { - if (!screenshot) { - hasScreenshot = false; - break; - } - } + const hasScreenshot = deployment.screenshotLight && deployment.screenshotDark; if (isReady && !hasScreenshot) { return 'finalizing'; diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index aef47d86d..b41104e09 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -26,6 +26,7 @@ const timeoutCleanup = () => { if (skipScreenshotTimeout) { clearTimeout(skipScreenshotTimeout); + skipScreenshotTimeout = null; } }; @@ -54,7 +55,11 @@ } if (isReady && isFinished) { - clearTimeout(skipScreenshotTimeout); + if (skipScreenshotTimeout) { + clearTimeout(skipScreenshotTimeout); + skipScreenshotTimeout = null; + } + goToFinishScreen(); } } From 482ef5ba6c59388b5a2723b80315ddd86256837c Mon Sep 17 00:00:00 2001 From: kylewhirl Date: Fri, 9 Jan 2026 08:17:18 -1000 Subject: [PATCH 32/45] Use column.required directly for relationship inputs --- .../rows/columns/types/relationship.svelte | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte index 9cc4bd868..fccc94df4 100644 --- a/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte +++ b/src/routes/(console)/project-[region]-[project]/databases/database-[database]/table-[table]/rows/columns/types/relationship.svelte @@ -297,7 +297,7 @@ Date: Mon, 12 Jan 2026 12:13:50 +0000 Subject: [PATCH 33/45] Initial plan From 91dfb60f79d658fae80d316be5a0994ba7bb2912 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Mon, 12 Jan 2026 12:21:48 +0000 Subject: [PATCH 34/45] Change Permissions to Security in Create function wizard Co-authored-by: HarshMN2345 <127186841+HarshMN2345@users.noreply.github.com> --- .../create-function/template-[template]/permissions.svelte | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/routes/(console)/project-[region]-[project]/functions/create-function/template-[template]/permissions.svelte b/src/routes/(console)/project-[region]-[project]/functions/create-function/template-[template]/permissions.svelte index d512b628f..0930c0e4f 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/create-function/template-[template]/permissions.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/create-function/template-[template]/permissions.svelte @@ -17,7 +17,7 @@ }); -
+
Date: Wed, 14 Jan 2026 13:14:44 +0530 Subject: [PATCH 35/45] some optimization --- .../domains/domain-[domain]/+page.svelte | 160 +++++++----------- 1 file changed, 62 insertions(+), 98 deletions(-) diff --git a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte index 6c3cc5a6a..adcc14747 100644 --- a/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte +++ b/src/routes/(console)/organization-[organization]/domains/domain-[domain]/+page.svelte @@ -78,43 +78,37 @@ {#if data.recordList.total} - {#if $isSmallViewport} - - -
- - - - - {#each presets as preset} - { - toggle(e); - selectedPreset = preset; - showPresetModal = true; - }}>{preset} - {/each} - - - -
- - - - - - Export as .txt - + {:else} + + Import zone file + {/if} + + + +
+ + + + + Export as .txt + +
+ + {#if !$isSmallViewport} +
+ {/if} + +
+ {#if $isSmallViewport} - -
+ +
+ + + + + {#each presets as preset} + { + toggle(e); + selectedPreset = preset; + showPresetModal = true; + }}>{preset} + {/each} + + + +
+ +
+ - - {:else} - - - - - - - - Export as .txt - - - - - - - - - - {#each presets as preset} - { - toggle(e); - selectedPreset = preset; - showPresetModal = true; - }}>{preset} - {/each} - - - - -
- -
-
-
- {/if} +
+
{:else} From 2366a6b3189e0deb06ecabda9fddf21a59303a62 Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Wed, 14 Jan 2026 13:16:41 +0530 Subject: [PATCH 36/45] merge conflicts --- package.json | 12 ++++----- pnpm-lock.yaml | 68 ++++++++++++++++++-------------------------------- 2 files changed, 29 insertions(+), 51 deletions(-) diff --git a/package.json b/package.json index 120ca71ca..131b11e21 100644 --- a/package.json +++ b/package.json @@ -22,12 +22,13 @@ }, "dependencies": { "@ai-sdk/svelte": "^1.1.24", - "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f", + "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755", "@appwrite.io/pink-icons": "0.25.0", - "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920", + "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc", "@appwrite.io/pink-legacy": "^1.0.3", - "@appwrite.io/pink-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920", + "@appwrite.io/pink-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc", "@faker-js/faker": "^9.9.0", + "@plausible-analytics/tracker": "^0.4.4", "@popperjs/core": "^2.11.8", "@sentry/sveltekit": "^8.38.0", "@stripe/stripe-js": "^3.5.0", @@ -40,11 +41,8 @@ "deep-equal": "^2.2.3", "echarts": "^5.6.0", "ignore": "^6.0.2", - "install": "^0.13.0", "nanoid": "^5.1.5", "nanotar": "^0.1.1", - "plausible-tracker": "^0.3.9", - "pnpm": "^10.27.0", "pretty-bytes": "^6.1.1", "prismjs": "^1.30.0", "remarkable": "^2.0.1", @@ -102,4 +100,4 @@ ] }, "packageManager": "pnpm@10.20.0" -} +} \ No newline at end of file diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 40ef93c38..c112c59e6 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -12,23 +12,26 @@ importers: specifier: ^1.1.24 version: 1.1.24(svelte@5.25.3)(zod@3.24.3) '@appwrite.io/console': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f - version: https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755 + version: https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755 '@appwrite.io/pink-icons': specifier: 0.25.0 version: 0.25.0 '@appwrite.io/pink-icons-svelte': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920 - version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920(svelte@5.25.3) + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc + version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc(svelte@5.25.3) '@appwrite.io/pink-legacy': specifier: ^1.0.3 version: 1.0.3 '@appwrite.io/pink-svelte': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920 - version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920(svelte@5.25.3) + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc + version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc(svelte@5.25.3) '@faker-js/faker': specifier: ^9.9.0 version: 9.9.0 + '@plausible-analytics/tracker': + specifier: ^0.4.4 + version: 0.4.4 '@popperjs/core': specifier: ^2.11.8 version: 2.11.8 @@ -65,21 +68,12 @@ importers: ignore: specifier: ^6.0.2 version: 6.0.2 - install: - specifier: ^0.13.0 - version: 0.13.0 nanoid: specifier: ^5.1.5 version: 5.1.5 nanotar: specifier: ^0.1.1 version: 0.1.1 - plausible-tracker: - specifier: ^0.3.9 - version: 0.3.9 - pnpm: - specifier: ^10.27.0 - version: 10.27.0 pretty-bytes: specifier: ^6.1.1 version: 6.1.1 @@ -278,17 +272,17 @@ packages: '@analytics/type-utils@0.6.2': resolution: {integrity: sha512-TD+xbmsBLyYy/IxFimW/YL/9L2IEnM7/EoV9Aeh56U64Ify8o27HJcKjo38XY9Tcn0uOq1AX3thkKgvtWvwFQg==} - '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f} - version: 1.10.0 + '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755} + version: 2.1.0 '@appwrite.io/pink-icons-svelte@2.0.0-RC.1': resolution: {integrity: sha512-iLFlV55hj8mGuAbmxJGenxN5RaZMmVT4GJb9dv/MP1xBAtYibFq7JvBcxm18qV2KU8c31Rntf+Ub4GL7HwqTYg==} peerDependencies: svelte: ^4.0.0 - '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920} + '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc} version: 2.0.0-RC.1 peerDependencies: svelte: ^4.0.0 @@ -302,8 +296,8 @@ packages: '@appwrite.io/pink-legacy@1.0.3': resolution: {integrity: sha512-GGde5fmPhs+s6/3aFeMPc/kKADG/gTFkYQSy6oBN8pK0y0XNCLrZZgBv+EBbdhwdtqVEWXa0X85Mv9w7jcIlwQ==} - '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920} + '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc} version: 2.0.0-RC.2 peerDependencies: svelte: ^4.0.0 @@ -1014,6 +1008,9 @@ packages: resolution: {integrity: sha512-dfUnCxiN9H4ap84DvD2ubjw+3vUNpstxa0TneY/Paat8a3R4uQZDLSvWjmznAY/DoahqTHl9V46HF/Zs3F29pg==} engines: {node: '>= 10.0.0'} + '@plausible-analytics/tracker@0.4.4': + resolution: {integrity: sha512-fz0NOYUEYXtg1TBaPEEvtcBq3FfmLFuTe1VZw4M8sTWX129br5dguu3M15+plOQnc181ShYe67RfwhKgK89VnA==} + '@playwright/test@1.56.1': resolution: {integrity: sha512-vSMYtL/zOcFpvJCW71Q/OEGQb7KYBPAdKh35WNSkaZA75JlAO8ED8UN6GUNTm3drWomcbcqRPFqQbLae8yBTdg==} engines: {node: '>=18'} @@ -2476,10 +2473,6 @@ packages: resolution: {integrity: sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==} engines: {node: '>=8'} - install@0.13.0: - resolution: {integrity: sha512-zDml/jzr2PKU9I8J/xyZBQn8rPCAY//UOYNmR01XwNwyfhEWObo2SWfSl1+0tm1u6PhxLwDnfsT/6jB7OUxqFA==} - engines: {node: '>= 0.10'} - internal-slot@1.1.0: resolution: {integrity: sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw==} engines: {node: '>= 0.4'} @@ -2910,10 +2903,6 @@ packages: resolution: {integrity: sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==} engines: {node: '>=12'} - plausible-tracker@0.3.9: - resolution: {integrity: sha512-hMhneYm3GCPyQon88SZrVJx+LlqhM1kZFQbuAgXPoh/Az2YvO1B6bitT9qlhpiTdJlsT5lsr3gPmzoVjb5CDXA==} - engines: {node: '>=10'} - playwright-core@1.56.1: resolution: {integrity: sha512-hutraynyn31F+Bifme+Ps9Vq59hKuUCz7H1kDOcBs+2oGguKkWTU50bBWrtz34OUWmIwpBTWDxaRPXrIXkgvmQ==} engines: {node: '>=18'} @@ -2924,11 +2913,6 @@ packages: engines: {node: '>=18'} hasBin: true - pnpm@10.27.0: - resolution: {integrity: sha512-ctaZ2haxF5wUup5k3HHJpAmIy9xlwmTLDkidt96RfyDc9NZNhyNiXylpulLUt+KhFwaC2awqXcrqq3MrfhbwSg==} - engines: {node: '>=18.12'} - hasBin: true - popmotion@11.0.5: resolution: {integrity: sha512-la8gPM1WYeFznb/JqF4GiTkRRPZsfaj2+kCxqQgr2MJylMmIKUwBfWW8Wa5fml/8gmtlD5yI01MP1QCZPWmppA==} @@ -3838,13 +3822,13 @@ snapshots: '@analytics/type-utils@0.6.2': {} - '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@f21fc7f': {} + '@appwrite.io/console@https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755': {} '@appwrite.io/pink-icons-svelte@2.0.0-RC.1(svelte@5.25.3)': dependencies: svelte: 5.25.3 - '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@cfa2920(svelte@5.25.3)': + '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc(svelte@5.25.3)': dependencies: svelte: 5.25.3 @@ -3857,7 +3841,7 @@ snapshots: '@appwrite.io/pink-icons': 1.0.0 the-new-css-reset: 1.11.3 - '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@cfa2920(svelte@5.25.3)': + '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc(svelte@5.25.3)': dependencies: '@appwrite.io/pink-icons-svelte': 2.0.0-RC.1(svelte@5.25.3) '@floating-ui/dom': 1.6.13 @@ -4590,6 +4574,8 @@ snapshots: '@parcel/watcher-win32-x64': 2.5.1 optional: true + '@plausible-analytics/tracker@0.4.4': {} + '@playwright/test@1.56.1': dependencies: playwright: 1.56.1 @@ -6287,8 +6273,6 @@ snapshots: indent-string@4.0.0: {} - install@0.13.0: {} - internal-slot@1.1.0: dependencies: es-errors: 1.3.0 @@ -6692,8 +6676,6 @@ snapshots: picomatch@4.0.3: {} - plausible-tracker@0.3.9: {} - playwright-core@1.56.1: {} playwright@1.56.1: @@ -6702,8 +6684,6 @@ snapshots: optionalDependencies: fsevents: 2.3.2 - pnpm@10.27.0: {} - popmotion@11.0.5: dependencies: framesync: 6.1.2 From 2458eae65b294d8ce84de04eda170e095a6be592 Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Wed, 14 Jan 2026 13:32:26 +0530 Subject: [PATCH 37/45] build fail --- package.json | 4 ++-- pnpm-lock.yaml | 20 ++++++++++---------- 2 files changed, 12 insertions(+), 12 deletions(-) diff --git a/package.json b/package.json index 131b11e21..5f7f70072 100644 --- a/package.json +++ b/package.json @@ -24,9 +24,9 @@ "@ai-sdk/svelte": "^1.1.24", "@appwrite.io/console": "https://pkg.vc/-/@appwrite/@appwrite.io/console@9c55755", "@appwrite.io/pink-icons": "0.25.0", - "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc", + "@appwrite.io/pink-icons-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@bbad65f", "@appwrite.io/pink-legacy": "^1.0.3", - "@appwrite.io/pink-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc", + "@appwrite.io/pink-svelte": "https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@bbad65f", "@faker-js/faker": "^9.9.0", "@plausible-analytics/tracker": "^0.4.4", "@popperjs/core": "^2.11.8", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index c112c59e6..23cbb7f83 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -18,14 +18,14 @@ importers: specifier: 0.25.0 version: 0.25.0 '@appwrite.io/pink-icons-svelte': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc - version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc(svelte@5.25.3) + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@bbad65f + version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@bbad65f(svelte@5.25.3) '@appwrite.io/pink-legacy': specifier: ^1.0.3 version: 1.0.3 '@appwrite.io/pink-svelte': - specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc - version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc(svelte@5.25.3) + specifier: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@bbad65f + version: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@bbad65f(svelte@5.25.3) '@faker-js/faker': specifier: ^9.9.0 version: 9.9.0 @@ -281,8 +281,8 @@ packages: peerDependencies: svelte: ^4.0.0 - '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc} + '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@bbad65f': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@bbad65f} version: 2.0.0-RC.1 peerDependencies: svelte: ^4.0.0 @@ -296,8 +296,8 @@ packages: '@appwrite.io/pink-legacy@1.0.3': resolution: {integrity: sha512-GGde5fmPhs+s6/3aFeMPc/kKADG/gTFkYQSy6oBN8pK0y0XNCLrZZgBv+EBbdhwdtqVEWXa0X85Mv9w7jcIlwQ==} - '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc': - resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc} + '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@bbad65f': + resolution: {tarball: https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@bbad65f} version: 2.0.0-RC.2 peerDependencies: svelte: ^4.0.0 @@ -3828,7 +3828,7 @@ snapshots: dependencies: svelte: 5.25.3 - '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@865e2fc(svelte@5.25.3)': + '@appwrite.io/pink-icons-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-icons-svelte@bbad65f(svelte@5.25.3)': dependencies: svelte: 5.25.3 @@ -3841,7 +3841,7 @@ snapshots: '@appwrite.io/pink-icons': 1.0.0 the-new-css-reset: 1.11.3 - '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@865e2fc(svelte@5.25.3)': + '@appwrite.io/pink-svelte@https://pkg.vc/-/@appwrite/@appwrite.io/pink-svelte@bbad65f(svelte@5.25.3)': dependencies: '@appwrite.io/pink-icons-svelte': 2.0.0-RC.1(svelte@5.25.3) '@floating-ui/dom': 1.6.13 From fb784f7aef480e81fa3fb9735521a51bd0c8a319 Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Wed, 14 Jan 2026 13:37:24 +0530 Subject: [PATCH 38/45] lint --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 5f7f70072..7b00655cd 100644 --- a/package.json +++ b/package.json @@ -100,4 +100,4 @@ ] }, "packageManager": "pnpm@10.20.0" -} \ No newline at end of file +} From 36f5ba408bcf30789cb4761214ffee2e5b4118dc Mon Sep 17 00:00:00 2001 From: Hemachandar <132386067+hmacr@users.noreply.github.com> Date: Wed, 14 Jan 2026 18:16:49 +0530 Subject: [PATCH 39/45] Handle NS record flow and auto-verification of sub-domains (#2784) * Handle NS record flow and auto-verification of sub-domains * shadow * text * Use updated rule for label * Org domain * Missing status for nameserver table * feedback * lint * remove unnecessary defaults --- .../components/domains/nameserverTable.svelte | 31 ++++++-- src/lib/components/domains/recordTable.svelte | 8 +- .../domains/+page.svelte | 4 +- .../domains/add-domain/+page.svelte | 12 ++- .../domains/recordsCard.svelte | 8 +- .../domains/retryDomainModal.svelte | 27 ++++--- .../domains/add-domain/+page.svelte | 26 +++++-- .../add-domain/verify-[domain]/+page.svelte | 73 +++++++++--------- .../domains/recordsCard.svelte | 4 +- .../domains/retryDomainModal.svelte | 55 +++++++------- .../function-[function]/domains/store.ts | 4 +- .../function-[function]/domains/table.svelte | 2 +- .../settings/domains/add-domain/+page.svelte | 26 +++++-- .../add-domain/verify-[domain]/+page.svelte | 71 ++++++++---------- .../settings/domains/retryDomainModal.svelte | 55 +++++++------- .../settings/domains/table.svelte | 4 +- .../domains/add-domain/+page.svelte | 26 +++++-- .../add-domain/verify-[domain]/+page.svelte | 74 +++++++++---------- .../domains/retryDomainModal.svelte | 55 +++++++------- .../sites/site-[site]/domains/store.ts | 4 +- .../sites/site-[site]/domains/table.svelte | 2 +- 21 files changed, 320 insertions(+), 251 deletions(-) diff --git a/src/lib/components/domains/nameserverTable.svelte b/src/lib/components/domains/nameserverTable.svelte index a08de4208..66c7c165d 100644 --- a/src/lib/components/domains/nameserverTable.svelte +++ b/src/lib/components/domains/nameserverTable.svelte @@ -3,8 +3,15 @@ import { Badge, Layout, Typography, Table, InteractiveText } from '@appwrite.io/pink-svelte'; - export let domain: string; - export let verified = undefined; + let { + domain, + verified, + ruleStatus + }: { + domain: string; + verified?: boolean; + ruleStatus?: 'created' | 'verifying' | 'unverified' | 'verified'; + } = $props(); const nameserverList = $regionalConsoleVariables?._APP_DOMAINS_NAMESERVERS ? $regionalConsoleVariables?._APP_DOMAINS_NAMESERVERS?.split(',') @@ -16,14 +23,24 @@ {domain} - {#if verified === true} - - {:else if verified === false} - + {#if verified !== undefined} + {#if ruleStatus === 'created'} + + {:else if ruleStatus === 'verifying'} + + {:else if ruleStatus === 'unverified'} + + {:else if verified === true} + + {/if} {/if} - Add the following nameservers on your DNS provider. Note that changes may take up to 48 + Add the following nameservers on your DNS provider. Note that DNS changes may take up to 48 hours to propagate fully. diff --git a/src/lib/components/domains/recordTable.svelte b/src/lib/components/domains/recordTable.svelte index 6dc145e35..dd0c305e7 100644 --- a/src/lib/components/domains/recordTable.svelte +++ b/src/lib/components/domains/recordTable.svelte @@ -14,10 +14,10 @@ let { domain, - verified = undefined, + verified, variant, service = 'general', - ruleStatus = undefined, + ruleStatus, onNavigateToNameservers = () => {}, onNavigateToA = () => {}, onNavigateToAAAA = () => {} @@ -115,7 +115,9 @@ {variant.toUpperCase()} - {subdomain || '@'} + + + diff --git a/src/routes/(console)/organization-[organization]/domains/+page.svelte b/src/routes/(console)/organization-[organization]/domains/+page.svelte index ec6c271e0..477786e8f 100644 --- a/src/routes/(console)/organization-[organization]/domains/+page.svelte +++ b/src/routes/(console)/organization-[organization]/domains/+page.svelte @@ -93,9 +93,9 @@ {#if !isDomainVerified(domain)} + size="xs" /> {/if} {:else if column.id === 'registrar'} diff --git a/src/routes/(console)/organization-[organization]/domains/add-domain/+page.svelte b/src/routes/(console)/organization-[organization]/domains/add-domain/+page.svelte index c6953c2e3..a1066a09a 100644 --- a/src/routes/(console)/organization-[organization]/domains/add-domain/+page.svelte +++ b/src/routes/(console)/organization-[organization]/domains/add-domain/+page.svelte @@ -1,6 +1,7 @@ @@ -125,7 +117,7 @@ - {data.proxyRule.domain} + {proxyRule.domain} @@ -172,14 +164,17 @@ {#if selectedTab === 'nameserver'} - + {:else} (selectedTab = 'nameserver')} onNavigateToA={() => (selectedTab = 'a')} onNavigateToAAAA={() => (selectedTab = 'aaaa')} /> diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/recordsCard.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/recordsCard.svelte index 07a2da2c4..55e9b5a95 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/recordsCard.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/recordsCard.svelte @@ -25,8 +25,8 @@ - Add the following nameservers on your DNS provider. Note that changes may take - up to 48 hours to propagate fully. + Add the following nameservers on your DNS provider. Note that DNS changes may + take up to 48 hours to propagate fully. diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/retryDomainModal.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/retryDomainModal.svelte index 391321a9b..bc90344d6 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/retryDomainModal.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/retryDomainModal.svelte @@ -13,13 +13,16 @@ import { Divider, Tabs } from '@appwrite.io/pink-svelte'; import NameserverTable from '$lib/components/domains/nameserverTable.svelte'; import RecordTable from '$lib/components/domains/recordTable.svelte'; + import { getApexDomain } from '$lib/helpers/tlds'; let { show = $bindable(false), - selectedProxyRule + selectedProxyRule, + domainsList }: { show: boolean; selectedProxyRule: Models.ProxyRule; + domainsList?: Models.DomainsList; } = $props(); const showCNAMETab = $derived( @@ -40,43 +43,42 @@ let selectedTab = $state<'cname' | 'nameserver' | 'a' | 'aaaa'>(getDefaultTab()); let error = $state(null); - let verified = $state(false); + let verified: boolean | undefined = $state(undefined); function getDefaultTab() { return showCNAMETab ? 'cname' : showATab ? 'a' : showAAAATab ? 'aaaa' : 'nameserver'; } async function retryProxyRule() { + error = null; + verified = undefined; + try { - error = null; - const proxyRule = await sdk + const apexDomain = getApexDomain(selectedProxyRule.domain); + const domain = domainsList?.domains.find((d) => d.domain === apexDomain); + if (isCloud && domain) { + await sdk.forConsole.domains.updateNameservers({ + domainId: domain.$id + }); + } + } catch { + // Ignore error + } + + try { + selectedProxyRule = await sdk .forProject(page.params.region, page.params.project) .proxy.updateRuleVerification({ ruleId: selectedProxyRule.$id }); - verified = proxyRule.status === 'verified'; await invalidate(Dependencies.FUNCTION_DOMAINS); - - // This means domain verification using DNS records hasn't succeeded and the rule is still in initial state. - if (proxyRule.status === 'created') { - throw new Error( - 'Domain verification failed. Please check your domain settings or try again later' - ); - } - - if (verified) { - addNotification({ - type: 'success', - message: `${selectedProxyRule.domain} has been verified` - }); - } else { - addNotification({ - type: 'info', - message: 'Verification in progress' - }); - } show = false; + addNotification({ + type: 'success', + message: 'Domain verified successfully' + }); trackEvent(Submit.DomainUpdateVerification); } catch (e) { + verified = false; error = e.message ?? 'Domain verification failed. Please check your domain settings or try again later'; @@ -130,7 +132,10 @@ {#if selectedTab === 'nameserver'} - + {:else} ([ title: 'Domain', type: 'string', format: 'string', - width: { min: 300 } + width: { min: 600 } }, { id: 'target', title: 'Target', type: 'string', - width: { min: 120, max: 400 } + width: { min: 160, max: 400 } }, { diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/table.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/table.svelte index 83daf1ffe..6f1693571 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/domains/table.svelte @@ -222,7 +222,7 @@ {/if} {#if showRetry} - + {/if} {#if showLogs} diff --git a/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/+page.svelte b/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/+page.svelte index 2f4250d19..eb2b2a214 100644 --- a/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/+page.svelte @@ -30,16 +30,24 @@ async function addDomain() { const apexDomain = getApexDomain(domainName); - let domain = data.domainsList.domains.find((d: Models.Domain) => d.domain === apexDomain); + const domain = data.domainsList.domains.find((d: Models.Domain) => d.domain === apexDomain); if (apexDomain && !domain && isCloud) { try { - domain = await sdk.forConsole.domains.create({ + await sdk.forConsole.domains.create({ teamId: $project.teamId, domain: apexDomain }); } catch (error) { - // Apex domain creation error needs to be silent. + // apex might already be added on organization level, skip. + const alreadyAdded = error?.type === 'domain_already_exists'; + if (!alreadyAdded) { + addNotification({ + type: 'error', + message: error.message + }); + return; + } } } @@ -47,12 +55,18 @@ const rule = await sdk .forProject(page.params.region, page.params.project) .proxy.createAPIRule({ domain: domainName.toLocaleLowerCase() }); - if (rule?.status === 'verified') { + + await invalidate(Dependencies.DOMAINS); + + const verified = rule?.status !== 'created'; + if (verified) { + addNotification({ + type: 'success', + message: 'Domain verified successfully' + }); await goto(routeBase); - await invalidate(Dependencies.DOMAINS); } else { await goto(`${routeBase}/add-domain/verify-${domainName}?rule=${rule.$id}`); - await invalidate(Dependencies.DOMAINS); } } catch (error) { addNotification({ diff --git a/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/verify-[domain]/+page.svelte b/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/verify-[domain]/+page.svelte index f0312de38..93f725eb0 100644 --- a/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/verify-[domain]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/settings/domains/add-domain/verify-[domain]/+page.svelte @@ -11,7 +11,6 @@ } from '@appwrite.io/pink-svelte'; import { Button, Form } from '$lib/elements/forms'; import { sdk } from '$lib/stores/sdk'; - import { organization } from '$lib/stores/organization'; import { addNotification } from '$lib/stores/notifications'; import { goto, invalidate } from '$app/navigation'; import { Dependencies } from '$lib/constants'; @@ -23,6 +22,7 @@ import NameserverTable from '$lib/components/domains/nameserverTable.svelte'; import RecordTable from '$lib/components/domains/recordTable.svelte'; import { regionalConsoleVariables } from '$routes/(console)/project-[region]-[project]/store'; + import { getApexDomain } from '$lib/helpers/tlds.js'; let { data } = $props(); @@ -44,8 +44,8 @@ ); const showNSTab = isCloud; + let proxyRule = $derived(data.proxyRule); let selectedTab = $state<'cname' | 'nameserver' | 'a' | 'aaaa'>(getDefaultTab()); - const routeBase = `${base}/project-${page.params.region}-${page.params.project}/settings/domains`; let verified: boolean | undefined = $state(undefined); const isSubmitting = writable(false); @@ -55,43 +55,31 @@ } async function verify() { - const isNewDomain = - data.domainsList.domains.find((rule) => rule.domain === data.proxyRule.domain) === - undefined; + verified = undefined; + try { - if (selectedTab !== 'nameserver') { - const ruleData = await sdk - .forProject(page.params.region, page.params.project) - .proxy.updateRuleVerification({ ruleId }); - verified = ruleData.status === 'verified'; - - // This means domain verification using DNS records hasn't succeeded and the rule is still in initial state. - if (ruleData.status === 'created') { - throw new Error( - 'Domain verification failed. Please check your domain settings or try again later' - ); - } - } else if (isNewDomain && isCloud) { - const domainData = await sdk.forConsole.domains.create({ - teamId: $organization.$id, - domain: data.proxyRule.domain - }); - verified = domainData.nameservers.toLowerCase() === 'appwrite'; - } - - if (verified) { - addNotification({ - type: 'success', - message: 'Domain added successfully' - }); - } else { - addNotification({ - type: 'info', - message: 'Verification in progress' + const apexDomain = getApexDomain(proxyRule.domain); + const domain = data.domainsList.domains.find((d) => d.domain === apexDomain); + if (isCloud && domain) { + await sdk.forConsole.domains.updateNameservers({ + domainId: domain.$id }); } - await goto(routeBase); + } catch (error) { + // Ignore error + } + + try { + proxyRule = await sdk + .forProject(page.params.region, page.params.project) + .proxy.updateRuleVerification({ ruleId }); + await invalidate(Dependencies.DOMAINS); + await goto(routeBase); + addNotification({ + type: 'success', + message: 'Domain verified successfully' + }); } catch (error) { verified = false; isSubmitting.set(false); @@ -108,7 +96,7 @@ .forProject(page.params.region, page.params.project) .proxy.deleteRule({ ruleId }); } - await goto(`${routeBase}/add-domain?domain=${data.proxyRule.domain}`); + await goto(`${routeBase}/add-domain?domain=${proxyRule.domain}`); } @@ -125,7 +113,7 @@ - {data.proxyRule.domain} + {proxyRule.domain} @@ -172,14 +160,17 @@ {#if selectedTab === 'nameserver'} - + {:else} (selectedTab = 'nameserver')} onNavigateToA={() => (selectedTab = 'a')} onNavigateToAAAA={() => (selectedTab = 'aaaa')} /> diff --git a/src/routes/(console)/project-[region]-[project]/settings/domains/retryDomainModal.svelte b/src/routes/(console)/project-[region]-[project]/settings/domains/retryDomainModal.svelte index bd77890a8..1098b8d3f 100644 --- a/src/routes/(console)/project-[region]-[project]/settings/domains/retryDomainModal.svelte +++ b/src/routes/(console)/project-[region]-[project]/settings/domains/retryDomainModal.svelte @@ -13,13 +13,16 @@ import { Divider, Tabs } from '@appwrite.io/pink-svelte'; import NameserverTable from '$lib/components/domains/nameserverTable.svelte'; import RecordTable from '$lib/components/domains/recordTable.svelte'; + import { getApexDomain } from '$lib/helpers/tlds'; let { show = $bindable(), - selectedProxyRule + selectedProxyRule, + domainsList }: { show: boolean; selectedProxyRule: Models.ProxyRule; + domainsList?: Models.DomainsList; } = $props(); const showCNAMETab = $derived( @@ -40,43 +43,42 @@ let selectedTab = $state<'cname' | 'nameserver' | 'a' | 'aaaa'>(getDefaultTab()); let error = $state(null); - let verified = $state(false); + let verified: boolean | undefined = $state(undefined); function getDefaultTab() { return showCNAMETab ? 'cname' : showATab ? 'a' : showAAAATab ? 'aaaa' : 'nameserver'; } async function retryDomain() { + error = null; + verified = undefined; + try { - error = null; - const proxyRule = await sdk + const apexDomain = getApexDomain(selectedProxyRule.domain); + const domain = domainsList?.domains.find((d) => d.domain === apexDomain); + if (isCloud && domain) { + await sdk.forConsole.domains.updateNameservers({ + domainId: domain.$id + }); + } + } catch { + // Ignore error + } + + try { + selectedProxyRule = await sdk .forProject(page.params.region, page.params.project) .proxy.updateRuleVerification({ ruleId: selectedProxyRule.$id }); - verified = proxyRule.status === 'verified'; await invalidate(Dependencies.DOMAINS); - - // This means domain verification using DNS records hasn't succeeded and the rule is still in initial state. - if (proxyRule.status === 'created') { - throw new Error( - 'Domain verification failed. Please check your domain settings or try again later' - ); - } - - if (verified) { - addNotification({ - type: 'success', - message: `${selectedProxyRule.domain} has been verified` - }); - } else { - addNotification({ - type: 'info', - message: 'Verification in progress' - }); - } show = false; + addNotification({ + type: 'success', + message: 'Domain verified successfully' + }); trackEvent(Submit.DomainUpdateVerification); } catch (e) { + verified = false; error = e.message ?? 'Domain verification failed. Please check your domain settings or try again later'; @@ -130,7 +132,10 @@ {#if selectedTab === 'nameserver'} - + {:else} + {/if} {#if showLogs} diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/+page.svelte index b4288a1f9..90f8c679d 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/+page.svelte @@ -58,16 +58,24 @@ async function addDomain() { const apexDomain = getApexDomain(domainName); const isSiteDomain = domainName.endsWith($regionalConsoleVariables._APP_DOMAIN_SITES); - let domain = data.domainsList.domains.find((d) => d.domain === apexDomain); + const domain = data.domainsList.domains.find((d) => d.domain === apexDomain); if (isCloud && apexDomain && !domain && !isSiteDomain) { try { - domain = await sdk.forConsole.domains.create({ + await sdk.forConsole.domains.create({ teamId: $project.teamId, domain: apexDomain }); } catch (error) { - // Apex domain creation error needs to be silent. + // apex might already be added on organization level, skip. + const alreadyAdded = error?.type === 'domain_already_exists'; + if (!alreadyAdded) { + addNotification({ + type: 'error', + message: error.message + }); + return; + } } } @@ -99,12 +107,18 @@ siteId: page.params.site }); } - if (rule?.status === 'verified') { + + await invalidate(Dependencies.SITES_DOMAINS); + + const verified = rule?.status !== 'created'; + if (verified) { + addNotification({ + type: 'success', + message: 'Domain verified successfully' + }); await goto(routeBase); - await invalidate(Dependencies.SITES_DOMAINS); } else { await goto(`${routeBase}/add-domain/verify-${domainName}?rule=${rule.$id}`); - await invalidate(Dependencies.SITES_DOMAINS); } } catch (error) { addNotification({ diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/verify-[domain]/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/verify-[domain]/+page.svelte index 80fba1842..83eb4f33d 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/verify-[domain]/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/add-domain/verify-[domain]/+page.svelte @@ -11,7 +11,6 @@ } from '@appwrite.io/pink-svelte'; import { Button, Form } from '$lib/elements/forms'; import { sdk } from '$lib/stores/sdk'; - import { organization } from '$lib/stores/organization'; import { addNotification } from '$lib/stores/notifications'; import { goto, invalidate } from '$app/navigation'; import { Dependencies } from '$lib/constants'; @@ -23,6 +22,7 @@ import RecordTable from '$lib/components/domains/recordTable.svelte'; import NameserverTable from '$lib/components/domains/nameserverTable.svelte'; import { regionalConsoleVariables } from '$routes/(console)/project-[region]-[project]/store'; + import { getApexDomain } from '$lib/helpers/tlds.js'; let { data } = $props(); @@ -44,6 +44,7 @@ ); const showNSTab = isCloud; + let proxyRule = $derived(data.proxyRule); let selectedTab = $state<'cname' | 'nameserver' | 'a' | 'aaaa'>(getDefaultTab()); let routeBase = `${base}/project-${page.params.region}-${page.params.project}/sites/site-${page.params.site}/domains`; let verified: boolean | undefined = $state(undefined); @@ -54,44 +55,34 @@ } async function verify() { - const isNewDomain = - data.domainsList.domains.findIndex((rule) => rule.domain === data.proxyRule.domain) === - -1; + verified = undefined; + try { - if (selectedTab !== 'nameserver') { - const ruleData = await sdk - .forProject(page.params.region, page.params.project) - .proxy.updateRuleVerification({ ruleId }); - verified = ruleData.status === 'verified'; - - // This means domain verification using DNS records hasn't succeeded and the rule is still in initial state. - if (ruleData.status === 'created') { - throw new Error( - 'Domain verification failed. Please check your domain settings or try again later' - ); - } - } else if (isNewDomain && isCloud) { - const domainData = await sdk.forConsole.domains.create({ - teamId: $organization.$id, - domain: data.proxyRule.domain - }); - verified = domainData.nameservers.toLowerCase() === 'appwrite'; - } - - if (verified) { - addNotification({ - type: 'success', - message: 'Domain added successfully' - }); - } else { - addNotification({ - type: 'info', - message: 'Verification in progress' + const apexDomain = getApexDomain(proxyRule.domain); + const domain = data.domainsList.domains.find((d) => d.domain === apexDomain); + if (isCloud && domain) { + await sdk.forConsole.domains.updateNameservers({ + domainId: domain.$id }); } + } catch (error) { + // Ignore error + } + + try { + proxyRule = await sdk + .forProject(page.params.region, page.params.project) + .proxy.updateRuleVerification({ ruleId }); + + await Promise.all([ + invalidate(Dependencies.DOMAINS), + invalidate(Dependencies.SITES_DOMAINS) + ]); await goto(routeBase); - await invalidate(Dependencies.DOMAINS); - await invalidate(Dependencies.SITES_DOMAINS); + addNotification({ + type: 'success', + message: 'Domain verified successfully' + }); } catch (error) { verified = false; isSubmitting.set(false); @@ -108,7 +99,7 @@ .forProject(page.params.region, page.params.project) .proxy.deleteRule({ ruleId }); } - await goto(`${routeBase}/add-domain?domain=${data.proxyRule.domain}`); + await goto(`${routeBase}/add-domain?domain=${proxyRule.domain}`); } @@ -125,7 +116,7 @@ - {data.proxyRule.domain} + {proxyRule.domain} @@ -172,14 +163,17 @@ {#if selectedTab === 'nameserver'} - + {:else} (selectedTab = 'nameserver')} onNavigateToA={() => (selectedTab = 'a')} onNavigateToAAAA={() => (selectedTab = 'aaaa')} /> diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/retryDomainModal.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/retryDomainModal.svelte index 6e36ac2ec..56fa02b6d 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/retryDomainModal.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/retryDomainModal.svelte @@ -13,13 +13,16 @@ import NameserverTable from '$lib/components/domains/nameserverTable.svelte'; import RecordTable from '$lib/components/domains/recordTable.svelte'; import { regionalConsoleVariables } from '$routes/(console)/project-[region]-[project]/store'; + import { getApexDomain } from '$lib/helpers/tlds'; let { show = $bindable(false), - selectedProxyRule + selectedProxyRule, + domainsList }: { show: boolean; selectedProxyRule: Models.ProxyRule; + domainsList?: Models.DomainsList; } = $props(); const showCNAMETab = $derived( @@ -40,43 +43,42 @@ let selectedTab = $state<'cname' | 'nameserver' | 'a' | 'aaaa'>(getDefaultTab()); let error = $state(null); - let verified = $state(false); + let verified: boolean | undefined = $state(undefined); function getDefaultTab() { return showCNAMETab ? 'cname' : showATab ? 'a' : showAAAATab ? 'aaaa' : 'nameserver'; } async function retryDomain() { + error = null; + verified = undefined; + try { - error = null; - const proxyRule = await sdk + const apexDomain = getApexDomain(selectedProxyRule.domain); + const domain = domainsList?.domains.find((d) => d.domain === apexDomain); + if (isCloud && domain) { + await sdk.forConsole.domains.updateNameservers({ + domainId: domain.$id + }); + } + } catch { + // Ignore error + } + + try { + selectedProxyRule = await sdk .forProject(page.params.region, page.params.project) .proxy.updateRuleVerification({ ruleId: selectedProxyRule.$id }); - verified = proxyRule.status === 'verified'; await invalidate(Dependencies.SITES_DOMAINS); - - // This means domain verification using DNS records hasn't succeeded and the rule is still in initial state. - if (proxyRule.status === 'created') { - throw new Error( - 'Domain verification failed. Please check your domain settings or try again later' - ); - } - - if (verified) { - addNotification({ - type: 'success', - message: `${selectedProxyRule.domain} has been verified` - }); - } else { - addNotification({ - type: 'info', - message: 'Verification in progress' - }); - } show = false; + addNotification({ + type: 'success', + message: 'Domain verified successfully' + }); trackEvent(Submit.DomainUpdateVerification); } catch (e) { + verified = false; error = e.message ?? 'Domain verification failed. Please check your domain settings or try again later'; @@ -130,7 +132,10 @@ {#if selectedTab === 'nameserver'} - + {:else} ([ title: 'Domain', type: 'string', format: 'string', - width: { min: 300 } + width: { min: 600 } }, { id: 'target', title: 'Target', type: 'string', - width: { min: 120, max: 400 } + width: { min: 160, max: 400 } }, { diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/table.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/table.svelte index a3921aeaa..b1a1b4447 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/domains/table.svelte @@ -222,7 +222,7 @@ {/if} {#if showRetry} - + {/if} {#if showLogs} From c8f397c656f11398cad55343ce75e464f7452ded Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Fri, 16 Jan 2026 15:12:35 +0530 Subject: [PATCH 40/45] Add execution timeout helper to show stuck executions as failed Similar to buildTimeout.ts, this adds executionTimeout.ts to detect executions stuck in 'waiting' or 'processing' state beyond the function's configured timeout, displaying them as 'failed'. --- src/lib/helpers/executionTimeout.ts | 37 +++++++++++++++++++ .../executions/sheet.svelte | 11 ++++-- .../executions/table.svelte | 12 +++--- 3 files changed, 51 insertions(+), 9 deletions(-) create mode 100644 src/lib/helpers/executionTimeout.ts diff --git a/src/lib/helpers/executionTimeout.ts b/src/lib/helpers/executionTimeout.ts new file mode 100644 index 000000000..5ef81af60 --- /dev/null +++ b/src/lib/helpers/executionTimeout.ts @@ -0,0 +1,37 @@ +import type { Models } from '@appwrite.io/console'; + +/** + * Checks if an execution has exceeded the maximum execution timeout duration + */ +function isExecutionTimedOut(createdAt: string, status: string, timeoutSeconds: number): boolean { + if (!['waiting', 'processing'].includes(status)) { + return false; + } + + if (!timeoutSeconds || timeoutSeconds <= 0) { + return false; + } + + const created = new Date(createdAt); + const elapsedSeconds = Math.floor((Date.now() - created.getTime()) / 1000); + + return elapsedSeconds > timeoutSeconds; +} + +/** + * Gets the effective status for an execution, considering timeout + */ +export function getEffectiveExecutionStatus( + execution: Models.Execution, + func: Models.Function +): string { + const originalStatus = execution.status; + const createdAt = execution.$createdAt; + + const timeoutSeconds = func.timeout; + if (isExecutionTimedOut(createdAt, originalStatus, timeoutSeconds)) { + return 'failed'; + } + + return originalStatus; +} diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte index 7cddff0bb..7f4ca4300 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte @@ -23,6 +23,8 @@ import { logStatusConverter } from './store'; import { LogsRequest, LogsResponse } from '$lib/components/logs'; import { timer } from '$lib/actions/timer'; + import { getEffectiveExecutionStatus } from '$lib/helpers/executionTimeout'; + import { func } from '../store'; export let selectedLogId: string; export let logs: Models.Execution[]; @@ -47,6 +49,7 @@ } $: selectedLog = logs?.find((log) => log.$id === selectedLogId); + $: effectiveStatus = selectedLog ? getEffectiveExecutionStatus(selectedLog, $func) : null; $: isFirstLog = logs.findIndex((log) => log.$id === selectedLogId) === 0; $: isLastLog = logs.findIndex((log) => log.$id === selectedLogId) === logs.length - 1; @@ -113,12 +116,12 @@
+ status={logStatusConverter(effectiveStatus)} + label={capitalize(effectiveStatus)}>
@@ -141,7 +144,7 @@ Duration - {#if ['processing', 'waiting'].includes(selectedLog.status)} + {#if ['processing', 'waiting'].includes(effectiveStatus)} {:else} {calculateTime(selectedLog.duration)} diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte index 1e6915c38..15deb002f 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte @@ -18,6 +18,7 @@ import DualTimeView from '$lib/components/dualTimeView.svelte'; import { func } from '../store'; import { sdk } from '$lib/stores/sdk'; + import { getEffectiveExecutionStatus } from '$lib/helpers/executionTimeout'; import { page } from '$app/state'; import { Submit, trackError, trackEvent } from '$lib/actions/analytics'; import { invalidate } from '$app/navigation'; @@ -66,6 +67,7 @@ {#snippet children(root)} {#each executions.executions as log (log.$id)} + {@const effectiveStatus = getEffectiveExecutionStatus(log, $func)}
+ status={logStatusConverter(effectiveStatus)} + label={capitalize(effectiveStatus)}>
@@ -115,7 +117,7 @@
{:else if column.id === 'duration'} - {#if ['processing', 'waiting'].includes(log.status)} + {#if ['processing', 'waiting'].includes(effectiveStatus)} {:else} {calculateTime(log.duration)} From fc3a27cb71a07249e969a91019f035381e6941d6 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Fri, 16 Jan 2026 15:14:48 +0530 Subject: [PATCH 41/45] fix audit issues --- package.json | 2 +- pnpm-lock.yaml | 79 ++++++++++++++++++++++++++++---------------------- 2 files changed, 45 insertions(+), 36 deletions(-) diff --git a/package.json b/package.json index 7b00655cd..6ff0f771a 100644 --- a/package.json +++ b/package.json @@ -57,7 +57,7 @@ "@melt-ui/svelte": "^0.86.5", "@playwright/test": "^1.55.1", "@sveltejs/adapter-static": "^3.0.8", - "@sveltejs/kit": "^2.42.1", + "@sveltejs/kit": "^2.49.5", "@sveltejs/vite-plugin-svelte": "^5.0.3", "@testing-library/dom": "^10.4.0", "@testing-library/jest-dom": "^6.6.3", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 23cbb7f83..d01808519 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -37,7 +37,7 @@ importers: version: 2.11.8 '@sentry/sveltekit': specifier: ^8.38.0 - version: 8.55.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.30.0)(@sveltejs/kit@2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) + version: 8.55.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.30.0)(@sveltejs/kit@2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) '@stripe/stripe-js': specifier: ^3.5.0 version: 3.5.0 @@ -110,10 +110,10 @@ importers: version: 1.56.1 '@sveltejs/adapter-static': specifier: ^3.0.8 - version: 3.0.8(@sveltejs/kit@2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0))) + version: 3.0.8(@sveltejs/kit@2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0))) '@sveltejs/kit': - specifier: ^2.42.1 - version: 2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) + specifier: ^2.49.5 + version: 2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) '@sveltejs/vite-plugin-svelte': specifier: ^5.0.3 version: 5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) @@ -364,8 +364,8 @@ packages: engines: {node: '>=6.0.0'} hasBin: true - '@babel/parser@7.28.5': - resolution: {integrity: sha512-KKBU1VGYR7ORr3At5HAtUQ+TV3SzRCXmA/8OdDZiLDBIZxVyzXuztPjfLd3BV1PRAQGCMWWSHYhL0F8d5uHBDQ==} + '@babel/parser@7.28.6': + resolution: {integrity: sha512-TeR9zWR18BvbfPmGbLampPMW+uW1NZnJlRuuHso8i87QZNq2JRF9i6RgxRqtEq+wQGsS19NNTWr2duhnE49mfQ==} engines: {node: '>=6.0.0'} hasBin: true @@ -385,8 +385,8 @@ packages: resolution: {integrity: sha512-H45s8fVLYjbhFH62dIJ3WtmJ6RSPt/3DRO0ZcT2SUiYiQyz3BLVb9ADEnLl91m74aQPS3AzzeajZHYOalWe3bg==} engines: {node: '>=6.9.0'} - '@babel/types@7.28.5': - resolution: {integrity: sha512-qQ5m48eI/MFLQ5PxQj4PFaprjyCTLI37ElWMmNs0K8Lk3dVeOdNpB3ks8jc7yM5CDmVC73eMVk/trk3fgmrUpA==} + '@babel/types@7.28.6': + resolution: {integrity: sha512-0ZrskXVEHSWIqZM/sQZ4EV3jZJXRkio/WCxaqKZP1g//CEWEPSfeZFcms4XeKBCHU0ZKnIkdJeU/kF+eRp5lBg==} engines: {node: '>=6.9.0'} '@csstools/color-helpers@5.0.2': @@ -1282,18 +1282,21 @@ packages: peerDependencies: '@sveltejs/kit': ^2.0.0 - '@sveltejs/kit@2.42.1': - resolution: {integrity: sha512-SoWdb/OxEKHMlXZ78eNZa4pR1YdOGnUfcFj5NylJv+ZaTrnHK5xapw+7RJP2MiS1D4T+sEH25/tmMtmEl8p6VA==} + '@sveltejs/kit@2.49.5': + resolution: {integrity: sha512-dCYqelr2RVnWUuxc+Dk/dB/SjV/8JBndp1UovCyCZdIQezd8TRwFLNZctYkzgHxRJtaNvseCSRsuuHPeUgIN/A==} engines: {node: '>=18.13'} hasBin: true peerDependencies: '@opentelemetry/api': ^1.0.0 '@sveltejs/vite-plugin-svelte': ^3.0.0 || ^4.0.0-next.1 || ^5.0.0 || ^6.0.0-next.0 svelte: ^4.0.0 || ^5.0.0-next.0 + typescript: ^5.3.3 vite: ^5.0.3 || ^6.0.0 || ^7.0.0-beta.0 peerDependenciesMeta: '@opentelemetry/api': optional: true + typescript: + optional: true '@sveltejs/vite-plugin-svelte-inspector@4.0.1': resolution: {integrity: sha512-J/Nmb2Q2y7mck2hyCX4ckVHcR5tu2J+MtBEQqpDrrgELZ2uvraQcK/ioCV61AqkdXFgriksOKIceDcQmqnGhVw==} @@ -1885,6 +1888,9 @@ packages: csstype@3.1.3: resolution: {integrity: sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==} + csstype@3.2.3: + resolution: {integrity: sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==} + d3-array@3.2.4: resolution: {integrity: sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==} engines: {node: '>=12'} @@ -2075,8 +2081,8 @@ packages: engines: {node: '>=0.10'} hasBin: true - devalue@5.3.2: - resolution: {integrity: sha512-UDsjUbpQn9kvm68slnrs+mfxwFkIflOhkanmyabZ8zOYk8SMEIbJ3TK+88g70hSIeytu4y18f0z/hYHMTrXIWw==} + devalue@5.6.2: + resolution: {integrity: sha512-nPRkjWzzDQlsejL1WVifk5rvcFi/y1onBRxjaFMjZeR9mFpqu2gmAZ9xUB9/IEanEP/vBtGeGganC/GO1fmufg==} devlop@1.1.0: resolution: {integrity: sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==} @@ -3130,14 +3136,14 @@ packages: engines: {node: '>=10'} hasBin: true - seroval-plugins@1.3.3: - resolution: {integrity: sha512-16OL3NnUBw8JG1jBLUoZJsLnQq0n5Ua6aHalhJK4fMQkz1lqR7Osz1sA30trBtd9VUDc2NgkuRCn8+/pBwqZ+w==} + seroval-plugins@1.4.2: + resolution: {integrity: sha512-X7p4MEDTi+60o2sXZ4bnDBhgsUYDSkQEvzYZuJyFqWg9jcoPsHts5nrg5O956py2wyt28lUrBxk0M0/wU8URpA==} engines: {node: '>=10'} peerDependencies: seroval: ^1.0 - seroval@1.3.2: - resolution: {integrity: sha512-RbcPH1n5cfwKrru7v7+zrZvjLurgHhGyso3HTyGtRivGWgYjbOmGuivCQaORNELjNONoK35nj28EoWul9sb1zQ==} + seroval@1.4.2: + resolution: {integrity: sha512-N3HEHRCZYn3cQbsC4B5ldj9j+tHdf4JZoYPlcI4rRYu0Xy4qN8MQf1Z08EibzB0WpgRG5BGK08FTrmM66eSzKQ==} engines: {node: '>=10'} set-cookie-parser@2.7.1: @@ -3944,9 +3950,9 @@ snapshots: dependencies: '@babel/types': 7.27.0 - '@babel/parser@7.28.5': + '@babel/parser@7.28.6': dependencies: - '@babel/types': 7.28.5 + '@babel/types': 7.28.6 '@babel/runtime@7.27.0': dependencies: @@ -3975,7 +3981,7 @@ snapshots: '@babel/helper-string-parser': 7.25.9 '@babel/helper-validator-identifier': 7.25.9 - '@babel/types@7.28.5': + '@babel/types@7.28.6': dependencies: '@babel/helper-string-parser': 7.27.1 '@babel/helper-validator-identifier': 7.28.5 @@ -4797,14 +4803,14 @@ snapshots: magic-string: 0.30.7 svelte: 5.25.3 - '@sentry/sveltekit@8.55.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.30.0)(@sveltejs/kit@2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0))': + '@sentry/sveltekit@8.55.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.30.0)(@sveltejs/kit@2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0))': dependencies: '@sentry/core': 8.55.0 '@sentry/node': 8.55.0 '@sentry/opentelemetry': 8.55.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.30.0) '@sentry/svelte': 8.55.0(svelte@5.25.3) '@sentry/vite-plugin': 2.22.6 - '@sveltejs/kit': 2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) + '@sveltejs/kit': 2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) magic-string: 0.30.7 magicast: 0.2.8 sorcery: 1.0.0 @@ -4876,11 +4882,11 @@ snapshots: dependencies: acorn: 8.15.0 - '@sveltejs/adapter-static@3.0.8(@sveltejs/kit@2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))': + '@sveltejs/adapter-static@3.0.8(@sveltejs/kit@2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))': dependencies: - '@sveltejs/kit': 2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) + '@sveltejs/kit': 2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)) - '@sveltejs/kit@2.42.1(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0))': + '@sveltejs/kit@2.49.5(@opentelemetry/api@1.9.0)(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(typescript@5.8.2)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0))': dependencies: '@standard-schema/spec': 1.0.0 '@sveltejs/acorn-typescript': 1.0.5(acorn@8.15.0) @@ -4888,7 +4894,7 @@ snapshots: '@types/cookie': 0.6.0 acorn: 8.15.0 cookie: 0.6.0 - devalue: 5.3.2 + devalue: 5.6.2 esm-env: 1.2.2 kleur: 4.1.5 magic-string: 0.30.18 @@ -4900,6 +4906,7 @@ snapshots: vite: 7.0.6(@types/node@22.13.14)(sass@1.86.0) optionalDependencies: '@opentelemetry/api': 1.9.0 + typescript: 5.8.2 '@sveltejs/vite-plugin-svelte-inspector@4.0.1(@sveltejs/vite-plugin-svelte@5.0.3(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0)))(svelte@5.25.3)(vite@7.0.6(@types/node@22.13.14)(sass@1.86.0))': dependencies: @@ -5293,7 +5300,7 @@ snapshots: '@vue/compiler-core@3.5.13': dependencies: - '@babel/parser': 7.28.5 + '@babel/parser': 7.28.6 '@vue/shared': 3.5.13 entities: 4.5.0 estree-walker: 2.0.2 @@ -5306,7 +5313,7 @@ snapshots: '@vue/compiler-sfc@3.5.13': dependencies: - '@babel/parser': 7.28.5 + '@babel/parser': 7.28.6 '@vue/compiler-core': 3.5.13 '@vue/compiler-dom': 3.5.13 '@vue/compiler-ssr': 3.5.13 @@ -5335,7 +5342,7 @@ snapshots: '@vue/reactivity': 3.5.13 '@vue/runtime-core': 3.5.13 '@vue/shared': 3.5.13 - csstype: 3.1.3 + csstype: 3.2.3 '@vue/server-renderer@3.5.13(vue@3.5.13(typescript@5.8.2))': dependencies: @@ -5620,6 +5627,8 @@ snapshots: csstype@3.1.3: {} + csstype@3.2.3: {} + d3-array@3.2.4: dependencies: internmap: 2.0.3 @@ -5837,7 +5846,7 @@ snapshots: detect-libc@1.0.3: optional: true - devalue@5.3.2: {} + devalue@5.6.2: {} devlop@1.1.0: dependencies: @@ -6902,11 +6911,11 @@ snapshots: semver@7.7.1: {} - seroval-plugins@1.3.3(seroval@1.3.2): + seroval-plugins@1.4.2(seroval@1.4.2): dependencies: - seroval: 1.3.2 + seroval: 1.4.2 - seroval@1.3.2: {} + seroval@1.4.2: {} set-cookie-parser@2.7.1: {} @@ -6983,9 +6992,9 @@ snapshots: solid-js@1.9.5: dependencies: - csstype: 3.1.3 - seroval: 1.3.2 - seroval-plugins: 1.3.3(seroval@1.3.2) + csstype: 3.2.3 + seroval: 1.4.2 + seroval-plugins: 1.4.2(seroval@1.4.2) solid-swr-store@0.10.7(solid-js@1.9.5)(swr-store@0.10.6): dependencies: From 407123e09f575972019e8d00bca138f4f179e101 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Fri, 16 Jan 2026 15:18:26 +0530 Subject: [PATCH 42/45] Fix duration timer to use original status instead of effective status The timer should continue running for executions stuck in processing/waiting even when they're displayed as failed due to timeout. --- .../functions/function-[function]/executions/sheet.svelte | 2 +- .../functions/function-[function]/executions/table.svelte | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte index 7f4ca4300..bde1b909f 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/sheet.svelte @@ -144,7 +144,7 @@ Duration - {#if ['processing', 'waiting'].includes(effectiveStatus)} + {#if ['processing', 'waiting'].includes(selectedLog.status)} {:else} {calculateTime(selectedLog.duration)} diff --git a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte index 15deb002f..f2431f02e 100644 --- a/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/functions/function-[function]/executions/table.svelte @@ -117,7 +117,7 @@ {:else if column.id === 'duration'} - {#if ['processing', 'waiting'].includes(effectiveStatus)} + {#if ['processing', 'waiting'].includes(log.status)} {:else} {calculateTime(log.duration)} From a35a5262b2f94da2d2b7bdcf31cece91fea9cf09 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Fri, 16 Jan 2026 15:30:26 +0530 Subject: [PATCH 43/45] fix comparision --- src/lib/helpers/buildTimeout.ts | 2 +- src/lib/helpers/executionTimeout.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/lib/helpers/buildTimeout.ts b/src/lib/helpers/buildTimeout.ts index df10478ee..3f767c840 100644 --- a/src/lib/helpers/buildTimeout.ts +++ b/src/lib/helpers/buildTimeout.ts @@ -15,7 +15,7 @@ function isBuildTimedOut(createdAt: string, status: string, timeoutSeconds: numb const created = new Date(createdAt); const elapsedSeconds = Math.floor((Date.now() - created.getTime()) / 1000); - return elapsedSeconds > timeoutSeconds; + return elapsedSeconds >= timeoutSeconds; } /** diff --git a/src/lib/helpers/executionTimeout.ts b/src/lib/helpers/executionTimeout.ts index 5ef81af60..4468350fe 100644 --- a/src/lib/helpers/executionTimeout.ts +++ b/src/lib/helpers/executionTimeout.ts @@ -15,7 +15,7 @@ function isExecutionTimedOut(createdAt: string, status: string, timeoutSeconds: const created = new Date(createdAt); const elapsedSeconds = Math.floor((Date.now() - created.getTime()) / 1000); - return elapsedSeconds > timeoutSeconds; + return elapsedSeconds >= timeoutSeconds; } /** From 0f80efe9f546339c7d654c97e2bdb619b92bfeaf Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Fri, 16 Jan 2026 16:47:55 +0530 Subject: [PATCH 44/45] Remove finalizing status from deployments --- src/lib/helpers/buildTimeout.ts | 7 ------- .../sites/(components)/logs.svelte | 1 - .../sites/(components)/logsTimer.svelte | 2 +- .../sites/create-site/deploying/+page.svelte | 2 +- 4 files changed, 2 insertions(+), 10 deletions(-) diff --git a/src/lib/helpers/buildTimeout.ts b/src/lib/helpers/buildTimeout.ts index 3f767c840..750e9f06b 100644 --- a/src/lib/helpers/buildTimeout.ts +++ b/src/lib/helpers/buildTimeout.ts @@ -33,13 +33,6 @@ export function getEffectiveBuildStatus( return 'failed'; } - const isReady = originalStatus === 'ready'; - const hasScreenshot = deployment.screenshotLight && deployment.screenshotDark; - - if (isReady && !hasScreenshot) { - return 'finalizing'; - } - return originalStatus; } diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte index 51c407652..65712df38 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte @@ -6,7 +6,6 @@ case 'ready': return 'success'; case 'building': - case 'finalizing': return 'warning'; case 'processing': return undefined; diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte index 79a00f541..8f7701b4b 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte @@ -13,7 +13,7 @@ - {#if ['processing', 'building', 'finalizing'].includes(effectiveStatus)} + {#if ['processing', 'building'].includes(effectiveStatus)}

diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index b41104e09..fa08f88e9 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -121,7 +121,7 @@ - {#if ['processing', 'building', 'finalizing'].includes(effectiveStatus)} + {#if ['processing', 'building'].includes(effectiveStatus)} Deployment will continue in the background From c3388c7e55504192caa114b1c1963150ed17deda Mon Sep 17 00:00:00 2001 From: Harsh Mahajan <127186841+HarshMN2345@users.noreply.github.com> Date: Fri, 16 Jan 2026 18:06:29 +0530 Subject: [PATCH 45/45] show ready when finalising --- src/lib/helpers/buildTimeout.ts | 7 +++++++ .../sites/(components)/logs.svelte | 1 + .../sites/(components)/logsTimer.svelte | 2 +- .../sites/create-site/deploying/+page.svelte | 2 +- .../sites/site-[site]/deployments/table.svelte | 5 +++-- .../sites/site-[site]/deploymentsOverview.svelte | 14 ++++++++------ 6 files changed, 21 insertions(+), 10 deletions(-) diff --git a/src/lib/helpers/buildTimeout.ts b/src/lib/helpers/buildTimeout.ts index 750e9f06b..3f767c840 100644 --- a/src/lib/helpers/buildTimeout.ts +++ b/src/lib/helpers/buildTimeout.ts @@ -33,6 +33,13 @@ export function getEffectiveBuildStatus( return 'failed'; } + const isReady = originalStatus === 'ready'; + const hasScreenshot = deployment.screenshotLight && deployment.screenshotDark; + + if (isReady && !hasScreenshot) { + return 'finalizing'; + } + return originalStatus; } diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte index 65712df38..51c407652 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logs.svelte @@ -6,6 +6,7 @@ case 'ready': return 'success'; case 'building': + case 'finalizing': return 'warning'; case 'processing': return undefined; diff --git a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte index 8f7701b4b..79a00f541 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/(components)/logsTimer.svelte @@ -13,7 +13,7 @@ - {#if ['processing', 'building'].includes(effectiveStatus)} + {#if ['processing', 'building', 'finalizing'].includes(effectiveStatus)}

diff --git a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte index fa08f88e9..b41104e09 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/create-site/deploying/+page.svelte @@ -121,7 +121,7 @@
- {#if ['processing', 'building'].includes(effectiveStatus)} + {#if ['processing', 'building', 'finalizing'].includes(effectiveStatus)} Deployment will continue in the background diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte index 92c82f8fb..3dac48976 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deployments/table.svelte @@ -85,6 +85,7 @@ deployment, $regionalConsoleVariables )} + {@const displayStatus = effectiveStatus === 'finalizing' ? 'ready' : effectiveStatus} {:else} + status={deploymentStatusConverter(displayStatus)} + label={capitalize(displayStatus)} /> {/if} {:else if column.id === 'type'} diff --git a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deploymentsOverview.svelte b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deploymentsOverview.svelte index b66277f2b..f9f2f8c0e 100644 --- a/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deploymentsOverview.svelte +++ b/src/routes/(console)/project-[region]-[project]/sites/site-[site]/deploymentsOverview.svelte @@ -66,6 +66,12 @@ {#each deploymentList?.deployments as deployment (deployment.$id)} + {@const effectiveStatus = getEffectiveBuildStatus( + deployment, + $regionalConsoleVariables + )} + {@const displayStatus = + effectiveStatus === 'finalizing' ? 'ready' : effectiveStatus} @@ -73,16 +79,12 @@ {deployment.$id} - {@const effectiveStatus = getEffectiveBuildStatus( - deployment, - $regionalConsoleVariables - )} {#if activeDeployment?.$id === deployment?.$id} {:else} + status={deploymentStatusConverter(displayStatus)} + label={capitalize(displayStatus)} /> {/if}