From 8f98e79df9eb184ce5132e91d056f7616614ba31 Mon Sep 17 00:00:00 2001 From: Christoph Brandau Date: Mon, 31 Aug 2026 08:43:00 +0200 Subject: [PATCH] feat(clone-dialog): redesign UI and group Azure DevOps repos Rework CloneRepositoryDialog into a two-column layout with a source sidebar and focused content area to make browsing sources easier. Group Azure DevOps repositories by project with a new derived value and render sticky project headers for clearer navigation. Replace showIntegrations with selectIntegrationSource to load the chosen integration, refresh repositories, and update labels and styles. - Introduce source sidebar and refreshed dialog layout - Add azureRepositoryGroups and project grouping UI - Rename flow to selectIntegrationSource and improve loading logic --- .../components/CloneRepositoryDialog.svelte | 171 +++++++++++++----- 1 file changed, 124 insertions(+), 47 deletions(-) diff --git a/src/lib/components/CloneRepositoryDialog.svelte b/src/lib/components/CloneRepositoryDialog.svelte index b8ff263..f1ad4e0 100644 --- a/src/lib/components/CloneRepositoryDialog.svelte +++ b/src/lib/components/CloneRepositoryDialog.svelte @@ -55,6 +55,18 @@ if (!query) return activeRepositories; return activeRepositories.filter((repository) => `${repository.fullName} ${repository.description}`.toLocaleLowerCase().includes(query)); }); + const azureRepositoryGroups = $derived.by(() => { + if (activeSource?.provider !== "azure-devops") return []; + const groups = new Map(); + for (const repository of filteredRepositories) { + const separator = repository.fullName.indexOf("/"); + const project = separator > 0 ? repository.fullName.slice(0, separator) : (isGerman ? "Weitere Repositories" : "Other repositories"); + const repositories = groups.get(project) ?? []; + repositories.push(repository); + groups.set(project, repositories); + } + return [...groups.entries()].map(([project, repositories]) => ({ project, repositories })); + }); const selectedRepository = $derived(activeRepositories.find((repository) => repository.id === selectedRepositoryId)); const directorySuggestion = $derived(directoryNameFromRemoteUrl(remoteUrl)); const canSubmit = $derived(!isBusy && remoteUrl.trim().length > 0 && parentPath.trim().length > 0); @@ -230,10 +242,9 @@ } } - function showIntegrations() { + function selectIntegrationSource(integrationSource: GitIntegrationSource) { source = "integrations"; - const nextSource = configuredSources.find((candidate) => candidate.id === selectedSourceId) ?? configuredSources[0]; - if (nextSource) void loadRepositories(nextSource); + void loadRepositories(integrationSource); } function showUrlInput() { @@ -255,33 +266,51 @@