fuzzyworld

word-waltz / files / src / public / sw.js

sw.js

1.4 KB · history · blame

1/**
2 * Word Waltz — Service Worker
3 *
4 * Handles incoming Web Push events and notification clicks.
5 * Registered from notifications.ts at runtime.
6 */
7
8/* global self, clients */
9
10// Derive the base icon path from the SW's own location so it works both on
11// localhost (scope /) and on GitLab Pages (scope /word-waltz/).
12const BASE = new URL('./', self.location.href).href; // e.g. "/word-waltz/"
13
14self.addEventListener('push', (event) => {
15 const data = event.data?.json() ?? {};
16 const title = data.title ?? 'Word Waltz';
17 const options = {
18 body: data.body ?? "It's your turn!",
19 icon: `${BASE}apple-touch-icon.png`,
20 badge: `${BASE}favicon-32x32.png`,
21 tag: 'word-waltz-turn', // replace previous notification
22 renotify: true,
23 data: { url: data.url ?? BASE },
24 };
25 event.waitUntil(self.registration.showNotification(title, options));
26});
27
28self.addEventListener('notificationclick', (event) => {
29 event.notification.close();
30 const target = event.notification.data?.url ?? BASE;
31 event.waitUntil(
32 clients
33 .matchAll({ type: 'window', includeUncontrolled: true })
34 .then((list) => {
35 // Focus an existing tab that is on the same origin+scope
36 for (const c of list) {
37 if (c.url.startsWith(BASE) && 'focus' in c) return c.focus();
38 }
39 return clients.openWindow(target);
40 }),
41 );
42});