Web Push

Learn about the basic configurations for Web Push channel

Web Push

At the moment, web push notifications are supported for Chrome version 50 for desktop and Android, and only work on HTTPS sites.

Chrome Web Push

Add the CleverTap JavaScript Library

Integrate the CleverTap JavaScript library by following the Web Quick Start Guide.

Integrate FCM and CleverTap

FCM has deprecated its existing web push protocol after July 2019 and moved to the VAPID protocol.

If your server key is generated before July 2019, the legacy protocol will continue to work. However, if they were generated after July 2019, only the VAPID protocol will be supported.

We recommend using the VAPID protocol due to increased security.

Legacy Protocol

Get your server key, then use the following steps:

  1. In the CleverTap dashboard, navigate to Settings > Engage > Channels > Web Push.
  2. Under the Chrome Web Push section, add your server key.
  3. Click Save.
2128

Add FCM API Key

VAPID Protocol

Get your public and private key pair from Firebase with the following steps:

  1. In the Firebase console, navigate to your Project > Project Settings > Cloud Messaging > Web Configuration.
  2. Click Generate key pair.
2880

Generate Key Pair

  1. In the CleverTap dashboard, navigate to Settings > Engage > Channels > Web Push.
  2. Select Use VAPID spec.
  3. Under the Chrome Web Push section, add your generated public and private key pairs.
  4. Click Save.
2118

Update FCM Server and API Keys

📘

Re-subscription of Users

After you move from legacy to the VAPID protocol, we recommend re-subscribing the users with legacy tokens to move them to VAPID. In this case, the permission pop-up will not re-appear. The subscription will happen in the browser's background silently.

To help you in the migration process, we also support the legacy protocol simultaneously, even though VAPID is enabled. This ensures web push delivery across all your subscribed users.

Firefox Web Push

This section covers the Firefox web push.

📘

Mobile Devices

At the moment, we do not support web push on Safari browsers for mobile devices.

Add the CleverTap JavaScript Library

Integrate the CleverTap JavaScript library by following the Web Quickstart Guide.

Generate VAPID keys

The VAPID keys can be generated using the following methods:

  1. Using npm package name web-push (recommended).
  2. You can also use VAPID keys generated for Chrome web push in FCM account. For more information, refer to VAPID Protocol. The same VAPID keys will be valid for Chrome as well as Firefox web push.

Paste VAPID Keys in CleverTap

Get your VAPID keys, then use the following steps:

  1. In the CleverTap dashboard, navigate to Settings > Engage > Channels > Web Push.
  2. Under the Firefox Web Push section, add your generated VAPID public and private key pairs.
  3. Click Save.
1448

Add VAPID Public and Private Key Pairs

Add the Service Worker File

This section is applicable to Chrome and Firefox browsers. Push notifications on browser use a special script called a service worker that listens for web pushes. Since the execution of these scripts is managed by the browser in the background, users can receive push notifications from your website even when they are not on your site. To get started, download the service worker file we have provided and copy it in your document root of your website in order to make it publicly accessible.

Download the service worker file from this JavaScript code. As mentioned above, you will have to host this file in your document root.

Integration with Existing Service Worker File

Import CleverTap's service worker at the start of your existing service worker. Add the following code snippet:

importScripts('https://s3-eu-west-1.amazonaws.com/static.wizrocket.com/js/sw_webpush.js');// remove CleverTap server worker from your root folder

Safari Web Push

This section covers the Safari web push.

📘

Mobile Devices

At the moment, we do not support web push on mobile devices.

Dashboard Setting

Enable Safari web push with the following steps:

  1. In the CleverTap dashboard, navigate to Settings > Engage > Channels > Web Push.
  2. Under the Safari Web Push section, select the toggle Safari Web Push.
  3. Provide your credentials.
  4. Click Save.
1448

Update Safari Web Push

Set Safari

To setup a Safari web push certificate, follow the steps below:

In OS X v10.9 and later, you can dispatch Safari push notifications from your webserver to OS X users by using the Apple Push Notification service (APNs). This is different from local notifications because push notifications can reach your users even if your website or Safari browser is not open.

1352

Safari Web Push Certificate Set Up Steps

To integrate push notifications on your website, you must first present an interface that allows the user to opt-in to receive notifications. If the user consents, Safari requests for its credentials on your website in the form of a file called a push package. The push package also contains notification assets used throughout OS X and data used to communicate to a web service that you must configure. If the push package is valid, you receive a unique identifier also known as device token for the user. The user receives the notification when you send the combination of this device token and your message, or payload to APNs.

This guide helps you with process management and maintaining a coherent way of getting your service implemented.

The following steps cover how to implement your service:

  1. Generate your push certificate. You will require the Apple WWDRCA certificate provided by Apple from your developer portal to send notifications. Another certificate is needed when actually sending notifications and also, while creating the push package.

While not mentioned in Apple’s official documentation, you will need two certificates:

  • For registering app with APNs.
  • Establishing a token-based connection to APNs.
  1. Configure the raw push package folder and then, use the companion PHP file to zip up your final push package. We will also check for any issues while creating the push package in the debugging section.

Your push package is a folder of icons and configurations used by each Mac device that subscribes to your notification service.

  1. Create a webserver to verify your push package.

  2. Run the front end Javascript to subscribe to your notifications and get the device token that is returned. Granting client access to your notifications is easy using Javascript. If a valid push package is returned, access is granted and a device token is given in a JSON response.

Generate Push Certificate

You must register in the Certificates, Identifiers & Profiles section of your developer account to send push notifications. You must have an Apple developer license to register.

  • Identifier: This is your unique reverse-domain string, such as web.com.example.domain (the string must start with web). This is also known as the Website Push ID.
  • Website push ID description: This is the name used throughout the provisioning portal to refer to your website. Use it for your own benefit to label your website push IDs into a more human-readable format.
1600

Enable WebSite Push IDs

1600

Generate Push Certificate

After the push ID is registered, create a production certificate of that push ID by clicking Create Certificate under Edit your Identifier Configuration.

1387

Create Production Certificate

If you already have the certificate signing request, then upload the file from your local machine. If not, refer to Create a certificate signing request in the Apple documentation.

1600

Upload a Certificate Signing Request

You can download the push certificate after the certificate signing request is uploaded:

1600

Download Push Certificate

Double-click the downloaded certificate and add it to your keychain:

  1. Navigate to your Keychains > My Certificates.
  2. Select your certificate and private key.
990

Add Keychain to the Certificate

  1. Export both as .p12.
  2. Add a password. This step is very important.
824

Add a Password

You will require one more certificate named Apple Worldwide Developer Relations Certification Authority. You can download it from the Apple Certification Authority.

  1. Add the AWDRCA certificate to the keychain and export it as .pem file.
  2. Sign the push package with both the web push certificate and the intermediate certificate.
1600

Add Apple Worldwide Developer Relations Certification Authority (AWDRCA) Certificate

Create a Push Package

When a user is asked for permission to receive push notifications, Safari asks your webserver for a package. The package contains data that is used by the notification UI, such as your website name and icon, as well as a cryptographic signature. The signature verifies that your notification has not been intercepted by a man-in-the-middle attack and that it is indeed coming from a trusted source.

Below is the folder structure you must create:

pushpackage/
    icon.iconset/
        icon_16x16.png
        [email protected]
        icon_32x32.png
        [email protected]
        icon_128x128.png
        [email protected]
     manifest.json
     signature
     website.json

Website JSON

The website JSON dictionary named website.json contains metadata used by Safari and Notification Center to present UI to the user and to communicate with your web service.

KeyDescription
websiteNameThe website name. This is the heading used in the Notification Center.
websitePushIDThe website push ID as specified in your developer account.
allowedDomainsAn array of websites that are allowed to request permission from the user.
urlFormatStringThe URL to go to when the notification is clicked. Use %@ as a placeholder for arguments you fill in when delivering your notification. This URL must use the http or https scheme; otherwise, it is invalid.
authenticationTokenA string that helps you identify the user. It is included in later requests to your web service. This string must be 16 characters or greater.
webServiceURLThe location used to make requests to your web service. The trailing slash should be omitted. This should be https.

Following is a sample valid website.json file:

{
    "websiteName": "Bay Airlines",
    "websitePushID": "web.com.example.domain",
    "allowedDomains": ["http://domain.example.com"],
    "urlFormatString": "http://domain.example.com/%@/?flight=%@",
    "authenticationToken": "19f8d7a6e9fb8a7f6d9330dabe",
    "webServiceURL": "https://example.com/push"
}

Iconset

The iconset is a directory called icon.iconset that contains PNG images in varying sizes. The images in your iconset populate the icons displayed to the user in the permission prompt, Notification Center, and the notification itself. Since your icon is static, it is unnecessary to include it in every push notification. Instead, your icons are downloaded once from your server and stored on the user’s computer.

The icons should be valid as per the Apple guidelines. Use https://tinypng.com/ to compress your icons to the required size.

Manifest

A manifest is a JSON dictionary named manifest.json that contains an entry for each file where the local file path is the entry’s key and a dictionary object is the entry’s value. This dictionary contains the hashType and hashValue which is the file’s SHA512 checksum.

Signature

The signature is a PKCS #7 detached signature of the manifest file. Sign the manifest file with the private key associated with your web push certificate that you obtained while registering with Apple.

We will use a PHP file named createPushPackage.php to generate the zip file for the pushpackage folder above. The folder to create a push package is present in the solution under the folder named “safari_push_package_creator”.

  1. Copy and paste the following files in one folder:
  • .p12 certificate we created above by registering.
  • PHP file.
  • .pem file created using AWDRCA certificate.
  • Create a tmp folder, then pushPackage inside it.
  1. Create one pushpackage.raw folder and paste the following files in it:
  • icon.iconset folder and all the icons mentioned above in it.
  • Website.json as per the guidelines mentioned above.
  1. Open the PHP file and modify it as per the following instructions:
  • Change $certificate_path to path of .p12 certificate.
  • Change $certificate_password to password of .p12 certificate.
  • Replace "<path to .pem>" under create_signature with path to .pem file.
  • Change $package_dir to path to tmp/pushPackage directory.

The AWDRCA.pem file is mandatory after 2014 for security purposes.

  1. After the above steps are done, run the PHP file in the terminal:
    php createPushPackage.php

If run successfully under the tmp folder, a pushPackage.zip file will be created. You can place this pushPackage.zip in your web service directory which will send the pushPackage.zip to the client when a request for Safari push notifications will be requested.

🚧

Considerations

Some things to consider:

  • All the files must be present.
  • Use the zipping method used in the PHP file attached as the order of the files is important.
  • Icons must be valid.
  • Use the valid certificates. If they expire, renew them.

Code Overview

This overview covers the client-side and web service code that return the pushPackage.zip file to the client (Safari browser).

Webserver

When Safari requests permission to display push notifications, an HTTPS request for credentials is sent to your webserver. Configure a RESTful HTTPS web service on your webserver to respond to these requests. The web service can be hosted on any server or domain. The webserver allows the request for push notification and sends a push package (application/zip format) to Safari. This push package is verified by Safari and it sends a push token to the CleverTap SDK.

FragmentDescription
webServiceURLThe URL to your web service; this is the same as the URL parameter in window.safari.pushNotification.requestPermission(). It must start with https.
versionThe version of the API. Currently, “v1”.
deviceTokenThe unique identifier for the user on the device.
websitePushIDThe website push ID.

Configure endpoints in a RESTful https web service on your server to respond:

  1. Download your website package.
    This POST request contains the following information:

The URL format is webServiceURL/version/pushPackages/websitePushID
For example: https://yourwebsite.com/v1/pushPackages/web.com.yourwebsite

  1. Register or update the device permission policy.
    This POST request contains the following information:

The URL format is webServiceURL/version/devices/deviceToken/registrations/websitePushID
For example: https://yourwebsite.com/v1/devices/deviceToken/registrations/web.com.yourwebsite

  1. Forget the device permission policy.
    This DELETE request contains the following information:

The URL format is webServiceURL/version/devices/deviceToken/registrations/websitePushID
For example: https://yourwebsite.com/v1/devices/deviceToken/registrations/web.com.yourwebsite

  1. Log errors.
    If an error occurs, a POST request is sent to the following URL:

The URL format is webServiceURL/version/log
For example: https://yourwebsite.com/v1/log

Client Side Code

To request permission to send the user push notifications, call the window.safari.pushNotification.requestPermission() method.

Requesting permission is an asynchronous call
window.safari.pushNotification.requestPermission(url, websitePushID, userInfo, callback);

A description of each argument is as follows:

  • URL: The URL of the web service which must start with https. The webserver and the website requesting permission can have different domains.
  • websitePushID: The website push ID as specified in your developer account for the generated certificate. It follows the convention on an Apple account and must start with web. For example, web.yourname.safari is a Safari certificate ID.
  • userInfo: An object required to pass to the server. Include any data in this object that helps you identify the user requesting permission.
  • callback: A callback function which is invoked on completion.

Following is a sample code:

//For Safari
function requestPermission() {
    if ('safari' in window && 'pushNotification' in window.safari) {

        var permissionData =
            window.safari.pushNotification.permission('web.pjay.push');
        window.safari.pushNotification.requestPermission(
            'https://localhost:8443/Push_notification_war_exploded',
            'web.pjay.push', {}, function(subscription) {
                console.log(subscription);
                if(subscription.permission === 'granted') {
                    subscriptionInfoSafari = subscription;
                    safariToken = subscription.deviceToken;
                    sending(safariToken);
                    // updateSubscriptionOnServer(subscription);
                }
                else if(subscription.permission === 'denied') {
                    // TODO:
                }
            });

    } else {
        alert("Push notifications not supported.");
    }
}

Troubleshooting

If there is an issue with downloading the push package or delivery of push notifications, the logging endpoint on your web service as described in the Log errors (section above) is contacted with an error message and error description.

The following table lists the possible errors and steps you can take to fix them:

Error MessageResolution
AuthenticationToken must be at least 16 charactersThe authenticationToken key in your website.json file must be 16 characters or greater.
Downloading push notification package failedThe Safari push package could not be retrieved from the specified location.
Extracting push notification package failedCheck that your push package is zipped correctly.
Missing file in push notification packageCheck that your push package contains all of the files specified in building the push package.
Missing image in push notification packageCheck that your push package contains all of the files specified in the iconset folder.
Missing key in website.jsonCheck that your website.json file has all of the keys listed in the Website JSON dictionary.
Serialization of JSON in website.json failedThe website.json file in your push package is not valid JSON.
Signature verification of push package failedThe manifest was not signed correctly or was signed using an invalid certificate.
Unable to create a notification bundle for push notification packageThe extracted push package could not be saved to the user’s disk.
Unable to generate ICNS file for push notification packageYour iconset may have malformed PNGs.
Unable to parse webServiceURLCheck that the value for webServiceURL in your website.json file is a valid URL.
Unable to save push notification packageThe push package could not be saved to the user’s disk.
urlFormatString must have http or https schemeMake sure that the value for urlFormatString in your website.json file starts with http or https.
Verifying hashes in manifest.json failedThe SHA512 checksums specified in your manifest.json file do not compute to their actual values.
Web Service API URL must be httpsMake sure that the URL at your push package endpoint starts with https.
webServiceURL must be equal to URL in call to requestPermissionCross-check that the web service URL in your JavaScript call matches the Web service URL in your website.json file.
websitePushID must be equal to identifier in call to requestPermissionCross-check that the identifier in your JavaScript call matches the identifier in your website.json file.
x cannot be used as a format string for URLsThe URL created by inserting the notification payload’s url-args values into the placeholders specified in the push package’s urlFormatString is not valid, or there are a different number of values than placeholders.

Requesting User Permissions

This section is applicable for all browsers such as, Chrome, Firefox, and Safari. Now that you have a service worker and manifest set up, it is time to start asking users if they want to subscribe to web pushes. For flexibility, CleverTap provides you with the ability to ask for notifications based on context and user actions.

As a general rule, we highly recommend asking for permission from users only after they have spent some time on your website and completed action of significance. Do not ask new users to subscribe to notifications as soon as they land on your site.

For example, after a user has completed a transaction, you may call the function below:

clevertap.notifications.push({
  "apnsWebPushId":"<apple web push id>", //only for safari browser
  "apnsWebPushServiceUrl":"<safari package service url>",//only for safari browser
  "titleText":'Would you like to receive Push Notifications?',
  "bodyText":'We promise to only send you relevant content and give you updates on your transactions',
  "okButtonText":'Sign me up!',
  "rejectButtonText":'No thanks',
  "okButtonColor":'#f28046'});

The general format for creating the pop-up is shown below:

clevertap.notifications.push({
    "titleText":popupTitleText,
    "bodyText":popupBodyText,
    "okButtonText":okButtonText,
    "rejectButtonText":rejectButtonText,
    "okButtonColor":okButtonColorInHex});

The custom service worker format for notification permission pop-up is shown below:

clevertap.notifications.push({
	"apnsWebPushId": "<apple web push id>",
	"apnsWebPushServiceUrl": "<safari package service url>", 
   	"titleText": "Would you like to receive Push Notifications?",
   	"bodyText": "We promise to only send you relevant content and give you updates on your transactions",
   	"okButtonText": "Sign me up!",
   	"rejectButtonText": "No thanks",
   	"okButtonColor":"#F28046",
   	"askAgainTimeInSeconds":5,
  	"serviceWorkerPath": "/foo/my_sw.js" // path to your custom service worker file
  });

If a user blocks the native Chrome permissions pop-up, the user is lost forever unless the user clears their browser settings; however, if you are using the CleverTap pop-up, you get the advantage of asking the same user again for permission after a defined period.

Permission Frequency

To ensure that users are not asked for permission too frequently, our API ensures that calling clevertap.notifications.push does nothing if the user has rejected the dialog less than one week ago. Once a week has passed by, calling the function will display the dialog as expected. This eliminates the need for you to implement a separate check before calling the function.

To set a separate frequency, send "askAgainTimeInSeconds":time_in_seconds along with the above object.

To skip the CleverTap pop-up, send "skipDialog":true along with the object above.

Migrating from Other Services

This section is applicable for all browsers such as, Chrome, Firefox, and Safari. If you are migrating from a different web push notifications provider, you may be concerned about asking subscribed users to enable notifications a second time.

📘

Migrating Subscribed Users

If a user has already enabled notifications on your host domain, calling clevertap.notifications.push will not display the pop-up for that particular user and the registration will automatically be migrated to our new implementation.

You can use the custom service file below which should only be used during the migration phase. Once the token migration of most of your users is complete, you can replace it with the parent service worker.

importScripts('https://s3-eu-west-1.amazonaws.com/static.wizrocket.com/js/sw_webpush_only_registration.js');