feat(ui): global confirm modal — browser dialogs retired sitewide (issues #5/#4/#7)
ONE styled modal answers every hx-confirm in the app: a body-level htmx:confirm interceptor (web/src/confirm.ts, canonical htmx pattern) preventDefaults and shows the dialog, issuing the request on Confirm. Nine hx-confirm call sites upgrade without touching them. The modal lives in the header partial so every page has it; confirmDialog() is exported for JS call sites and degrades to the native dialog if the header is absent (bare layouts). Migrated the five window.confirm sites (admin.ts ×3, book-detail.ts ×2) to the same promise API. Podcast feed detail (issues #4/#7): the unsubscribe copy is role-aware — non-admins get 'Unsubscribe from this feed?' with silent retention (file state is admin knowledge); an admin who is the LAST subscriber gets a three-choice modal instead: Unsubscribe (files kept, the D6 default — sliding-window feeds make purge unrecoverable) / Remove feed + files / Cancel. Admins with co-subscribers keep the files-note confirm.
This commit is contained in:
1 parent
30766020c8
commit
acbcc61ae4
5 files changed
+113
-10
No files matched your search
+7
-6
@@ -1,3 +1,4 @@
|
||||
import { confirmDialog } from "./confirm";
|
||||
import { Alpine } from "./alpine";
|
||||
import { showToast } from "./toast";
|
||||
|
||||
@@ -423,9 +424,9 @@ async function purgeArchivedItems(): Promise<void> {
|
||||
if (!token) return;
|
||||
|
||||
if (
|
||||
!window.confirm(
|
||||
!(await confirmDialog(
|
||||
"Permanently delete all archived items? Their reading progress, notes, and highlights will be lost.",
|
||||
)
|
||||
))
|
||||
) {
|
||||
return;
|
||||
}
|
||||
@@ -475,9 +476,9 @@ async function deleteArchivedItem(id: string): Promise<void> {
|
||||
const token = requireToken();
|
||||
if (!token) return;
|
||||
if (
|
||||
!window.confirm(
|
||||
!(await confirmDialog(
|
||||
"Permanently delete this item? Its reading progress, notes, and highlights will be lost.",
|
||||
)
|
||||
))
|
||||
) {
|
||||
return;
|
||||
}
|
||||
@@ -504,9 +505,9 @@ async function mergeArchivedItem(sourceId: string, targetId: string): Promise<vo
|
||||
const token = requireToken();
|
||||
if (!token) return;
|
||||
if (
|
||||
!window.confirm(
|
||||
!(await confirmDialog(
|
||||
"Merge this archived copy's reading progress, notes, and highlights into the active copy? The archived entry is removed.",
|
||||
)
|
||||
))
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user