browser-compat-data icon indicating copy to clipboard operation
browser-compat-data copied to clipboard

api.ServiceWorkerGlobalScope.notificationclick_event - It looks like the events are actually fired on iOS Safari - please verify

Open bedney opened this issue 1 year ago • 3 comments

MDN URL

https://developer.mozilla.org/en-US/docs/Web/API/ServiceWorkerGlobalScope/notificationclick_event

What specific section or headline is this issue about?

iOS Safari support of notificationclick events

What information was incorrect, unhelpful, or incomplete?

The Browser Compatibility section indicates that this event is not supported in iOS Safari.

What did you expect to see?

That the Browser Compatibility section would indicate that this event is supported in iOS Safari.

Do you have any supporting links, references, or citations?

I have code which does executed in a notificationclick handler on iOS Safari and there are multiple users here that indicate the same: https://forums.developer.apple.com/forums/thread/726793

Do you have anything more you want to share?

No response

MDN metadata

Page report details
  • Folder: en-us/web/api/serviceworkerglobalscope/notificationclick_event
  • MDN URL: https://developer.mozilla.org/en-US/docs/Web/API/ServiceWorkerGlobalScope/notificationclick_event
  • GitHub URL: https://github.com/mdn/content/blob/main/files/en-us/web/api/serviceworkerglobalscope/notificationclick_event/index.md
  • Last commit: https://github.com/mdn/content/commit/28848ba41c082db2a8c55e85c804bd06363afb57
  • Document last modified: 2024-04-12T08:51:58.000Z

bedney avatar Apr 29 '24 11:04 bedney

I agree with this issue notificationclick worked on ios17.6.1 however, event.preventDefault() is required

  • https://forums.developer.apple.com/forums/thread/733604?answerId=784041022#784041022
  • https://bugs.webkit.org/show_bug.cgi?id=268797#c19

somezi avatar Sep 08 '24 13:09 somezi

With regard to the ServiceWorkerGlobalScope.notificationclick_event feature, we detect this by checking "onnotificationclick" in self in a ServiceWorker context. This detection fails in Safari iOS 16, 17 and 18.

The WebKit source code shows that both onnotificationclick and onnotificationclose properties are behind the NotificationEventEnabled setting:

https://github.com/WebKit/WebKit/blob/770984f81ade0b1cb3ab67f1be2f568b248dd500/Source/WebCore/workers/service/ServiceWorkerGlobalScope.idl#L51-L52

And that setting is currently disabled on iOS:

https://github.com/WebKit/WebKit/blob/770984f81ade0b1cb3ab67f1be2f568b248dd500/Source/WTF/Scripts/Preferences/UnifiedWebPreferences.yaml#L5457-L5471

We could record the fact that the notificationclick event is fired under certain circumstances, by setting partial_implementation: true.

Note though that https://bugs.webkit.org/show_bug.cgi?id=252625 suggests that notification events are intentionally disabled on iOS.

caugner avatar May 07 '25 22:05 caugner

I have tested this and can confirm that the notificationclick is fired on iOS 18, despite the WebKit settings apparently.

Demo: https://whatpwacando.today/notifications

To test, install the PWA at https://whatpwacando.today/, send a notification with a 5 second delay and close the PWA. When the notification arrives, tap it and then the PWA will open at https://whatpwacando.today/notifications.

This is the URL that is configured in the push notification payload and it consistently navigates to other URLs when I change this.

Push event handler:

const pushHandler = async e => {
  const data = e.data.json();
  const {title, message, interaction, url} = data;

  const options = {
    body: message,
    icon: '/src/img/icons/icon-512x512.png',
    vibrate: [100, 50, 100],
    data: {
      dateOfArrival: Date.now(),
      url
    },
    actions: [
      {
        action: 'confirm',
        title: 'OK'
      },
      {
        action: 'close',
        title: 'Close notification'
      },
    ],
    requireInteraction: interaction
  };

  e.waitUntil(
    self.registration.showNotification(title, options)
    .then(hasActiveClients)
    .then((activeClients) => {
      if(!activeClients) {
        updateBadges();
      }
    })
    .catch(err => sendMessage(err))
  )
};

Notificationclick event handler:

const notificationClickHandler = async (e) => {
  const {notification} = e;
  const {data} = notification;
  
  notification.close();
  
  e.waitUntil(clients.openWindow(data.url))
};

DannyMoerkerke avatar May 27 '25 11:05 DannyMoerkerke