Skip to content

Push Notifications

The remote notification client class helps your mobile applications use push notification capabilities provided by SAP Mobile Services. First, the mobile applications will need to obtain a push token from the FCM infrastructure and register it with the mobile services Push service. Once the Push token is registered, the mobile services administration infrastructure can be used to send the notification to devices.

Setting up FCM Capability for an Application

To enable FCM for your application, follow the Google documentation at Set Up a Firebase Cloud Messaging Client App on Android.

Note

Firebase Cloud Messaging (FCM) is the new version of GCM. It inherits the reliable and scalable GCM infrastructure and provides new features. See the FAQ to learn more. If you are integrating messaging in a new app, start with FCM. GCM users are strongly recommended to upgrade to FCM in order to benefit from new FCM features today and in the future.

You can find how to set up GCM at Set up a Firebase Cloud Messaging client app on Android.

Notifications

Registering a Device Token

Device tokens are the UUID codes generated by the FCM. The device token obtained from push infrastructures such as FCM should be registered with mobile services using the registerDeviceToken method of the RemoteNotificationClient class.

This method must be invoked from the UI thread. It takes the device token and RemoteNotificationParameters as parameters. The callback methods are invoked on the UI thread.

    RemoteNotificationParameters parameters = new RemoteNotificationParameters.Builder()
        .lastKnownLocation(new RemoteNotificationParameters.LastKnownLocation("32.80776", "12.456546"))
        .build();
    RemoteNotificationClient remoteNotificationClient = new RemoteNotificationClient();

    remoteNotificationClient.registerDeviceToken(token,parameters,
    new RemoteNotificationClient.CallbackListener() {
        @Override
        public void onSuccess() {
            //Code for processing a successful response...
        }

        @Override
        public void onError(Throwable result) {
            //Handle failure here...
            if (result instanceof HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    HttpException ne = (HttpException)result;
                    Log.e("Http Exception: " , ne.message() + ", with Error code: " + ne.code());
            } else {
                    Log.e("Exception occurred: ", result.getMessage());
            }
        }
        }
    );
    val parameters = RemoteNotificationParameters.Builder()
        .lastKnownLocation(RemoteNotificationParameters.LastKnownLocation("32.80776", "12.456546"))
        .build()
    val remoteNotificationClient = RemoteNotificationClient()

    remoteNotificationClient.registerDeviceToken(token, parameters,
        object : RemoteNotificationClient.CallbackListener {
            override fun onSuccess() {
                //Code for processing a successful response...
            }

            override fun onError(result: Throwable) {
                //Handle failure here...
                if (result is HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    Log.e("Http Exception: ", result.message() + ", with Error code: " + result.code())
                } else {
                    Log.e("Exception occurred: ", result.message)
                }
            }
        }
    )

Unregistering a Device Token

To disable notifications for mobile applications, delete the device token from the mobile service using the unregisterDeviceToken method. Once the unregistration is done, the server will not be able to send a push notification to the device.

This method must be invoked from the UI thread. The callback methods are invoked on the UI thread.

    RemoteNotificationClient remoteNotificationClient = new RemoteNotificationClient();

    remoteNotificationClient.unregisterDeviceToken(
        new RemoteNotificationClient.CallbackListener() {
            @Override
            public void onSuccess() {
                //Code for processing successful response...
            }
            @Override
            public void onError(Throwable result) {
                //Handle error here...
                if (result instanceof HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    HttpException ne = (HttpException)result;
                    Log.e("Http Exception: " , ne.message() + ", with Error code: " + ne.code());
                } else {
                    Log.e("Exception occurred: ", result.getMessage());
                }
            }
    }
    );
    val remoteNotificationClient = RemoteNotificationClient()

    remoteNotificationClient.unregisterDeviceToken(
        object : RemoteNotificationClient.CallbackListener {
            override fun onSuccess() {
                //Code for processing successful response...
            }

            override fun onError(result: Throwable) {
                //Handle error here...
                if (result is HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    Log.e("Http Exception: ", result.message() + ", with Error code: " + result.code())
                } else {
                    Log.e("Exception occurred: ", result.message)
                }
            }
        }
    )

Notification Feedback

SAP Mobile Services provides a feedback service that a mobile application can use to acknowledge the notification. Every notification message from the service carries a notificationid that uniquely identifies the notification. Using this unique identification value, the updateNotificationStatus method can be used to update the notification status.

The mobile service supports three statuses for feedback: NOTIFICATIONSTATUS.RECEIVED, NOTIFICATIONSTATUS.CONFIRMED and NOTIFICATIONSTATUS.CONSUMED. The code sample below shows how to provide received feedback.

This method must be invoked from the UI thread. It takes the device notification id and SettingsParameters as parameters. The callback methods are invoked on the UI thread.

    RemoteNotificationClient remoteNotificationClient = new RemoteNotificationClient();
    remoteNotificationClient.updateNotificationStatus(notificationId, RemoteNotificationClient.NOTIFICATIONSTATUS.RECEIVED,
        new RemoteNotificationClient.CallbackListener() {
            @Override
            public void onSuccess() {
                //Code for processing successful response...
            }

            @Override
            public void onError(Throwable result) {
                //Handle error here...
                if (result instanceof HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    HttpException ne = (HttpException)result;
                    Log.e("Http Exception: " , ne.message() + ", with Error code: " + ne.code());
                } else {
                    Log.e("Exception occurred: ", result.getMessage());
                }
            }
        }
    );
    val remoteNotificationClient = RemoteNotificationClient()
    remoteNotificationClient.updateNotificationStatus(notificationId, RemoteNotificationClient.NOTIFICATIONSTATUS.RECEIVED,
        object : RemoteNotificationClient.CallbackListener {
            override fun onSuccess() {
                //Code for processing successful response...
            }

            override fun onError(result: Throwable) {
                //Handle error here...
                if (result is HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    Log.e("Http Exception: ", result.message() + ", with Error code: " + result.code())
                } else {
                    Log.e("Exception occurred: ", result.message)
                }
            }
        }
    )

Support for Baidu Push

The remote notification API can be used to support the Baidu push service. Register and unregister the device token by specifying Baidu as the push service using SettingsParameter. The settings parameter should be configured prior to creating a RemoteNotificationClient instance.

The following example shows how to register a Baidu push token to mobile services:

    RemoteNotificationParameters parameters = new RemoteNotificationParameters.Builder()
        .lastKnownLocation(new RemoteNotificationParameters.LastKnownLocation("32.80776", "12.456546"))
        .build();
    //This following line specify that the target we are using is for BAIDU
    settingsParameters.setPushService(SettingsParameters.PushService.BAIDU);
    RemoteNotificationClient remoteNotificationClient = new RemoteNotificationClient();

    remoteNotificationClient.registerDeviceToken(token,parameters,
    new RemoteNotificationClient.CallbackListener() {
        @Override
        public void onSuccess() {
            //Code for processing successful response...
        }

        @Override
        public void onError(Throwable result) {
            //Handle failure here...
            if (result instanceof HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    HttpException ne = (HttpException)result;
                    Log.e("Http Exception: " , ne.message() + ", with Error code: " + ne.code());
            } else {
                    Log.e("Exception occurred: ", result.getMessage());
            }
        }
        }
    );
    val parameters = RemoteNotificationParameters.Builder()
        .lastKnownLocation(RemoteNotificationParameters.LastKnownLocation("32.80776", "12.456546"))
        .build()
    //This following line specify that the target we are using is for BAIDU
    settingsParameters.pushService = SettingsParameters.PushService.BAIDU
    val remoteNotificationClient = RemoteNotificationClient()

    remoteNotificationClient.registerDeviceToken(token, parameter,
        object : RemoteNotificationClient.CallbackListener {
            override fun onSuccess() {
                //Code for processing successful response...
            }

            override fun onError(result: Throwable) {
                //Handle failure here...
                if (result is HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    Log.e("Http Exception: ", result.message() + ", with Error code: " + result.code())
                } else {
                    Log.e("Exception occurred: ", result.message)
                }
            }
        }
    )

The following example shows how to unregister the Baidu push token from mobile services:

    //The following line specifies that the target we are using is for BAIDU
    settingsParameters.setPushService(SettingsParameters.PushService.BAIDU);

    RemoteNotificationClient remoteNotificationClient = new RemoteNotificationClient();

    remoteNotificationClient.unregisterDeviceToken(
        new RemoteNotificationClient.CallbackListener() {
            @Override
            public void onSuccess() {
                //Code for processing a successful response...
            }
            @Override
            public void onError(Throwable result) {
                //Handle error here...
                if (result instanceof HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    HttpException ne = (HttpException)result;
                    Log.e("Http Exception: " , ne.message() + ", with Error code: " + ne.code());
                } else {
                    Log.e("Exception occurred: ", result.getMessage());
                }
            }
    }
    );
    //The following line specifies that the target we are using is for BAIDU
    settingsParameters.pushService = SettingsParameters.PushService.BAIDU

    val remoteNotificationClient = RemoteNotificationClient()

    remoteNotificationClient.unregisterDeviceToken(
        object : RemoteNotificationClient.CallbackListener {
            override fun onSuccess() {
                //Code for processing successful response...
            }

            override fun onError(result: Throwable) {
                //Handle error here...
                if (result is HttpException) {
                    //HttpException type com.sap.cloud.mobile.foundation.networking.HttpException
                    Log.e("Http Exception: ", result.message() + ", with Error code: " + result.code())
                } else {
                    Log.e("Exception occurred: ", result.message)
                }
            }
        }
    )

Using PushService to Register Push Notifications

The SAP BTP SDK for Android (3.0.0 and later) provides a PushService API that simplifies push registration. Add the PushService instance to the SDKInitializer.start method to start the push service.

    SDKInitializer.INSTANCE.start(application, new MobileService[]{new PushService()}, null);
    SDKInitializer.start(application, PushService())

Using PushService to Display Notification Messages

PushService can add a listener to receive messages sent from the server. It can also customize the displayed notification messages.

    PushService pushService = new PushService();
    pushService.setPushCallbackListener((context, message) -> {
        ...
    });
    SDKInitializer.INSTANCE.start(application, new MobileService[]{pushService}, null);
    val pushService = PushService().apply {
        this.setPushCallbackListener { context, message ->
            ...
        }
    }
    SDKInitializer.start(application, pushService)

Here is an example of how to implement the listener. The example shows how to handle messages in both foreground and background situations. For the background scenario, the message will toast by Android system notification and it will jump to your application when the message is clicked. In the foreground scenario it will toast a dialog to notify the message regarding your current activity.

    public class FCMPushCallbackListener implements PushCallbackListener {

        @Override
        public void onReceive(Context context, PushRemoteMessage message) {
                // The following section is a sample for handling push messages. This could be customized
                // according to the needs of the concrete application.
                // ---------------------start of suggested customization--------------------------
            String textMsg = context.getResources().getString(com.sap.cloud.mobile.foundation.R.string.push_text);
            String notificationTitle = context.getResources().getString(com.sap.cloud.mobile.foundation.R.string.push_message);
            String notificationID = message.getNotificationID();

                if (message != null) {
                    if(message.getTitle() != null && !message.getTitle().isEmpty()){
                        notificationTitle = message.getTitle();
                    }else {

                    }
                    if(message.getAlert() != null && !message.getAlert().isEmpty()){
                        textMsg = message.getAlert();
                    }else {

                    }

                }
                if (isAppInBackground()) {
                    // background
                    Intent pushActivityStarter = new Intent(context.getApplicationContext(), PushNotificationActivity.class);
                    pushActivityStarter.putExtra(NOTIFICATION_DATA, message);
                    pushActivityStarter.putExtra(NOTIFICATION_ID_EXTRA,notificationID);
                    NotificationUtilities notUtils = new NotificationUtilities(context.getApplicationContext());
                    notUtils.showNotificationMessage(notificationTitle, textMsg, pushActivityStarter);
                } else {
                    // foreground
                    Activity foregroundActivity = AppLifecycleCallbackHandler.getInstance().getActivity();
                    foregroundActivity.getIntent().putExtra(NOTIFICATION_ID_EXTRA, notificationID);
                    foregroundActivity.getIntent().putExtra(NOTIFICATION_DATA, message);
                    PushNotificationActivity.presentPushMessage(foregroundActivity, notificationID);
                }

        }
        /**
        * Method checks whether the app is in background or not
        */
        public boolean isAppInBackground() {
            Lifecycle.State currentState = ProcessLifecycleOwner.get().getLifecycle().getCurrentState();
            return !currentState.isAtLeast(Lifecycle.State.RESUMED);
        }
    }
    class FCMPushCallbackListener : PushCallbackListener {

        override fun onReceive(context: Context, message: PushRemoteMessage) {
            // The following section is a sample for handling push messages. This could be customized
            // according to the needs of the concrete application.
            // ---------------------start of suggested customization--------------------------
            var textMsg = context.resources.getString(com.sap.cloud.mobile.foundation.R.string.push_text)
            var notificationTitle = context.resources.getString(com.sap.cloud.mobile.foundation.R.string.push_message)
            val notificationID = message.notificationID

            if (message != null) {
                if (message.title != null) {
                    notificationTitle = message.title
                } else {

                }
                if (message.alert != null) {
                    textMsg = message.alert
                } else {

                }

            }
            if (isAppInBackground) {
                // background
                val pushActivityStarter = Intent(context.applicationContext, PushNotificationActivity::class.java)
                pushActivityStarter.putExtra(NOTIFICATION_DATA, message)
                pushActivityStarter.putExtra(NOTIFICATION_ID_EXTRA, notificationID)
                val notUtils = NotificationUtilities(context.applicationContext)
                notUtils.showNotificationMessage(notificationTitle, textMsg, pushActivityStarter)
            } else {
                // foreground
                val foregroundActivity = AppLifecycleCallbackHandler.getInstance().activity
                foregroundActivity!!.intent.putExtra(NOTIFICATION_ID_EXTRA, notificationID)
                foregroundActivity.intent.putExtra(NOTIFICATION_DATA, message)
                PushNotificationActivity.presentPushMessage(foregroundActivity, notificationID)
            }
        }

        /**
        * Method checks whether the app is in background or not
        */
        val isAppInBackground: Boolean
            get() {
                val currentState = ProcessLifecycleOwner.get().lifecycle.currentState
                return !currentState.isAtLeast(Lifecycle.State.RESUMED)
            }

    }

NotificationUtilities code example:

    public class NotificationUtilities {

        private static final String PUSH_CHANNEL = "my_push_channel";
        public static final String NOTIFICATION_ID_EXTRA = "NotificationID";
        public static final String NOTIFICATION_DATA = "NotificationData";
        private Context context;
        private String negativeButton;

        /**
        * id to handle the notifications in the notification tray.
        * This is intentionally declared static so that the increment of this variable is shared with multiple background notifications.
        * Each time a background notification is received, this value will be incremented to maintain a unique id for the intents.
        */
        private static int notificationIdStart = 100;

        public NotificationUtilities(Context context) {
            this.context = context;
            negativeButton = context.getApplicationContext().getResources().getString(R.string.cancel);
        }

        public void showNotificationMessage(final String title, final String message, Intent intent) {
            // Check for empty push message
            if (TextUtils.isEmpty(message))
                return;

            // status bar icon
            final int smallIcon = R.mipmap.ic_statusbar;

            // notification bar icon
            final int largeIcon = R.mipmap.ic_launcher;
            intent.putExtra(RemoteNotificationConfig.CURRENT_NOTIFICATION_ID, notificationIdStart );
            intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
            final PendingIntent resultPendingIntent =
            PendingIntent.getActivity(
                    context,
                    notificationIdStart,
                    intent,
                    PendingIntent.FLAG_UPDATE_CURRENT
                );

            NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
            // versions >= 26 we need to have notification channel, as well
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {

                // user-visible name of the channel.
                CharSequence name = "push-channel";
                // user-visible description of the channel.
                String description = "notification channel for push messages";
                // importance
                int importance = NotificationManager.IMPORTANCE_HIGH;
                NotificationChannel notificationChannel = new NotificationChannel(PUSH_CHANNEL, name, importance);
                notificationChannel.setDescription(description);
                notificationChannel.enableLights(true);
                // sets the notification light color for notifications posted to this
                // channel, if the device supports this feature.
                notificationChannel.setLightColor(Color.RED);
                notificationChannel.enableVibration(true);
                notificationChannel.setVibrationPattern(new long[]{100, 200, 300, 400, 500, 400, 300, 200, 400});
                notificationManager.createNotificationChannel(notificationChannel);
            }

            NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(context, PUSH_CHANNEL);

            showSmallNotification(notificationBuilder, smallIcon, largeIcon, title, message, resultPendingIntent);
        }


        private void showSmallNotification(NotificationCompat.Builder notificationBuilder, int smallIcon, int largeIcon, String title, String message, PendingIntent resultPendingIntent) {

            NotificationCompat.InboxStyle inboxStyle = new NotificationCompat.InboxStyle();

            inboxStyle.addLine(message);

            Intent intentCancel = new Intent(context, PushNotificationActionReceiver.class);
            intentCancel.setAction(negativeButton);
            intentCancel.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
            intentCancel.putExtra(RemoteNotificationConfig.CURRENT_NOTIFICATION_ID,notificationIdStart );
            //This Intent will be called when the user clicks the Cancel button from the notification.
            PendingIntent pendingIntentCancel = PendingIntent.getBroadcast(context, notificationIdStart, intentCancel, PendingIntent.FLAG_CANCEL_CURRENT);

            Notification notification = notificationBuilder
                    .setSmallIcon(smallIcon)
                    .setLargeIcon(BitmapFactory.decodeResource(context.getResources(), largeIcon))
                    .setTicker(title)
                    .setWhen(0)
                    .setAutoCancel(true)
                    .setContentTitle(title)
                    .setContentIntent(resultPendingIntent)
                    .setStyle(inboxStyle)
                    .setBadgeIconType(NotificationCompat.BADGE_ICON_SMALL)
                    .setContentText(message)
                    .addAction(R.drawable.ic_close_black_24dp, negativeButton, pendingIntentCancel)
                    .build();

            NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
            notificationManager.notify(notificationIdStart++, notification);
        }

        // Clears notification tray messages
        public static void clearNotifications(Context context) {
            NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
            notificationManager.cancelAll();
        }
    }
    class NotificationUtilities(private val context: Context) {
        private val negativeButton: String = context.applicationContext.resources.getString(R.string.cancel)

        fun showNotificationMessage(title: String, message: String, intent: Intent) {
            // Check for empty push message
            if (TextUtils.isEmpty(message))
                return

            // status bar icon
            val smallIcon = R.mipmap.ic_statusbar

            // notification bar icon
            val largeIcon = R.mipmap.ic_launcher
            intent.putExtra(RemoteNotificationConfig.CURRENT_NOTIFICATION_ID, notificationIdStart)
            intent.flags = Intent.FLAG_ACTIVITY_CLEAR_TOP or Intent.FLAG_ACTIVITY_NEW_TASK
            val resultPendingIntent = PendingIntent.getActivity(
                    context,
                    notificationIdStart,
                    intent,
                    PendingIntent.FLAG_UPDATE_CURRENT
            )

            val notificationManager = context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
            // versions >= 26 we need to have a notification channel, as well
            if (SDK_INT >= O) {

                // user-visible name of the channel.
                val name = "push-channel"
                // user-visible description of the channel.
                val description = "notification channel for push messages"
                // importance
                val importance = NotificationManager.IMPORTANCE_HIGH
                val notificationChannel = NotificationChannel(PUSH_CHANNEL, name, importance)
                notificationChannel.description = description
                notificationChannel.enableLights(true)
                // sets the notification light color for notifications posted to this
                // channel, if the device supports this feature.
                notificationChannel.lightColor = Color.RED
                notificationChannel.enableVibration(true)
                notificationChannel.vibrationPattern = longArrayOf(100, 200, 300, 400, 500, 400, 300, 200, 400)
                notificationManager.createNotificationChannel(notificationChannel)
            }
            val notificationBuilder: NotificationCompat.Builder = NotificationCompat.Builder(context, PUSH_CHANNEL)
            showSmallNotification(notificationBuilder, smallIcon, largeIcon, title, message, resultPendingIntent)
        }


        private fun showSmallNotification(notificationBuilder: NotificationCompat.Builder, smallIcon: Int, largeIcon: Int, title: String, message: String, resultPendingIntent: PendingIntent) {

            val inboxStyle = NotificationCompat.InboxStyle()

            inboxStyle.addLine(message)

            val intentCancel =  Intent(context, PushNotificationActionReceiver::class.java)
            intentCancel.action = negativeButton
            intentCancel.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
            intentCancel.putExtra(RemoteNotificationConfig.CURRENT_NOTIFICATION_ID, notificationIdStart)

            //This Intent will be called when the user clicks the Cancel button from the notification.
            val pendingIntentCancel = PendingIntent.getBroadcast(context, notificationIdStart, intentCancel, PendingIntent.FLAG_CANCEL_CURRENT)

            val notification = notificationBuilder
                    .setSmallIcon(smallIcon)
                    .setLargeIcon(BitmapFactory.decodeResource(context.resources, largeIcon))
                    .setTicker(title)
                    .setWhen(0)
                    .setAutoCancel(true)
                    .setContentTitle(title)
                    .setContentIntent(resultPendingIntent)
                    .setStyle(inboxStyle)
                    .setBadgeIconType(NotificationCompat.BADGE_ICON_SMALL)
                    .setContentText(message)
                    .addAction(R.drawable.ic_close_black_24dp, negativeButton, pendingIntentCancel)
                    .build()

            val notificationManager = context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
            notificationManager.notify(notificationIdStart++, notification)
        }

        companion object {

            private const val PUSH_CHANNEL = "my_push_channel"
            val NOTIFICATION_ID_EXTRA = "NotificationID"
            val NOTIFICATION_DATA = "NotificationData"
            /**
            * id to handle the notifications in the notification tray.
            * This is intentionally declared static so that the increment of this variable is shared with multiple background notifications.
            * Each time a background notification is RECEIVED, this value will be incremented to maintain a unique id for the intents
            */
            private var notificationIdStart = 100

            // Clears notification tray messages
            fun clearNotifications(context: Context) {
                val notificationManager = context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
                notificationManager.cancelAll()
            }
        }
    }

Using PushService to Unregister Device Tokens

PushService also provides the API to unregister device tokens from the server.

    PushService.unregisterPush(new RemoteNotificationClient.CallbackListener() {
                @Override
                public void onSuccess() {
                  //handle success message
                }

                @Override
                public void onError(@NonNull Throwable throwable) {
                  //handle failed message
                }
            });
    PushService.unregisterPush(object : RemoteNotificationClient.CallbackListener {
                    override fun onSuccess() {
                      //handle success message
                    }
                    }

                    override fun onError(throwable: Throwable) {
                      //handle failed message
                    }
                })

Using PushService for Notification Feedback

The PushService provides a simplified way to manage notifications.

    PushService.setPushMessageStatus(notificationId, PushService.NotificationStatus.CONSUMED);
    PushService.setPushMessageStatus(notificationId, PushService.NotificationStatus.CONSUMED)

Let PushService Handle Notifications From Foreground and Background

Starting with SAP BTP SDK for Android 3.4.0, PushService provides a new way to display notifications, providing ForegroundNotificationInterceptor and BackgroundNotificationInterceptor to handle notifications from the foreground and background. You need to set EnableAutoMessageHandling to true when initializing PushService. For the foreground notification, use a ForegroundPushNotificationReady handler to decide when the notification should be displayed. Note that the SDK implements FirebaseMessagingService, so there is no need to do it manually.

    pushService.setEnableAutoMessageHandling(true);
    pushService.setBackgroundNotificationInterceptor(pushNotificationEvent -> pushNotificationEvent.displayNotification(pushNotificationEvent.getPushRemoteMessage()));
    pushService.setForegroundNotificationInterceptor(pushNotificationEvent -> {
        pushNotificationEvent.displayNotificationWhen(pushNotificationEvent.getPushRemoteMessage(), ()->{
            Activity activity = AppLifecycleCallbackHandler.getInstance().getActivity();
            if (activity == null)
                return false;
            else
                return !activity.getClass().getName().equals("packageName.app.WelcomeActivity");
        });
    });
    services.add(PushService().apply {
        setPushCallbackListener(FCMPushCallbackListener())
        setPushServiceConfig(configPushServiceConfig())
        isEnableAutoMessageHandling = true
        setBackgroundNotificationInterceptor { pushEvent ->
            pushEvent.displayNotification(pushEvent.pushRemoteMessage)
        }
        setForegroundNotificationInterceptor { pushEvent->
                pushEvent.displayNotificationWhen(pushEvent.pushRemoteMessage, object: ForegroundPushNotificationReady{
                    override fun onConditionReady(): Boolean {
                        return  AppLifecycleCallbackHandler.getInstance().activity?.let {
                            it.javaClass.name != "packageName.app.WelcomeActivity"
                        }?:false
                    }
                })
            }
        })

In addition, PushService can store the notification when it is not appropriate to display it. When ForegroundPushNotificationReady is satisfied , PushService will display the stored notification. For example, the following code shows the scenario where the notification will not be displayed in the activity whose name contains WelcomeActivity.

    PushService service = SDKInitializer.INSTANCE.getService(JvmClassMappingKt.getKotlinClass(PushService.class));
    service.storeNotificationMessage(true, message, () -> !AppLifecycleCallbackHandler.getInstance().getActivity().getClass().getName().contains("WelcomeActivity"));
    val service = getService(PushService::class.java.kotlin)
    service!!.storeNotificationMessage(true, message, object : ForegroundPushNotificationReady {
        override fun onConditionReady(): Boolean {
            return !AppLifecycleCallbackHandler.getInstance().activity!!.javaClass.name.contains("WelcomeActivity")
        }
    })

Last update: June 29, 2021