How we implemented push notifications on our website
Too many websites use push notifications irresponsibly. They will prompt users to signup the moment they visit the site, without providing any value to people first.
This not only hurts the user experience, it’s also a risky business. If a user denies a site access at the start, that site might not be able to ask for it again, as permission will be blocked (In Chrome).
This is not to say push notifications are a bad technology in itself. When used responsibly, they offer a way to form a connection between people and the content they want.
Our Approach
We wanted a responsible way of using push notifications on our website. At the end of each blog post, we show these buttons to allow guests to get notified when new posts arrive.
When people click the notification button, the browser will prompt for permissions:
At any time, users have the ability to turn off notifications on the website after signing up.
Under the hood
There is both front and back-end logic behind the solution. The front-end has a Service Worker to listen to messages when people are not browsing the site. Meanwhile, the back-end stores subscriptions and sends messages to its registered browsers.
Instead of building all this ourselves, we decided to use OneSignal as our push notification provider. OneSignal enables us to easily send messages, manage subscriptions and more.
OneSignal has an additional support for Safari on macOS that uses a non-standard way for push notifications. Here is the complete browser support:
The browser support will broaden further going forward.
Show me the code!
The OneSignal documentation is quite good. However, it doesn’t include a full example for our approach, so let’s go through it in this post.
As a start, we added OneSignal to our site.
<script src="https://cdn.onesignal.com/sdks/OneSignalSDK.js" async></script>
<script>
var OneSignal = window.OneSignal || [];
</script>
Notice the async keyword to prevent the script from blocking rendering of the page. All of OneSignal calls are in-fact asynchronous.
Calling init
The next step is to initialise OneSignal.
OneSignal.push(() => {
OneSignal.init({
appId: "<APP_ID>",
safari_web_id: '<SAFARI_WEB_ID>',
autoRegister: false,
allowLocalhostAsSecureOrigin: true,
welcomeNotification: {
title: '14islands',
message: 'We will keep you posted!'
},
promptOptions: {},
notifyButton: { enable: false }
})
})
We got app_id and safari_id under the App Settings in the OneSignal Dashboard after creating a new app in there.
The allowLocalhostAsSecureOrigin: true flag will treat http://localhost and http://127.0.0.1 as a secure origin. In production, push notifications require HTTPS to work.
It’s important not to call the init method more than once. Doing so results in an error.
Progressive enhancement
Push notifications are not supported by all browsers. For those browsers, we only show the newsletter signup form on our website - in a true progressive enhancement fashion.
The newsletter signup form works on all browsers and even without JavaScript enabled.
Next, we check if there is support and show the notification button in those cases.
OneSignal.push(() => {
this.showNotfications = OneSignal.isPushNotificationsSupported()
if (this.showNotfications) {
this.$context.addClass('show-notifications')
}
})
In the CSS, the show-notifications class will switch to the view showing both buttons.
Subscribe
When people click
the “Get Notification” button they will be subscribed.
OneSignal.push(() => {
OneSignal.registerForPushNotifications()
OneSignal.setSubscription(true)
})
A welcome notification is sent out at this point. It’s a nice way to give feedback to people that they are now receiving notifications.
In the constructor, we have the following code to detect if the user is subscribed and respond to subscription changes.
OneSignal.push(() => {
// Check if subscribed on load
OneSignal.isPushNotificationsEnabled().then((isSubscribed) => {
this.$context.toggleClass('is-subscribed-to-push', isSubscribed)
})
// Check if user hits the subscribe button
OneSignal.on('subscriptionChange', (isSubscribed) => {
this.$context.toggleClass('is-subscribed-to-push', isSubscribed)
})
})
In the CSS, the is-subscribed-to-push
will show the “Turn off Notification” button.
Turn off notification
People unregister when they click
the “Turn off” button.
new window.Notification('14islands', {
body: 'Notifications are now turned off.',
icon: '/icons/android-chrome-192x192.png'
})
OneSignal.push(() => {
OneSignal.setSubscription(false)
})
We send out a notification using the standard Notification API. This is nice to give the user feedback for unregistering.
To summarize
Users should show intent before a site asks for a permission, and allow users easily to turn notifications off.
You can try out our implementation under the comments section below.
Write a comment