| Index: third_party/cacheinvalidation/src/java/com/google/ipc/invalidation/ticl/android2/channel/AndroidMessageReceiverService.java
|
| diff --git a/third_party/cacheinvalidation/src/java/com/google/ipc/invalidation/ticl/android2/channel/AndroidMessageReceiverService.java b/third_party/cacheinvalidation/src/java/com/google/ipc/invalidation/ticl/android2/channel/AndroidMessageReceiverService.java
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..54d0fb91ecf11471ea32aca913196df771c862c1
|
| --- /dev/null
|
| +++ b/third_party/cacheinvalidation/src/java/com/google/ipc/invalidation/ticl/android2/channel/AndroidMessageReceiverService.java
|
| @@ -0,0 +1,135 @@
|
| +/*
|
| + * Copyright 2011 Google Inc.
|
| + *
|
| + * Licensed under the Apache License, Version 2.0 (the "License");
|
| + * you may not use this file except in compliance with the License.
|
| + * You may obtain a copy of the License at
|
| + *
|
| + * http://www.apache.org/licenses/LICENSE-2.0
|
| + *
|
| + * Unless required by applicable law or agreed to in writing, software
|
| + * distributed under the License is distributed on an "AS IS" BASIS,
|
| + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
| + * See the License for the specific language governing permissions and
|
| + * limitations under the License.
|
| + */
|
| +package com.google.ipc.invalidation.ticl.android2.channel;
|
| +
|
| +import com.google.android.gcm.GCMRegistrar;
|
| +import com.google.ipc.invalidation.external.client.SystemResources.Logger;
|
| +import com.google.ipc.invalidation.external.client.android.service.AndroidLogger;
|
| +import com.google.ipc.invalidation.external.client.contrib.MultiplexingGcmListener;
|
| +import com.google.ipc.invalidation.ticl.android2.AndroidTiclManifest;
|
| +import com.google.ipc.invalidation.ticl.android2.ProtocolIntents;
|
| +import com.google.ipc.invalidation.ticl.android2.channel.AndroidChannelConstants.C2dmConstants;
|
| +import com.google.ipc.invalidation.ticl.proto.AndroidChannel.AddressedAndroidMessage;
|
| +import com.google.ipc.invalidation.util.ProtoWrapper.ValidationException;
|
| +
|
| +import android.content.Context;
|
| +import android.content.Intent;
|
| +import android.util.Base64;
|
| +
|
| +
|
| +/**
|
| + * Service that receives messages from using GCM.
|
| + *
|
| + */
|
| +public class AndroidMessageReceiverService extends MultiplexingGcmListener.AbstractListener {
|
| + /*
|
| + * This class is public so that it can be instantiated by the Android runtime. All of the
|
| + * {@code onYYY} methods are called holding a wakelock that will be automatically released when
|
| + * they return, since this is a subclass of {@code AbstractListener}.
|
| + */
|
| +
|
| + /**
|
| + * Receiver for broadcasts by the multiplexed GCM service. It forwards them to
|
| + * AndroidMessageReceiverService.
|
| + */
|
| + public static class Receiver extends MultiplexingGcmListener.AbstractListener.Receiver {
|
| + /* This class is public so that it can be instantiated by the Android runtime. */
|
| + @Override
|
| + protected Class<?> getServiceClass() {
|
| + return AndroidMessageReceiverService.class;
|
| + }
|
| + }
|
| +
|
| + private final Logger logger = AndroidLogger.forTag("MsgRcvrSvc");
|
| +
|
| + public AndroidMessageReceiverService() {
|
| + super("AndroidMessageReceiverService");
|
| + }
|
| +
|
| + @Override
|
| + protected void onMessage(Intent intent) {
|
| + // Forward the message to the Ticl service.
|
| + if (intent.hasExtra(C2dmConstants.CONTENT_PARAM)) {
|
| + String content = intent.getStringExtra(C2dmConstants.CONTENT_PARAM);
|
| + byte[] msgBytes = Base64.decode(content, Base64.URL_SAFE);
|
| + try {
|
| + // Look up the name of the Ticl service class from the manifest.
|
| + String serviceClass = new AndroidTiclManifest(this).getTiclServiceClass();
|
| + AddressedAndroidMessage addrMessage = AddressedAndroidMessage.parseFrom(msgBytes);
|
| + Intent msgIntent =
|
| + ProtocolIntents.InternalDowncalls.newServerMessageIntent(addrMessage.getMessage());
|
| + msgIntent.setClassName(this, serviceClass);
|
| + startService(msgIntent);
|
| + } catch (ValidationException exception) {
|
| + logger.warning("Failed parsing inbound message: %s", exception);
|
| + }
|
| + } else {
|
| + logger.fine("GCM Intent has no message content: %s", intent);
|
| + }
|
| +
|
| + // Store the echo token.
|
| + String echoToken = intent.getStringExtra(C2dmConstants.ECHO_PARAM);
|
| + if (echoToken != null) {
|
| + AndroidChannelPreferences.setEchoToken(this, echoToken);
|
| + }
|
| + }
|
| +
|
| + @Override
|
| + protected void onRegistered(String registrationId) {
|
| + // Inform the sender service that the registration id has changed. If the sender service
|
| + // had buffered a message because no registration id was previously available, this intent
|
| + // will cause it to send that message.
|
| + Intent sendBuffered = new Intent();
|
| + final String ignoredData = "";
|
| + sendBuffered.putExtra(AndroidChannelConstants.MESSAGE_SENDER_SVC_GCM_REGID_CHANGE, ignoredData);
|
| + sendBuffered.setClass(this, AndroidMessageSenderService.class);
|
| + startService(sendBuffered);
|
| +
|
| + // Inform the Ticl service that the registration id has changed. This will cause it to send
|
| + // a message to the data center and update the GCM registration id stored at the data center.
|
| + Intent updateServer = ProtocolIntents.InternalDowncalls.newNetworkAddrChangeIntent();
|
| + updateServer.setClassName(this, new AndroidTiclManifest(this).getTiclServiceClass());
|
| + startService(updateServer);
|
| + }
|
| +
|
| + @Override
|
| + protected void onUnregistered(String registrationId) {
|
| + // Nothing to do.
|
| + }
|
| +
|
| + @Override
|
| + protected void onDeletedMessages(int total) {
|
| + // This method must be implemented if we start using non-collapsable messages with GCM. For
|
| + // now, there is nothing to do.
|
| + }
|
| +
|
| + /**
|
| + * Initializes GCM as a convenience method for tests. In production, applications should handle
|
| + * this.
|
| + */
|
| + public static void initializeGcmForTest(Context context, Logger logger, String senderId) {
|
| + // Initialize GCM.
|
| + GCMRegistrar.checkDevice(context);
|
| + GCMRegistrar.checkManifest(context);
|
| + String regId = GCMRegistrar.getRegistrationId(context);
|
| + if (regId.isEmpty()) {
|
| + logger.info("Not registered with GCM; registering");
|
| + GCMRegistrar.register(context, senderId);
|
| + } else {
|
| + logger.fine("Already registered with GCM: %s", regId);
|
| + }
|
| + }
|
| +}
|
|
|