Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using 2 or more GCM Intent Services in one Application

I am writing an application that integrates with Smooch and Carnival. Both these libraries receive GCM push messages using the standard approach of defining a GCM Intent Service to receive messages.

When I use only Smooch, everything works great. When I use only Carnival, everything works great. The problem comes in when I try to use both. What I have found is that the GCM receiver will simply start the first service listed in the manifest that defines intent com.google.android.c2dm.intent.RECEIVE.

In fact, I found that the order the libraries are listed in my build.gradle affects in which order their manifests are merged into the application manifest. So, if I put smooch first, it works (but Carnival doesn't receive anything). And if I put Carnival first, it works (but Smooch never receives anything).

How can I handle multiple GCM intent services when I don't control either one? In general, how should applications define and manage multiple GCM intent services?

like image 232
Greg Ennis Avatar asked Apr 11 '16 00:04

Greg Ennis


People also ask

What is an intentservice in Android?

The IntentService is a subclass of the Service class that provides an Android specific implementation of this pattern. It will manage queueing work, starting up a worker thread to service the queue, and pulling requests off the queue to be run on the worker thread.

How do I get the GCM Service?

The GCM service handles all aspects of queueing of messages and delivery to client applications running on target devices, and it is completely free. To get this service from Google, however, you will need to do certain things: Enable GCM for that project. Get the SENDER_ID of the project or create a configuration file.

How to integrate GCM with Android push notifications?

Implement an Android Client app to register with GCM, send the registration id to your push notification server and manage the notifications sent from your server via GCM. Implement a server side API to get and store registration ids from the client app and optionally provide an Admin panel to send push notification from.

What is mygcmlistenerservice?

MyGcmListenerService: It's an intent service which runs in the background (always) for the project and responsible for getting the notification and triggering different events accordingly.


1 Answers

The reason you can't get push to work in both Carnival and Smooch is that both libraries are registering their own GcmListenerService, and in Android the first GcmListenerService defined in your manifest will receive all GCM messages.

I have a solution for you based primarily off the following SO article: Multiple GCM listeners using GcmListenerService

The best solution would be to just have one GcmListenerService implementation, and have this handle messages for both.

In order to specify your own GcmListenerService, follow the instructions from Google's Cloud Messaging Documentation.

Smooch provides the tools necessary for you to disable their internal GCM registration when you have your own.

To do so, simply call setGoogleCloudMessagingAutoRegistrationEnabled while initializing Smooch:

Settings settings = new Settings("<your_app_token>");
settings.setGoogleCloudMessagingAutoRegistrationEnabled(false);
Smooch.init(this, settings);

And in your own GcmRegistrationIntentService, call Smooch.setGoogleCloudMessagingToken(token); with your token.

Once that is complete, you'll be able to pass the GCM message on to any GCM Receiver that you'd like.

@Override
public void onMessageReceived(String from, Bundle data) {
    final String smoochNotification = data.getString("smoochNotification");

    if (smoochNotification != null && smoochNotification.equals("true")) {
        data.putString("from", from);

        Intent intent = new Intent();
        intent.putExtras(data);
        intent.setAction("com.google.android.c2dm.intent.RECEIVE");
        intent.setComponent(new ComponentName(getPackageName(), "io.smooch.core.GcmService"));

        GcmReceiver.startWakefulService(getApplicationContext(), intent);
    }
}

EDIT

As of Smooch version 3.2.0, you can now more easily trigger Smooch’s notification by calling GcmService.triggerSmoochGcm in your onMessageReceived.

@Override
public void onMessageReceived(String from, Bundle data) {
    final String smoochNotification = data.getString("smoochNotification");

    if (smoochNotification != null && smoochNotification.equals("true")) {
        GcmService.triggerSmoochGcm(data, this);
    }
}
like image 76
Julian Garritano Avatar answered Nov 26 '22 04:11

Julian Garritano