Nourhan Elsherif
Nourhan Elsherif

Reputation: 31

Angular Push Notifications Issue on Safari (MacBook & iPhone)

I'm trying to add push notifications to my Angular app, and I have successfully implemented it for Chrome, Firefox, and Edge. However, I'm facing issues with Safari on both iPhones and MacBooks.

Environment:

Issue: MacBook Safari: I get the following error in service worker web inspector not the console: Push event ended without showing any notification may trigger removal of the push subscription.

iPhone Safari: When I try to subscribe to push notifications, I get this error:

Push notifications not supported in this browser

though I registered the service worker in app.module.ts imports:

ServiceWorkerModule.register('ngsw-worker.js', {enabled:true})

Code: Here's my code in the app component:

ngOnInit() {
  this.swPush.messages.subscribe((message: any) => {
    this.showNotification(message);
  });

  if (
    navigator.userAgent.indexOf('Safari') !== -1 &&
    navigator.userAgent.indexOf('Chrome') === -1
  ) {
    document.addEventListener('click', this.triggerPushNotifications);
  } else {
    this.pushNotifications();
  }
}

pushNotifications() {
  if (!('Notification' in window)) {
    console.warn('Push notifications not supported in this browser');
    return;
  }

  Notification.requestPermission()
    .then((permission) => {
      if (permission === 'granted') {
        this.swPush
          .requestSubscription({ serverPublicKey: this.publicKey })
          .then((subscription) => {
            this.store.dispatch(new PushNotifications(subscription));
            this.swPush.messages.subscribe((message: any) => {
              this.showNotification(message);
            });
          })
          .catch((err) => {
            document.removeEventListener(
              'click',
              this.triggerPushNotifications
            );
            console.error('Subscription failed:', err);
          });
      } else {
        console.warn('User denied permission for push notifications');
      }
    })
    .catch((err) => {
      console.error('Error requesting notification permission:', err);
    });
}

showNotification(data: any) {
  const URL = this.generateURL(data?.source_id, data?.source_type);
  const options = {
    body: data?.message || 'You have a new notification',
    icon: 'assets/images/oolaLogo.svg',
    data: {
      url: URL,
    },
  };

  navigator.serviceWorker
    .getRegistration()
    .then((registration) => {
      if (registration) {
        if (Notification.permission === 'granted') {
          registration.showNotification(data?.title || 'Notification', options);
          this.handleNotificationClicks();
        } else {
          console.error('Notification permission not granted.');
        }
      } else {
        console.error('Service Worker registration not found.');
      }
    })
    .catch((error) => {
      console.error('Error fetching service worker registration:', error);
    });
}

handleNotificationClicks() {
  this.swPush.notificationClicks.subscribe(({ action, notification }) => {
    if (notification.data && notification.data.url) {
      window.open(notification.data.url, '_blank');
    }
  });
}

Notes:

Question: Has anyone faced similar issues with push notifications in Safari? What might be causing these errors, and how can I resolve them?

Upvotes: 1

Views: 353

Answers (1)

F Horm
F Horm

Reputation: 13

Safari requires that you immediately post a notification when a push message is received. "Immediately" means that it cannot be after some async operation.

If you display a notification immediately from the service worker itself, it will stop displaying that error. I cannot remember 100% but I think if you clear your cache and cookies you will be able to receive push messages again if you accidentally get blocked while testing.

From the developer guide: https://developer.apple.com/documentation/usernotifications/sending-web-push-notifications-in-web-apps-and-browsers

"Safari doesn’t support invisible push notifications. Present push notifications to the user immediately after your service worker receives them. If you don’t, Safari revokes the push notification permission for your site."

Regarding safari mobile - safari mobile only supports Push API if a user adds the site to their home screen. Check out the caveat under safari mobile here: https://developer.mozilla.org/en-US/docs/Web/API/Push_API

Upvotes: 0

Related Questions