Node.jsNode.jsPhoneGapReact V4WebJavaScriptNode.JS V4 Mobile Push Gateway Tutorial for Realtime Apps

 
Requires that the Push Notifications add-on is enabled for your key. How do I enable add-on features for my keys? - see http://www.pubnub.com/knowledge-base/discussion/644/how-do-i-enable-add-on-features-for-my-keys
PubNub's Mobile Push Gateway feature enables developers to bridge native PubNub publishing with 3rd-party push notification services including Google Android GCM (Google Cloud Messaging)/FCM (Firebase Cloud Messaging), Apple iOS APNS (Apple Push Notification Service), and Microsoft Windows Phone MPNS (Microsoft Push Notification Service).
By using the Mobile Push Gateway, developers can eliminate the need for developing, configuring, and maintaining additional server-side components for 3rd-party push notification providers.
When to use Native PubNub Messaging vs PubNub Mobile Push Gateway to 3rd-Party Messaging Services
For mission critical messaging, PubNub recommends implementing PubNub native messaging functionality. PubNub native messaging touts a low-latency, bi-directional notification solution that can be delivered to any mobile device, secure, access restricted, and encrypted message payloads of 32KB, and the ability to recover missed messages with Storage & Playback (history) APIs.
Despite the advantages of the native PubNub approach, there are cases where a developer may choose to utilize a 3rd-party notification system, for example, when migrating existing applications already utilizing 3rd-party notification systems to PubNub native messaging. On iOS applications where running in the background is not an option, the Mobile Push Gateway provides a method to send messages quickly and reliably via PubNub whether or not the application is in the foreground or background.
When publishing a message associated with an APNS deviceID, the message is sent to all PubNub native subscribers listening on that channel. For example, if you have native PubNub Python, Ruby, and JavaScript subscribers listening on channel "foo", and you've previoulsy associated channel "foo" with APNS deviceIDs abc, and xyz, when you publish "hello world" to channel "foo", it will be received by the PubNub native Python, Ruby, and JavaScript subscribers.
In addition, the portion of the message encapsulated within a "pn_apns" attribute, containing a valid APNS object messaging format (see below), will also be forwarded to Apple's APNS gateway, where it will be sent via APNS to Apple devices with APNS deviceIDs abc and xyz.
Behind the scenes, the PubNub Mobile Push Gateway establishes an authenticated connection to the Apple APNS service based on the application's configured Apple Push Certificate (which the developer has uploaded to the PubNub Admin Console). Assuming this certificate, and application are configured correctly for Push Notifications, and the deviceID has been associated with the PubNub channel the message was published on, Apple will accept the APNS message for delivery.
PubNub supports both PushKit APNS and VoIP push notifications. Apple Push Notification services require that a Push Certificate (APNS or VoIP) be generated that uniquely identifies your PubNub enabled application to the APN service. This Push Certificate is uploaded to PubNub in the PubNub Admin Portal and is used to form a secure connection to the APN service.
Additional information on creating and verifying your certificate can be found at https://github.com/pubnub/objective-c/tree/v3.7.11/iOS/create_and_verify_apns.md.
Similarly, a Device Token is created for each client iOS device that registers with Apple to receive push notifications. The Device Token is analogous to a phone number; it contains information that enables APNs to locate the device on which the client application is installed.
Before you can push APNS messages natively through Apple, or through PubNub, you must first define an App ID and create a PEM Certificate file. http://code.google.com/p/apns-php/wiki/CertificateCreation#Generate_a_Push_Certificate depicts a quick summary of the steps.
Verify your development cert was created correctly by running this command (replace with your key/cert name):
openssl s_client -connect gateway.sandbox.push.apple.com:2195 -cert server_certificates_bundle_sandbox.pem -key server_certificates_bundle_sandbox.pem
	
To verify production certs, replace gateway.sandbox.push.apple.com with gateway.push.apple.com (remove the sandbox portion of the name). Once they are verified, upload them to the PubNub Admin Console's Mobile Push Gateway configuration.
In addition to the above steps, We also provide a step-by-step video tutorial of the process:
Two files referenced from the video, generateAPNSPemKey.sh and verifyCertWithApple.sh are also available in our Github repo. The Final product is available here: HOWTO/APNSVideo
Normally, messages published to PubNub Reatime Network are only accessible by native PubNub subscribers, routed by subscribe key and channel name. When messages are published to a PubNub channel associated with the APNS Device Token, the Device Token is used to identify which devices should receive the message as a push notification. The Device token is combined with the published message and this Notification Package is sent from PubNub Mobile Push Gateway to the APN service.
Apple enforces that both APNS Push Certificates and Device Tokens must be created and used separately for Development and Production environments.
A notification is a short message consisting of two major pieces of data: the Device Token and the Payload. The Apple Notification Payload contains information about how the system should alert the user as well as any custom data you provide.
 
As noted on Apple's Developer site here
Each remote notification includes a payload. The payload contains information about how the system should alert the user as well as any custom data you provide. In iOS 8 and later, the maximum size allowed for a notification payload is 2 kilobytes; Apple Push Notification service refuses any notification that exceeds this limit. (Prior to iOS 8 and in OS X, the maximum payload size is 256 bytes.)
The forementioned site also continues to explain that: Each notification payload is composed of a JSON dictionary object (as defined by link: RFC 4627). This dictionary must contain another dictionary identified by the key aps. The aps dictionary contains one or more properties that specify the following actions:
  • An alert message to display to the user
  • A number to badge the application icon with
  • A sound to play
The following JSON messages detail the structure the PubNub Mobile Push Gateway expects to properly route a message to a channel associated with an APNS deviceID.
For the most simple test, you can send a simple String, such as hello world from any PubNub publishing entity, including the PubNub Developer Console available at http://www.pubnub.com/console/:
When sending the above string to a channel associated with an iOS DeviceID, if everything is in place, the device should display "hello world" when the application is in the background. You should only send strings to test connectivity; once you've verified connectivity, send notifications in object format which can contain alert, badge count, and sound data:
{
	"pn_apns": {
		"aps": {
			"alert": "This is a push notification",
			"badge": 9,
			"sound": "bingbong.aiff"
		}
	}
}
Its critical that the above structure be followed. Apple will drop any messages destined for APNS that do not follow the forementioned object structure.
 
FCM is just a rebranding of GCM and there is no function difference to handle it in PubNub. The PubNub server's still expect a pn_gcm as part of the payload.
Before you can push GCM/FCM messages natively through Google, or through PubNub, you must first setup your GCM/FCM configuration.
Once you've obtained the API Key, login to the PubNub Admin Console, and scroll down to Push Notifications → Google Cloud Messaging and click on "Add" to add your API Key. https://developers.google.com/cloud-messaging/ provides additional information about this process.
When publishing a message associated with an GCM/FCM deviceID, the message is sent to all PubNub native subscribers listening on that channel. For example, if you have native PubNub Python, Ruby, and JavaScript subscribers listening on channel foo, and you've previoulsy associated channel foo with GCM/FCM RegistrationIDs abc, and xyz, when you publish hello world to channel foo, it will be received by the PubNub native Python, Ruby, and JavaScript subscribers.
In addition, the portion of the message encapsulated within a pn_gcm attribute, containing a valid GCM/FCM object messaging format (see below), will also be forwarded to Googles's GCM/FCM gateway, where it will be sent via GCM/FCM to Android devices with GCM/FCM RegistrationIDs abc and xyz.
Behind the scenes, the PubNub Mobile Push Gateway establishes an authenticated connection to the Google GCM/FCM service based on the application's configured GCM/FCM API Key (which the developer has uploaded to the PubNub Admin Console). Assuming this API key, and application are configured correctly for Push Notifications, and the RegistrationID has been associated with the PubNub channel the message was published on, Google will accept the GCM/FCM message for delivery.
This key is used by Google to authenticate your application for accounting purposes. This key is uploaded to the PubNub Administrator Console upon configuring your PubNub account to enable Mobile Push Gateway.
The first time an Android application needs to use the GCM/FCM service, it must call the GoogleCloudMessaging method register() which should return a Registration ID. This Registration ID is then associated with one or more channels. The Android application should store this ID for later use (for instance, to check in onCreate() if it is already registered.
The Sender ID is created during the GCM/FCM registration process ( Sender ID is your GCM/FCM Project Number ) and is used to permit PubNub Mobile Push Gateway push notification messages to be sent to the Android device via GCM/FCM.
When sending the following object to a channel associated with a GCM/FCM Registration ID, if everything is in place, the device should receive the object {"summary":"hello world"} when the application is in the background or foreground.
{
    "pn_gcm": {
        "data" : {
            "summary": "hello world"
        }
    }
}
This dictionary must contain another dictionary identified by the key pn_gcm. When sending a message to GCM/FCM you must use the data parameter to include a message payload.
It is possible to structure a single message to contain different message payloads for native PubNub and multiple 3rd-Party endpoints. To do this, just specify root-level pn_apns, pn_gcm and pn_mpns keys with appropriate platform-specific data. Its important to remember that Native PubNub devices will receive the ENTIRE payload, but 3rd-Party endpoints will only receive the data encapsulated in their associated pn_* key.
In the below example, associated iOS devices will receive only the data within the pn_apns key, and associated GCM/FCM devices will receive only the data within the pn_gcm key. Native PubNub subscribers will receive the entire literal object, including pn_apns, pn_gcm and full_game keys.
{
    "pn_apns": {
        "aps" : {
            "alert": "Game update 49ers touchdown",
            "badge": 2
        },
        "teams" : ["49ers", "raiders"],
        "score" : [7, 0]
    },
    "pn_gcm": {
        "data" : {
            "summary": "Game update 49ers touchdown",
            "teams" : ["49ers", "raiders"],
            "score" : [7, 0],
            "lastplay" : "5yd run up the middle"
        }
    },
    "full_game" : {
        "date" : "2014.05.20",
        "foobar" : "Data that is not pertinent to devices"
    }
}
For any given published message, you may include any combination of pn_* and non-pn_* keys and data.
To modify associations between a channel and an APNS or GCM/FCM Device ID, use the .mobile_gw_provision() method:
pubnub.mobile_gw_provision ({
    device_id: 'A655FBA9931AB',
    op       : 'add', // or 'remove'
    gw_type  : 'apns', // or 'gcm'
    channel  : 'my_chat',
    callback : mySuccessCallback,
    error    : myErrorCallback,
});
After successfully associating device IDs with channels, publishing messages in the correct formats to those channels will result in all associated devices receiving the 3rd-party notifications.
Inform customers of unregistered/inactive push devices via a webhook (similar to presence webhooks).
The following events will trigger the webhook. All errors should trigger immediately after a push (except for feedback which can happen after 5 minutes of a push).
  • Feedback -­ Apple feedback service ­- PubNub push server polls the feedback server after 5 minutes of a push to get list of inactive/uninstalled devices.
  • Remove - Invalid token error -­ Usually indicates when a sandbox token is used in production or vice versa.
  • Update -­ Canonical ID -­ The device has multiple tokens (old and new), replace the old token with new token.
  • Remove - NotRegistered - App was uninstalled or no longer configured for push notifications.
	HTTP POST
	Content­Type: application/json
	{
		"sub_key" : <sub­key>,
		"action" : <action contains extra details about how the device was removed ­ see events section>
		"device" : <device token>,
		"platform" : "apns|gcm|mpns",
		"timestamp" : <unix timestamp (utc) when the device was removed>
	}
An APNS device was uninstalled from feedback.
	{
		"sub_key" : "sub­c­e0d8405a­b823­11e2­89ba­02ee2ddab7fe",
		"action" : "feedback",
		"device" :"904181a3fc8bfaf95cc40551d81b5b8d0bd1d42c38b1e496648132a555325e8c",
		"platform" : "apns",
		"timestamp" : 1444241230
	}
A GCM/FCM device was updated from old token APA91bEgK4D to new token ta28zYhV.
	{
		"sub_key" : "sub­c­4745b1e4­19ba­11e4­bbbf­02ee2ddab7fe",
		"action" : "update",
		"old_device": "APA91bEgK4D"
		"device" : "ta28zYhV"
		"platform" : "gcm",
		"timestamp" : 1441230130
	}
A MPNS device was uninstalled.
	{
		"sub_key" : "sub­c­8a888f2c­d7a1­11e3­8c07­02ee2ddab7fe",
		"action" : "remove",
		"device" : "http://sn1.notify.live.net/throttledthirdparty/01.00/AQG2MdvoLlZFT7­VJ2TJ5LnbAgAAAAADAQAAAAQUZm52OkRFNzg2NTMxMzlFMEZFNkMFBlVTU0MwMQ"
		"platform" : "mpns",
		"timestamp" : 1400218910
	}
 
If a device has been registered to receive Mobile Push Gateway messages via GCM/FCM, APNS, or MPNS, and is also running a native PubNub Android, iOS, or Windows client SDK, and is natively subscribed to the same associated channel via the native PubNub client SDK, it will receive the message twice -- once via the Mobile Push Gateway, and once via the native PubNub client SDK. You will need to manually add logic to de-duplicate in this case.

If you are experiencing issues publishing to devices via the PubNub Mobile Gateway, the following are debug techniques that may help narrow down the issue. Each of them circumvents PubNub's Mobile Push Gateway logic to ensure that your device push tokens, applications, and registration/certificates are configured correctly.

If the following scripts are not working for you, then PubNub isn't a variable in the cause of the issue -- successful results with the below scripts script is a pre-requisite for PubNub Mobile Gatway logic to work.  Regardless if its a PubNub issue or not, we're always happy to help!  By getting us the results of the following tests when opening a support ticket, it may save a lot time isolating the root cause of your issue.

Use this script to publish a message to APNS, completely circumventing PubNub infrastructure. It requires an APNS certificate and an iOS device token.

Use the following curl command to publish a message to GCM/FCM, completely circumventing PubNub infrastructure. It requires a registration ID. Taken from Google's GCM/FCM page.

    curl --header "Authorization: key=<API_KEY>" \
        --header Content-Type:"application/json" \
        https://gcm-http.googleapis.com/gcm/send \
        -d "{\"registration_ids\":[\"ABC\"]}"

Use the following curl command to publish a message to MPNS, completely circumventing PubNub infrastructure. It requires a device push token.

    curl -v -H "Content-Type:text/xml" -H "X-WindowsPhone-Target:Toast" -H "X-NotificationClass:2" -X POST -d "<?xml version='1.0' encoding='utf-8'?><wp:Notification xmlns:wp='WPNotification'><wp:Toast><wp:Text1>My title</wp:Text1><wp:Text2>My subtitle</wp:Text2></wp:Toast></wp:Notification>" http://dm2.notify.live.net/throttledthirdparty/01.00/AQGiZ6EjjX0ySLELCr3iykPvAgAAAAADBAAAAAQUZm52OkRFNzg2NTMxMzlFMEZFNkMFBlVTU0MwMQ

You have implemented mobile push notifications into your PubNub application but now you are having some troubles. Maybe it's missing messages on client devices, getting duplicate messages, getting messages meant for another user/device. Whatever it is, we will provide the best tools and techniques for finding the root cause and resolving, or at least just getting all the necessary data points to send to PubNub Support to assist with troubleshooting.

You can do some high level debugging using the channel's -pndebug channel and checking to see if the device is still registered to the channel. Messages from -pndebug come from the APNS and GCM/FCM services (from Apple and Google, not PubNub). Here are the steps:

  1. Use the PubNub Debug Console to subscribe to the channel's -pndebug channel. If the channel you are publishing to is foo, then subscribe to foo-pndebug. Make sure you use the right pub/sub keys.
  2. Add 'pn_debug':true to your message payload at the top level.
        {
            "pn_gcm": {
                "data": {
                    "message": "hello"
                }
            },
            "pn_apns": {
                "aps": {
                    "alert": "hello"
                }
            },
            "pn_debug": true
        }
  3. Publish the message to channel foo, not to the channel's -pndebug channel. You can publish from your client or server application or from another instance of Debug Console (again, make sure you use the same pub/sub keys). You should see useful error messages in the Debug Console where you are subscribing to foo-pndebug, if there are any problems with the push message registration.

The following message shows how many devices successfully received the push notification that were registered for push messages on the target channel for each push service.

Devices found for push notification apns: 2 gcm: 3 mpns: 0

The following messages are examples of the types of messages that GCM/FCM and APNS push services can send back to PubNub's mobile push notification gateway servers.

    gcm Error: InvalidRegistration Devices: null
    gcm WARNING error: NotRegistered, sub_key: sub-c-..., channel: my_channel, reg_id: APA91bHRRxfHHB_T0AVojoJx..., timetoken: 14567269547473296
    apns INFO Certificate for sub-c-... valid (expiration: Sep 14 08:58:26 2016 GMT)
    apns ERROR Error on APNS send for subkey sub-c-... / channel gone_fishing / device 2a0a6234ffdb85df6624cf0546...: invalid token

All of the above messages can be sent to your server using PubNub's Mobile Push Gateway web hooks. A web hook is a URL (that you can have us configure on your keys) to a REST endpoint on your server. As messages come back to PubNub from the mobile push notification services, PubNub will relay them onto your REST endpoint for you to log and process as you require. Contact PubNub Support to request this configuration for your keys.

You can also check to see if the device is still registered to the channel after you publish the push notification using a simple REST URL in the browser.

  1. http://pubsub.pubnub.com/v1/push/sub-key/your_sub_key/devices/device_reg_token?type=push_type
  • where push_type is either gcm or apns
  • and device_reg_token is the device's registration token

This will return all channels the device is still registered for push notification for the push type provided.

Example of response:

["demo","demo1","demo2"]

If that list comes back empty then there was likely a device registration token issue (invalid token or device not registered, for example). This might happen because the device token was reported as invalid by the push notification services (APNS or GCM/FCM) and PubNub in turn unregisters that device token from all channels. But the -pndebug channel should reveal the reason for this to you.

Most times it is not PubNub that is causing the push notification issues. Often it is an invalid registration token (APNS or GCM/FCM) or a device with two valid registration tokens (yes, it can actually happen) or the push service cert or key is no longer valid. Testing push notifications without PubNub getting involved is the best way to eliminate, or hone in on, the area of probable fault.

There are a few good online tools for testing GCM/FCM push notifications and one native Mac app.

For APNS, you can run a simple Python script that uses your push certificate (.pem file) to verify that the certificate is valid. And optionally, you can specify a device registration token to which test push notifications will be sent. See our knowledge base article, How Do I Test My PEM Key, for full details.

For more rich UI/UX tools, you can find APNS test apps for the Mac (in the App Store) as well as online web apps:

See also:

  1. Apple Doc Troubleshooting Push Notifications

For additional platform and endpoint information, please see our detailed Android, Objective-C, Swift, and .NET Mobile Gateway guides.