<script lang="ts">
import { tick } from "svelte";
import { ui } from "../../stores/ui.svelte.js";
import { sessions } from "../../stores/sessions.svelte.js";
import { truncate } from "../../utils/format.js";
let deleting = $state(false);
let deleteBtn = $state<HTMLButtonElement>();
let sessionName = $derived.by(() => {
const s = sessions.activeSession;
if (!s) return "this session";
return truncate(
s.display_name ?? s.first_message ?? "this session",
60,
);
});
function close() {
ui.activeModal = null;
}
async function confirmDelete() {
const id = sessions.activeSessionId;
if (!id || deleting) return;
deleting = true;
try {
await sessions.deleteSession(id);
close();
} catch {
} finally {
deleting = false;
await tick();
deleteBtn?.focus();
}
}
function handleOverlayClick(e: MouseEvent) {
if (
(e.target as HTMLElement).classList.contains(
"confirm-overlay",
)
) {
close();
}
}
</script>
<svelte:window
onkeydown={(e) => {
if (e.key === "Escape") close();
}}
/>
<div
class="confirm-overlay"
role="button"
tabindex="0"
aria-label="Dismiss delete confirmation"
onclick={handleOverlayClick}
onkeydown={(e) => {
if (e.key === "Escape") {
e.preventDefault();
close();
}
}}
>
<div class="confirm-modal">
<div class="confirm-header">
<h3 class="confirm-title">Delete Session</h3>
<button class="close-btn" onclick={close}>×</button>
</div>
<div class="confirm-body">
<p class="confirm-message">
Move <strong>{sessionName}</strong> to trash?
</p>
<p class="confirm-hint">
You can restore it later from the Trash page.
</p>
</div>
<div class="confirm-actions">
<button class="cancel-btn" onclick={close}>Cancel</button>
<button
class="delete-btn"
bind:this={deleteBtn}
onclick={confirmDelete}
disabled={deleting}
autofocus
>
{deleting ? "Deleting..." : "Move to Trash"}
</button>
</div>
</div>
</div>
<style>
.confirm-overlay {
position: fixed;
inset: 0;
background: var(--vscode-widget-shadow);
display: flex;
align-items: center;
justify-content: center;
z-index: 100;
}
.confirm-modal {
width: 380px;
background: var(--vscode-sideBar-background);
border: 1px solid var(--vscode-panel-border);
border-radius: var(--wsb-radius-lg);
box-shadow: var(--wb-shadow-md);
overflow: hidden;
}
.confirm-header {
display: flex;
align-items: center;
justify-content: space-between;
padding: var(--wb-spacing-12) var(--wb-spacing-16);
border-bottom: 1px solid var(--vscode-panel-border);
}
.confirm-title {
font-size: var(--wb-font-size-13);
font-weight: 600;
color: var(--vscode-editor-foreground);
}
.close-btn {
width: var(--wb-control-size-24);
height: var(--wb-control-size-24);
display: flex;
align-items: center;
justify-content: center;
font-size: var(--wb-font-size-16);
color: var(--vscode-disabledForeground);
border-radius: var(--wsb-radius-sm);
}
.close-btn:hover {
background: var(--vscode-list-hoverBackground);
color: var(--vscode-editor-foreground);
}
.confirm-body {
padding: var(--wb-spacing-16);
}
.confirm-message {
font-size: var(--wb-font-size-13);
color: var(--vscode-editor-foreground);
margin: 0 0 var(--wb-spacing-6);
}
.confirm-hint {
font-size: var(--wb-font-size-12);
color: var(--vscode-disabledForeground);
margin: 0;
}
.confirm-actions {
display: flex;
justify-content: flex-end;
gap: var(--wb-spacing-8);
padding: var(--wb-spacing-12) var(--wb-spacing-16);
border-top: 1px solid var(--vscode-panel-border);
}
.cancel-btn {
height: var(--wb-control-size-30);
padding: 0 var(--wb-spacing-14);
border-radius: var(--wsb-radius-sm);
font-size: var(--wb-font-size-12);
font-weight: 500;
color: var(--vscode-foreground);
background: var(--vscode-input-background);
border: 1px solid var(--vscode-panel-border);
cursor: pointer;
}
.cancel-btn:hover {
background: var(--vscode-list-hoverBackground);
}
.delete-btn {
height: var(--wb-control-size-30);
padding: 0 var(--wb-spacing-14);
border-radius: var(--wsb-radius-sm);
font-size: var(--wb-font-size-12);
font-weight: 500;
color: white;
background: var(--vscode-errorForeground, #d32f2f);
border: none;
cursor: pointer;
}
.delete-btn:hover:not(:disabled) {
opacity: 0.9;
}
.delete-btn:disabled {
opacity: 0.6;
cursor: default;
}
</style>