fix: instance link includes domain, project delete cleans up containers and proxies
- InstanceCard appends settings domain to subdomain link (stage-dev-app.example.com instead of just stage-dev-app) - Project deletion now removes Docker containers and proxy routes before deleting DB records - Pass domain from settings to InstanceCard via project detail page
This commit is contained in:
@@ -169,6 +169,26 @@ func (s *Server) updateProject(w http.ResponseWriter, r *http.Request) {
|
||||
// deleteProject handles DELETE /api/projects/{id}.
|
||||
func (s *Server) deleteProject(w http.ResponseWriter, r *http.Request) {
|
||||
id := chi.URLParam(r, "id")
|
||||
|
||||
// Clean up Docker containers and proxy routes before deleting the project.
|
||||
ctx := r.Context()
|
||||
stages, _ := s.store.GetStagesByProjectID(id)
|
||||
for _, stage := range stages {
|
||||
instances, _ := s.store.GetInstancesByStageID(stage.ID)
|
||||
for _, inst := range instances {
|
||||
if inst.ContainerID != "" {
|
||||
if err := s.docker.RemoveContainer(ctx, inst.ContainerID, true); err != nil {
|
||||
slog.Warn("delete project: remove container", "container", inst.ContainerID, "error", err)
|
||||
}
|
||||
}
|
||||
if inst.ProxyRouteID != "" {
|
||||
if err := s.proxyProvider.DeleteRoute(ctx, inst.ProxyRouteID); err != nil {
|
||||
slog.Warn("delete project: delete proxy route", "route", inst.ProxyRouteID, "error", err)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if err := s.store.DeleteProject(id); err != nil {
|
||||
if errors.Is(err, store.ErrNotFound) {
|
||||
respondNotFound(w, "project")
|
||||
|
||||
@@ -13,17 +13,20 @@
|
||||
interface Props {
|
||||
instance: Instance;
|
||||
projectId: string;
|
||||
domain?: string;
|
||||
onchange?: () => void;
|
||||
}
|
||||
|
||||
const { instance, projectId, onchange }: Props = $props();
|
||||
const { instance, projectId, domain = '', onchange }: Props = $props();
|
||||
|
||||
let loading = $state(false);
|
||||
let error = $state('');
|
||||
let confirmAction = $state<'stop' | 'restart' | 'remove' | null>(null);
|
||||
|
||||
const subdomainUrl = $derived(
|
||||
instance.subdomain ? `https://${instance.subdomain}` : ''
|
||||
instance.subdomain && domain
|
||||
? `https://${instance.subdomain}.${domain}`
|
||||
: instance.subdomain ? `https://${instance.subdomain}` : ''
|
||||
);
|
||||
|
||||
const timeSinceCreated = $derived(() => {
|
||||
|
||||
@@ -106,6 +106,7 @@
|
||||
}
|
||||
}
|
||||
let tagsLoading = $state(false);
|
||||
let settingsDomain = $state('');
|
||||
|
||||
let showDeleteConfirm = $state(false);
|
||||
|
||||
@@ -142,6 +143,11 @@
|
||||
} catch {
|
||||
deploys = [];
|
||||
}
|
||||
|
||||
try {
|
||||
const settings = await api.getSettings();
|
||||
settingsDomain = settings.domain ?? '';
|
||||
} catch { /* non-critical */ }
|
||||
} catch (e) {
|
||||
error = e instanceof Error ? e.message : $t('projectDetail.loadFailed');
|
||||
} finally {
|
||||
@@ -486,6 +492,7 @@
|
||||
<InstanceCard
|
||||
{instance}
|
||||
{projectId}
|
||||
domain={settingsDomain}
|
||||
onchange={loadProject}
|
||||
/>
|
||||
{/each}
|
||||
|
||||
Reference in New Issue
Block a user