5e1b0f791d
* feat(branding): implement dynamic branding in service worker and reports * refactor(service-worker): remove push notification handling code * feat(service-worker): implement dynamic branding in service worker and related scripts
98 lines
2.5 KiB
JavaScript
98 lines
2.5 KiB
JavaScript
/**
|
|
* Service Worker for Push Notifications
|
|
* Handles incoming push notifications and notification click events
|
|
*
|
|
* NOTE: This is the source template. The deployed file at public/sw.js is
|
|
* generated by scripts/inject-public-branding.mjs (runs via predev/prebuild)
|
|
* and is gitignored. Edit this template, not the generated file.
|
|
*/
|
|
|
|
// Handle push events
|
|
self.addEventListener('push', (event) => {
|
|
if (!event.data) {
|
|
console.log('Push event received but no data')
|
|
return
|
|
}
|
|
|
|
let payload
|
|
try {
|
|
payload = event.data.json()
|
|
} catch (e) {
|
|
console.error('Error parsing push data:', e)
|
|
return
|
|
}
|
|
|
|
const { title, body, icon, badge, tag, data, actions } = payload
|
|
|
|
const options = {
|
|
body: body || '',
|
|
icon: icon || '/icons/icon-192.png',
|
|
badge: badge || '/icons/badge-72.png',
|
|
tag: tag,
|
|
data: data || {},
|
|
actions: actions || [],
|
|
vibrate: [200, 100, 200],
|
|
requireInteraction: false,
|
|
}
|
|
|
|
event.waitUntil(
|
|
self.registration.showNotification(title || '__NEXT_PUBLIC_BRANDING_APP_NAME__', options)
|
|
)
|
|
})
|
|
|
|
// Handle notification clicks
|
|
self.addEventListener('notificationclick', (event) => {
|
|
event.notification.close()
|
|
|
|
const action = event.action
|
|
const data = event.notification.data
|
|
|
|
// Determine URL to open
|
|
let url = '/'
|
|
|
|
if (action === 'view' && data?.url) {
|
|
url = data.url
|
|
} else if (action === 'dismiss') {
|
|
// Just close the notification
|
|
return
|
|
} else if (data?.url) {
|
|
// Default click goes to the data URL
|
|
url = data.url
|
|
}
|
|
|
|
event.waitUntil(
|
|
// Try to focus existing window, otherwise open new one
|
|
clients.matchAll({ type: 'window', includeUncontrolled: true }).then((windowClients) => {
|
|
// Check if there's already a window we can focus
|
|
for (const client of windowClients) {
|
|
if (client.url.includes(self.location.origin) && 'focus' in client) {
|
|
client.focus()
|
|
if ('navigate' in client) {
|
|
client.navigate(url)
|
|
}
|
|
return
|
|
}
|
|
}
|
|
// Otherwise open a new window
|
|
if (clients.openWindow) {
|
|
return clients.openWindow(url)
|
|
}
|
|
})
|
|
)
|
|
})
|
|
|
|
// Handle notification close (for analytics if needed)
|
|
self.addEventListener('notificationclose', (event) => {
|
|
console.log('Notification closed:', event.notification.tag)
|
|
})
|
|
|
|
// Service worker activation
|
|
self.addEventListener('activate', (event) => {
|
|
event.waitUntil(clients.claim())
|
|
})
|
|
|
|
// Service worker install
|
|
self.addEventListener('install', (event) => {
|
|
self.skipWaiting()
|
|
})
|