From cbf897ff1375f4524f894866bfcb886bcb6fbd35 Mon Sep 17 00:00:00 2001 From: Eric Wagoner Date: Tue, 29 Sep 2026 13:03:37 -0400 Subject: [PATCH] Pages show the hall-wide notice, when there is one, at the top The keeper's hall-announce writes one file on the shared host; the site serves it at /hall/announcement.json, and the banner shows it with the time in the reader's own clock, dismissable one notice at a time. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01Jm2auWk6RP71CjaAb4FMoG --- deploy/Caddyfile.tmpl | 7 ++ packages/web/src/Announcement.svelte | 119 +++++++++++++++++++++++++++ packages/web/src/main.ts | 3 + 3 files changed, 129 insertions(+) create mode 100644 packages/web/src/Announcement.svelte diff --git a/deploy/Caddyfile.tmpl b/deploy/Caddyfile.tmpl index ea864e0..a82e5e3 100644 --- a/deploy/Caddyfile.tmpl +++ b/deploy/Caddyfile.tmpl @@ -1,6 +1,13 @@ # Wiz-War's site on a host shared with the other games of Kestrel's Hall: # setup-droplet.sh fills __HOST__ and writes it to /etc/caddy/sites/wizwar.caddy. __HOST__ { + # The hall-wide notice (hall-announce on the host): one file, served by every game's site. + handle_path /hall/* { + root * /var/lib/hall + header Cache-Control "no-store" + file_server + } + header { Strict-Transport-Security "max-age=31536000" X-Content-Type-Options "nosniff" diff --git a/packages/web/src/Announcement.svelte b/packages/web/src/Announcement.svelte new file mode 100644 index 0000000..18f343f --- /dev/null +++ b/packages/web/src/Announcement.svelte @@ -0,0 +1,119 @@ + + +{#if shown} +
+ {shown.text}{when} + +
+{/if} + + diff --git a/packages/web/src/main.ts b/packages/web/src/main.ts index 0ad479c..aaadf6f 100644 --- a/packages/web/src/main.ts +++ b/packages/web/src/main.ts @@ -1,4 +1,5 @@ import { mount } from "svelte"; +import Announcement from "./Announcement.svelte"; import * as Sentry from "@sentry/browser"; // Errors only — no tracing, no replay. Without a DSN baked at build time @@ -35,3 +36,5 @@ const page = location.pathname.startsWith("/watch/") ? import("./SharePage.svelte") : import("./App.svelte"); page.then(({ default: Root }) => mount(Root, { target })); +// The hall-wide notice sits above the game, apart from it: every game of Kestrel's Hall shows the same one. +mount(Announcement, { target: document.body, anchor: document.body.firstChild ?? undefined });