Android

Android Cloud to Device Messaging Framework

Android Cloud to Device Messaging (C2DM) is a service that helps developers send data from servers to their applications on Android devices. The service provides a simple, lightweight mechanism that servers can use to tell mobile applications to contact the server directly, to fetch updated application or user data. The C2DM service handles all aspects of queueing of messages and delivery to the target application running on the target device.

Contents

  1. Introduction
  2. Architectural Overview
    1. Lifecycle Flow
    2. What Does the User See?
  3. Writing Android Applications that use C2DM
    1. Creating the Manifest
    2. Registering for C2DM
    3. Unregistering from C2DM
    4. Handling Registration Results
    5. Handling Received Data
    6. Developing and Testing Your Applications
  4. Role of the Third-Party Application Server
    1. How the Application Server Sends Messages
  5. Examples
  6. Limitations

Introduction

Here are the primary characteristics of Android Cloud to Device Messaging (C2DM):

  • It allows third-party application servers to send lightweight messages to their Android applications. The messaging service is not designed for sending a lot of user content via the messages. Rather, it should be used to tell the application that there is new data on the server, so that the application can fetch it.
  • C2DM makes no guarantees about delivery or the order of messages. So, for example, while you might use this feature to tell an instant messaging application that the user has new messages, you probably would not use it to pass the actual messages.
  • An application on an Android device doesn’t need to be running to receive messages. The system will wake up the application via Intent broadcast when the the message arrives, as long as the application is set up with the proper broadcast receiver and permissions.
  • It does not provide any built-in user interface or other handling for message data. C2DM simply passes raw message data received straight to the application, which has full control of how to handle it. For example, the application might post a notification, display a custom user interface, or silently sync data.
  • It requires devices running Android 2.2 or higher that also have the Market application installed. However, you are not limited to deploying your applications through Market.
  • It uses an existing connection for Google services. This requires users to set up their Google account on their mobile devices.

Architectural Overview

This section gives an overview of how C2DM works.

This table summarizes the key terms and concepts involved in C2DM. It is divided into these categories:

  • Components — The physical entities that play a role in C2DM.
  • Credentials — The IDs and tokens that are used in different stages of C2DM to ensure that all parties have been authenticated, and that the message is going to the correct place.
Components
Mobile Device The device that is running an Android application that uses C2DM. This must be a 2.2 Android device that has Market installed, and it must have at least one logged in Google account.
Third-Party Application Server An application server that developers set up as part of implementing C2DM in their applications. The third-party application server sends data to an Android application on the device via the C2DM server.
C2DM Servers The Google servers involved in taking messages from the third-party application server and sending them to the device.
Credentials
Sender ID An email account associated with the application's developer. The sender ID is used in the registration process to identify a Android application that is permitted to send messages to the device. This ID is typically role-based rather than being a personal account—- for example, my-app@gmail.com.
Application ID The application that is registering to receive messages. The application is identified by the package name from the manifest. This ensures that the messages are targeted to the correct application.
Registration ID An ID issued by the C2DM servers to the Android application that allows it to receive messages. Once the application has the registration ID, it sends it to the third-party application server, which uses it to identify each device that has registered to receive messages for a given application. In other words, a registration ID is tied to a particular application running on a particular device.
Google User Account For C2DM to work, the mobile device must include at least one logged in Google account.
Sender Auth Token A ClientLogin Auth token that is saved on the third-party application server that gives the application server authorized access to Google services. The token is included in the header of POST requests that send messages. For more discussion of ClientLogin Auth tokens, see ClientLogin for Installed Applications.

Lifecycle Flow

Here are the primary processes involved in cloud-to-device messaging:

  • Enabling C2DM. An Android application running on a mobile device registers to receive messages.
  • Sending a message. A third-party application server sends messages to the device.
  • Receiving a message. An Android application receives a message from a C2DM server.

These processes are described in more detail below.

Enabling C2DM

This is the sequence of events that occurs when an Android application running on a mobile device registers to receive messages:

  1. The first time the application needs to use the messaging service, it fires off a registration Intent to a C2DM server.

    This registration Intent (com.google.android.c2dm.intent.REGISTER) includes the sender ID (that is, the account authorized to send messages to the application, which is typically the email address of an account set up by the application's developer), and the application ID.

  2. If the registration is successful, the C2DM server broadcasts a REGISTRATION Intent which gives the application a registration ID.

    The application should store this ID for later use. Note that Google may periodically refresh the registration ID, so you should design your application with the understanding that the REGISTRATION Intent may be called multiple times. Your application needs to be able to respond accordingly.

  3. To complete the registration, the application sends the registration ID to the application server. The application server typically stores the registration ID in a database.

The registration ID lasts until the application explicitly unregisters itself, or until Google refreshes the registration ID for your application.

Sending a Message

For an application server to send a message, the following things must be in place:

  • The application has a registration ID that allows it to receive messages for a particular device.
  • The third-party application server has stored the registration ID.

There is one more thing that needs to be in place for the application server to send messages: a ClientLogin authorization token. This is something that the developer must have already set up on the application server for the application (for more discussion, see Role of the Third-Party Application Server). Now it will get used to send messages to the device.

The ClientLogin token authorizes the application server to send messages to a particular Android application. An application server has one ClientLogin token for a particular 3rd party app, and multiple registration IDs. Each registration ID represents a particular device that has registered to use the messaging service for a particular 3rd party app.

Here is the sequence of events that occurs when the application server sends a message:

  1. The application server sends a message to C2DM servers.
  2. Google enqueues and stores the message in case the device is inactive.
  3. When the device is online, Google sends the message to the device.
  4. On the device, the system broadcasts the message to the specified application via Intent broadcast with proper permissions, so that only the targeted application gets the message. This wakes the application up. The application does not need to be running beforehand to receive the message.
  5. The application processes the message. If the application is doing non-trivial processing, you may want to grab a wake lock and do any processing in a Service.

An application can unregister C2DM if it no longer wants to receive messages.

Receiving a Message

This is the sequence of events that occurs when an Android application running on a mobile device receives a message:

  1. The system receives the incoming message and extracts the raw key/value pairs from the message payload.
  2. The system passes the key/value pairs to the targeted Android application in a com.google.android.c2dm.intent.RECEIVE Intent as a set of extras.
  3. The Android application extracts the raw data from the RECEIVE Intent by key and processes the data.

What Does the User See?

When mobile device users install an applications that include C2DM, they will get a permission from Android Market informing them that the application includes C2DM. They must approve the use of this feature to install the application. Depending on the implementation of the application, it may offer users the option of unregistering to receive messages. Uninstalling the application also has the effect of unregistering.

Writing Android Applications that Use C2DM

To write Android applications that use C2DM, you must have an application server that can perform the tasks described in Role of the Third-Party Application Server. This section describes the steps you take to create a client application that uses C2DM.

Remember that there is no user interface associated with the C2DM Framework. However you choose to process messages in your application is up to you.

There are two primary steps involved in writing a client application:

  • Creating a manifest that contains the permissions the application needs to use C2DM.
  • Implementing your Java code. To use C2DM, this implementation must include:
    • Code to start and stop the registration service.
    • Receivers for com.google.android.c2dm.intent.C2D_MESSAGE and com.google.android.c2dm.intent.REGISTRATION.

Creating the Manifest

Every application must have an AndroidManifest.xml file (with precisely that name) in its root directory. The manifest presents essential information about the application to the Android system, information the system must have before it can run any of the application's code (for more discussion of the manifest file, see the Android Developers Guide). To use the C2DM feature, the manifest must include the following:

  • com.google.android.c2dm.permission.RECEIVE states that the application has permission register and receive messages.
  • android.permission.INTERNET states that the application has permission to send the receiver key to the 3rd party server.
  • applicationPackage + ".permission.C2D_MESSAGE prevents other applications from registering and receiving the application's messages.
  • Receivers for com.google.android.c2dm.intent.RECEIVE and com.google.android.c2dm.intent.REGISTRATION, with the category set as applicationPackage. The receiver should require the com.google.android.c2dm.SEND permission, so that only the C2DM Framework can send it the message. Note that both registration and the receiving of messages are implemented as Intents.
  • If the C2DM feature is critical to the application's function, be sure to set android:minSdkVersion="8" in the manifest. This ensures that the application cannot be installed in an environment in which it could not run properly.

Received C2D_MESSAGE Intents have all key/value pairs sent by the 3rd party server as extras. One special key is collapse_key, which is specified by the sender to allow handling of messages waiting for an off-line device.

Here are excerpts from a manifest that supports C2DM:

<manifest package="com.example.myapp" ...>

   <!-- Only this application can receive the messages and registration result --> 
   <permission android:name="com.example.myapp.permission.C2D_MESSAGE" android:protectionLevel="signature" />
   <uses-permission android:name="com.example.myapp.permission.C2D_MESSAGE" />

   <!-- This app has permission to register and receive message -->
   <uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" />

   <!-- Send the registration id to the server -->
   <uses-permission android:name="android.permission.INTERNET" />

   <application...>
      <!-- Only C2DM servers can send messages for the app. If permission is not set - any other app can generate it --> 
      <receiver android:name=".C2DMReceiver" android:permission="com.google.android.c2dm.permission.SEND">
          <!-- Receive the actual message -->
          <intent-filter>
              <action android:name="com.google.android.c2dm.intent.RECEIVE" />
              <category android:name="com.example.myapp" />
          </intent-filter>
          <!-- Receive the registration id -->
          <intent-filter>
              <action android:name="com.google.android.c2dm.intent.REGISTRATION" />
              <category android:name="com.example.myapp" />
          </intent-filter>
      </receiver>
      ...
   </application>
   ...
</manifest>

Registering for C2DM

An Android application needs to register with C2DM servers before receiving any message. To register it needs to send an Intent (com.google.android.c2dm.intent.REGISTER), with 2 extra parameters:

  • sender is the ID of the account authorized to send messages to the application, typically the email address of an account set up by the application's developer.
  • app is the application's ID, set with a PendingIntent to allow the registration service to extract application information.

For example:

Intent registrationIntent = new Intent("com.google.android.c2dm.intent.REGISTER");
registrationIntent.putExtra("app", PendingIntent.getBroadcast(this, 0, new Intent(), 0)); // boilerplate
registrationIntent.putExtra("sender", emailOfSender);
startService(registrationIntent);

Registration is not complete until the application sends the registration ID to the third-party application server. The application server uses the registration ID to send messages that are targeted to the application running on that particular device.

Unregistering from C2DM

To unregister from C2DM:

Intent unregIntent = new Intent("com.google.android.c2dm.intent.UNREGISTER");
unregIntent.putExtra("app", PendingIntent.getBroadcast(this, 0, new Intent(), 0));
startService(unregIntent);

Handling Registration Results

As discussed in Creating the Manifest, the manifest defines a receiver for com.google.android.c2dm.intent.REGISTRATION. It also defines a receiver for com.google.android.c2dm.intent.RECEIVE. Note that both registration and the receiving of messages are implemented as Intents.

The main use of REGISTRATION is to allow the application to receive the registration ID. The Intent can be sent at any time. Google may periodically refresh the receiver ID. An application receiving this Intent with a registration_id parameter must ensure that the third-party application server receives the registration ID. It may do so by saving the registration ID and sending it to the server. If the network is down or there are errors, the application should retry sending the registration ID when the network is up again or the next time it starts. An application should keep track of its registration status and attempt to register again if the process is not fully completed.

The REGISTRATION Intent is generated with an error parameter if the registration couldn't be completed. If that happens, the application should try again later with exponential back off. When the application unregisters, the REGISTRATION Intent will be sent with an unregistered extra parameter.

Here are the possible error codes for the REGISTRATION Intent:

Error Code Description
SERVICE_NOT_AVAILABLE The device can't read the response, or there was a 500/503 from the server that can be retried later. The application should use exponential back off and retry.
ACCOUNT_MISSING There is no Google account on the phone. The application should ask the user to open the account manager and add a Google account. Fix on the device side.
AUTHENTICATION_FAILED Bad password. The application should ask the user to enter his/her password, and let user retry manually later. Fix on the device side.
TOO_MANY_REGISTRATIONS The user has too many applications registered. The application should tell the user to uninstall some other applications, let user retry manually. Fix on the device side.
INVALID_SENDER The sender account is not recognized.
PHONE_REGISTRATION_ERROR Incorrect phone registration with Google. This phone doesn't currently support C2DM.

The application receives a REGISTRATION Intent broadcast whenever the application server attempts to send a message to it. But registration IDs can be nonexistent or invalid for a variety of reasons:

  • If an application is running for the first time, it has no registration ID yet.
  • If the application unregistered, it has no registration ID.
  • The C2DM server periodically refreshes registration IDs.

An application must be prepared to handle every case. For example:

public void onReceive(Context context, Intent intent) {
    if (intent.getAction().equals("com.google.android.c2dm.intent.REGISTRATION")) {
        handleRegistration(context, intent);
    } else if (intent.getAction().equals("com.google.android.c2dm.intent.RECEIVE")) {
        handleMessage(context, intent);
     }
 }

private void handleRegistration(Context context, Intent intent) {
    String registration = intent.getStringExtra("registration_id"); 
    if (intent.getStringExtra("error") != null) {
        // Registration failed, should try again later.
    } else if (intent.getStringExtra("unregistered") != null) {
        // unregistration done, new messages from the authorized sender will be rejected
    } else if (registration != null) {
       // Send the registration ID to the 3rd party site that is sending the messages.
       // This should be done in a separate thread.
       // When done, remember that all registration is done. 
    }
}

Handling Received Data

When the C2DM server receives a message from the third-party application server, C2DM extracts the raw key/value pairs from the message payload and passes them to the Android application in the com.google.android.c2dm.intent.RECEIVE Intent as a set of extras. The application extracts the data by key and processes it, whatever that means for that application.

Here is an example:

protected void onReceive(Context context, Intent intent) {
    String accountName = intent.getExtras().getString(Config.C2DM_ACCOUNT_EXTRA);
    String message = intent.getExtras().getString(Config.C2DM_MESSAGE_EXTRA);
    if (Config.C2DM_MESSAGE_SYNC.equals(message)) {
        if (accountName != null) {
            if (Log.isLoggable(TAG, Log.DEBUG)) {
                Log.d(TAG, "Messaging request received for account " + accountName);
            }
            
            ContentResolver.requestSync(
                new Account(accountName, SyncAdapter.GOOGLE_ACCOUNT_TYPE),
                JumpNoteContract.AUTHORITY, new Bundle());
        }
    }
}

Developing and Testing Your Applications

Here are some guidelines for developing and testing an Android application that uses the C2DM feature:

  • To develop and test your C2DM applications, you need to run and debug the applications on an Android 2.2 system image that includes the necessary underlying Google services.
  • To develop and debug on an actual device, you need a device running an Android 2.2 system image that includes the Market application.
  • To develop and test on the Android Emulator, you need to download the Android 2.2 version of the Google APIs Add-On into your SDK using the Android SDK and AVD Manager. Specifically, you need to download the component named "Google APIs by Google Inc, Android API 8". Then, you need to set up an AVD that uses that system image.
  • If the C2DM feature is critical to the application's function, be sure to set android:minSdkVersion="8" in the manifest. This ensures that the application cannot be installed in an environment in which it could not run properly.

Role of the Third-Party Application Server

Before you can write client applications that use the C2DM feature, you must have an HTTPS application server that meets the following criteria:

  • Able to communicate with your client.
  • Able to fire off HTTP requests to the C2DM server.
  • Able to handle requests and queue data as needed. For example, it should be able to perform exponential back off.
  • Able to store the ClientLogin Auth token and client registration IDs. The ClientLogin Auth token is included in the header of POST requests that send messages. For more discussion of this topic, see ClientLogin for Installed Applications. The server should store the token and have a policy to refresh it periodically.

How the Application Server Sends Messages

This section describes how the third-party application server sends messages to a 3rd party client application running on a mobile device.

Before the third-party application server can send a message to an application, it must have received a registration ID from it.

To send a message, the application server issues a POST request to https://android.apis.google.com/c2dm/send that includes the following:

Field Description
registration_id The registration ID retrieved from the Android application on the phone. Required.
collapse_key An arbitrary string that is used to collapse a group of like messages when the device is offline, so that only the last message gets sent to the client. This is intended to avoid sending too many messages to the phone when it comes back online. Note that since there is no guarantee of the order in which messages get sent, the "last" message may not actually be the last message sent by the application server. Required.
data.<key> Payload data, expressed as key-value pairs. If present, it will be included in the Intent as application data, with the <key>. There is no limit on the number of key/value pairs, though there is a limit on the total size of the message. Optional.
delay_while_idle If included, indicates that the message should not be sent immediately if the device is idle. The server will wait for the device to become active, and then only the last message for each collapse_key value will be sent. Optional.
Authorization: GoogleLogin auth=[AUTH_TOKEN] Header with a ClientLogin Auth token. The cookie must be associated with the ac2dm service. Required.

This table lists the possible response codes:

Response Description
200

Includes body containing:

  • id=[ID of sent message]
  • Error=[error code]
    • QuotaExceeded — Too many messages sent by the sender. Retry after a while.
    • DeviceQuotaExceeded — Too many messages sent by the sender to a specific device. Retry after a while.
    • InvalidRegistration — Missing or bad registration_id. Sender should stop sending messages to this device.
    • NotRegistered — The registration_id is no longer valid, for example user has uninstalled the application or turned off notifications. Sender should stop sending messages to this device.
    • MessageTooBig — The payload of the message is too big, see the limitations. Reduce the size of the message.
    • MissingCollapseKey — Collapse key is required. Include collapse key in the request.
503 Indicates that the server is temporarily unavailable (i.e., because of timeouts, etc ). Sender must retry later, honoring any Retry-After header included in the response. Application servers must implement exponential back off. Senders that create problems risk being blacklisted.
401 Indicates that the ClientLogin AUTH_TOKEN used to validate the sender is invalid.

Examples

Here are a few complete examples to get you started:

  • JumpNote. JumpNote is a sample two-way notes application, with auto-sync. JumpNote shows how to use the Android Cloud to Device Messaging Framework, as well as the Android Sync framework. JumpNote runs on top of Google App Engine, and it uses GWT for the web user interface.
  • Google Chrome to Phone Extension. "Chrome to Phone" lets users send content from the Chrome browser to their mobile device.

To view the source code, open the Source tab and click Browse. From there, you can navigate through the source tree.

Limitations

C2DM imposes the following limitations:

  • The message size limit is 1024 bytes.
  • Google limits the number of messages a sender sends in aggregate, and the number of messages a sender sends to a specific device

Authentifizierung erforderlich

Dazu müssen Sie in Google+ angemeldet sein.

Anmeldung...

Google Developers braucht hierfür Ihre Erlaubnis.