summaryrefslogtreecommitdiffstats
path: root/docs/html/google/gcm/server.jd
diff options
context:
space:
mode:
Diffstat (limited to 'docs/html/google/gcm/server.jd')
-rw-r--r--docs/html/google/gcm/server.jd448
1 files changed, 115 insertions, 333 deletions
diff --git a/docs/html/google/gcm/server.jd b/docs/html/google/gcm/server.jd
index b5e6b48..92a1531 100644
--- a/docs/html/google/gcm/server.jd
+++ b/docs/html/google/gcm/server.jd
@@ -1,34 +1,36 @@
-page.title=Implementing GCM Server
+page.title=GCM Server
@jd:body
<div id="qv-wrapper">
<div id="qv">
+<h2>Quickview</h2>
+
+<ul>
+<li>Understand how to set up the server side of a GCM app.</li>
+<li>Become familiar with the <a href="{@docRoot}reference/com/google/android/gcm/server/package-summary.html">GCM server helper library</a>.</li>
+</ul>
+
+
<h2>In this document</h2>
-<ol class="toc">
- <li><a href="#choose">Choosing a GCM Connection Server</a></li>
- <li><a href="#role">Role of the 3rd-party Application Server</a></li>
- <li><a href="#send-msg">Sending Messages</a>
- <ol class="toc">
-
- <li><a href="#target">Target</a></li>
- <li><a href="#payload">Payload</a></li>
- <li><a href="#params">Message parameters</a>
+<ol>
+ <li><a href="#requirements">Requirements</a> </li>
+ <li><a href="#gcm-setup">Setting Up GCM</a></li>
+ <li><a href="#server-setup">Setting Up an HTTP Server</a>
+ <ol>
+ <li><a href="#webserver-setup">Using a standard web server</a></li>
+ <li><a href="#appengine-setup">Using App Engine for Java</a></li>
</ol>
- </li>
- <li><a href="#receive">Receiving Messages</a> </li>
</li>
-
</ol>
<h2>See Also</h2>
<ol class="toc">
<li><a href="gs.html">Getting Started</a></li>
-<li><a href="client.html">Implementing GCM Client</a></li>
-<li><a href="ccs.html">Cloud Connection Server (XMPP)</a></li>
-<li><a href="http.html">HTTP Connection Server</a></li>
+<li><a href="client.html">GCM Client</a></li>
+<li><a href="ccs.html">Cloud Connection Server</a></li>
</ol>
@@ -37,342 +39,122 @@ page.title=Implementing GCM Server
</div>
-<p>The server side of GCM consists of 2 components:</p>
-<ul>
-<li>Google-provided <strong>GCM Connection Servers</strong>
-take messages from a 3rd-party application server and send them to a GCM-enabled
-Android application (the &quot;client app&quot;) running on a device. For example,
-Google provides connection servers for <a href="{@docRoot}google/gcm/http.html">
-HTTP</a> and <a href="{@docRoot}google/gcm/ccs.html">CCS</a> (XMPP).</li>
-<li>A <strong>3rd-party application server</strong> that you must implement. This application
-server sends data to a GCM-enabled Android application via the chosen GCM connection server.</li>
-</ul>
-</p>
-<p>Here are the basic steps you follow to implement your 3rd-party app server:</p>
+<p>This document gives examples of GCM server-side code for HTTP. For an example of an XMPP server (<a href="ccs.html">Cloud Connection Server</a>), see <a href="gs.html#server">Getting Started</a>. Note that a full GCM implementation requires a client-side implementation, in addition to the server. For a complete working example that includes client and server-side code, see <a href="gs.html">Getting Started</a>.</a>
+
+<h2 id="requirements">Requirements</h2>
+<p>For the web server:</p>
<ul>
- <li>Decide which GCM connection server(s) you want to use. Note that if you want to use
- upstream messaging from your client applications, you must use CCS. For a more detailed
- discussion of this, see <a href="#choose">
- Choosing a GCM Connection Server</a>.</li>
- <li>Decide how you want to implement your app server. For example:
- <ul>
- <li>If you decide to use the HTTP connection server, you can use the
-GCM server helper library and demo app to help in implementing your app server.</li>
- <li>If you decide to use the XMPP connection server, you can use
-the provided Python or Java <a href="http://www.igniterealtime.org/projects/smack/">
-Smack</a> demo apps as a starting point.</li>
- <li>Note that Google AppEngine does not support connections to CCS.</li>
- </ul>
- </li>
+ <li> <a href="http://ant.apache.org/">Ant 1.8</a> (it might work with earlier versions, but it's not guaranteed).</li>
+ <li>One of the following:
+ <ul>
+ <li>A running web server compatible with Servlets API version 2.5, such as <a href="http://tomcat.apache.org/">Tomcat 6</a> or <a href="http://jetty.codehaus.org/">Jetty</a>, or</li>
+ <li><a href="http://code.google.com/appengine/">Java App Engine SDK</a> version 1.6 or later.</li>
</ul>
</li>
+ <li>A Google account registered to use GCM.</li>
+ <li>The API key for that account.</li>
</ul>
+<p>For the Android application:</p>
+<ul>
+ <li>Emulator (or device) running Android 2.2 with Google APIs.</li>
+ <li>The Google API project number of the account registered to use GCM.</li>
+</ul>
+<h2 id="gcm-setup">Setting Up GCM</h2>
+<p>Before proceeding with the server and client setup, it's necessary to register a Google account with the Google API Console, enable Google Cloud Messaging in GCM, and obtain an API key from the <a href="https://code.google.com/apis/console">Google API Console</a>.</p>
+<p>For instructions on how to set up GCM, see <a href="gs.html">Getting Started</a>.</p>
-<p>A full GCM implementation requires both a client implementation and a server
-implementation. For more
-information about implementing the client side, see <a href="client.html">
-Implementing GCM Client</a>.</p>
-<h2 id="choose">Choosing a GCM Connection Server</h2>
+<h2 id="server-setup">Setting Up an HTTP Server</h2>
+<p>This section describes the different options for setting up an HTTP server.</p>
+<h3 id="webserver-setup">Using a standard web server</h3>
+<p>To set up the server using a standard, servlet-compliant web server:</p>
+<ol>
+ <li>From the <a href="http://code.google.com/p/gcm">open source site</a>, download the following directories: <code>gcm-server</code>, <code>samples/gcm-demo-server</code>, and <code>samples/gcm-demo-appengine</code>.</p>
-<p>Currently GCM provides two connection servers: <a href="{@docRoot}google/gcm/http.html">
-HTTP</a> and <a href="{@docRoot}google/gcm/ccs.html">CCS</a> (XMPP). You can use them
-separately or in tandem. CCS messaging differs from GCM HTTP messaging in the following ways:</p>
-<ul>
- <li>Upstream/Downstream messages
- <ul>
- <li>GCM HTTP: Downstream only: cloud-to-device. </li>
- <li>CCS: Upstream and downstream (device-to-cloud, cloud-to-device). </li>
- </ul>
- </li>
- <li>Asynchronous messaging
- <ul>
- <li>GCM HTTP: 3rd-party app servers send messages as HTTP POST requests and
-wait for a response. This mechanism is synchronous and causes the sender to block
-before sending another message.</li>
- <li>CCS: 3rd-party app servers connect to Google infrastructure using a
-persistent XMPP connection and send/receive messages to/from all their devices
-at full line speed. CCS sends acknowledgment or failure notifications (in the
-form of special ACK and NACK JSON-encoded XMPP messages) asynchronously.</li>
- </ul>
- </li>
- <li>JSON
- <ul>
- <li>GCM HTTP: JSON messages sent as HTTP POST.</li>
- <li>CCS: JSON messages encapsulated in XMPP messages.</li>
- </ul>
- </li>
-</ul>
+ <li>In a text editor, edit the <code>samples/gcm-demo-server/WebContent/WEB-INF/classes/api.key</code> and replace the existing text with the API key obtained above.</li>
+ <li>In a shell window, go to the <code>samples/gcm-demo-server</code> directory.</li>
+ <li>Generate the server's WAR file by running <code>ant war</code>:</li>
+
+ <pre class="prettyprint">$ ant war
-<h2 id="role">Role of the 3rd-party Application Server</h2>
+Buildfile:build.xml
-<p>Before you can write client Android applications that use the GCM feature, you must
-have an application server that meets the following criteria:</p>
+init:
+ [mkdir] Created dir: build/classes
+ [mkdir] Created dir: dist
-<ul>
- <li>Able to communicate with your client.</li>
- <li>Able to fire off properly formatted requests to the GCM server.</li>
- <li>Able to handle requests and resend them as needed, using
-<a href="http://en.wikipedia.org/wiki/Exponential_backoff">exponential back-off.</a></li>
- <li>Able to store the API key and client registration IDs. The
-API key is included in the header of POST requests that send
-messages.</li>
- <li>Able to store the API key and client registration IDs.</li>
- <li>Able to generate message IDs to uniquely identify each message it sends.</li>
-</ul>
+compile:
+ [javac] Compiling 6 source files to build/classes
-<h2 id="send-msg">Sending Messages</h2>
+war:
+ [war] Building war: <strong>dist/gcm-demo.war</strong>
-<p>Here is the general sequence of events that occurs when a 3rd-party application
-server sends a message:</p>
-<ol>
- <li>The application server sends a message to GCM servers.</li>
- <li>Google enqueues and stores the message in case the device is offline.</li>
- <li>When the device is online, Google sends the message to the device.</li>
- <li>On the device, the system broadcasts the message to the specified Android
-application via Intent broadcast with proper permissions, so that only the targeted
-ndroid application gets the message. This wakes the Android application up.
-The Android application does not need to be running beforehand to receive the message.</li>
- <li>The Android application processes the message. </li>
+BUILD SUCCESSFUL
+Total time: 0 seconds
+</pre>
+
+ <li>Deploy the <code>dist/gcm-demo.war</code> to your running server. For instance, if you're using Jetty, copy <code>gcm-demo.war</code> to the <code>webapps</code> directory of the Jetty installation.</li>
+ <li>Open the server's main page in a browser. The URL depends on the server you're using and your machine's IP address, but it will be something like <code>http://192.168.1.10:8080/gcm-demo/home</code>, where <code>gcm-demo</code> is the application context and <code>/home</code> is the path of the main servlet.
+
+ </li>
</ol>
+<p class="note"><strong>Note:</strong> You can get the IP by running <code>ifconfig</code> on Linux or MacOS, or <code>ipconfig</code> on Windows. </p>
-<p>The following sections describe the basic requirements for
-sending messages.</p>
+<p> You server is now ready.</p>
-<h3 id="target">Target</h3>
-<p>Required. When your app server sends a message in GCM, it must specify a target.</p>
-<p>For HTTP you must specify the target as one of:</p>
-<ul>
-<li><code>registration_ids</code>: For sending to 1 more more devices (up to 1000).
-When you send a message to multiple registration IDs, that is called a multicast message.</li>
-<li><code>notification_key</code>: For sending to multiple devices owned by a single user.</li>
-</ul>
-<p>For CCS (XMPP):</p>
-<ul>
-<li>You must specify the target as the &quot;to&quot; field, where the &quot;to&quot;
-field may contain a single registration ID or a notification key.
-CCS does not support multicast messaging.</li>
-</ul>
-<h3 id="payload">Payload</h3>
-<p>Optional. If you are including a payload in the message, you use the <code>data</code>
-parameter to include the payload. This applies for both HTTP and CCS.</p>
-
-<h3 id="params">Message parameters</h3>
-
-<p>The following table lists the parameters that a 3rd-party app server might
-include in the JSON messages it sends to a connection server. See the "Where Supported"
-column for information about which connection servers support that particular
-parameter.</p>
-
-<p class="table-caption" id="table1">
- <strong>Table 1.</strong> Message parameters.</p>
-
-<table>
- <tr>
- <th>Field</th>
- <th>Description</th>
-<th>Where Supported</th>
-</tr>
- <td><code>to</code></td>
-<td>In CCS, used in place of <code>registration_ids</code> to specify the
-recipient of a message. Its value must be a registration ID.
-The value is a string. Required.</td>
-<td>CCS</td>
-</tr>
-<tr>
-<td><code>message_id</code></td>
-<td>In CCS, uniquely identifies a message in an XMPP connection. The value is a
-string that uniquely identifies the associated message. The value is a string. Required.</td>
-<td>CCS</td>
-</tr>
-<tr>
-<td><code>message_type</code></td>
-<td>In CCS, indicates a special status message, typically sent by the system.
-However, your app server also uses this parameter to send an 'ack' or 'nack'
-message back to the CCS connection server. For more discussion of this topic, see
-<a href="ccs.html">Cloud Connection Server</a>. The value is a string. Optional.</td>
-<td>CCS</td>
-<tr>
- <td><code>registration_ids</code></td>
- <td>A string array with the list of devices (registration IDs) receiving the
-message. It must contain at least 1 and at most 1000 registration IDs. To send a
-multicast message, you must use JSON. For sending a single message to a single
-device, you could use a JSON object with just 1 registration id, or plain text
-(see below). A request must include a recipient&mdash;this can be either a
-registration ID, an array of registration IDs, or a {@code notification_key}.
-Required.</td>
-<td>HTTP</td>
-</tr>
- <tr>
- <td><code>notification_key</code></td>
- <td>A string that maps a single user to multiple registration IDs associated
-with that user. This allows a 3rd-party server to send a single message to
-multiple app instances (typically on multiple devices) owned by a single user.
-A 3rd-party server can use {@code notification_key} as the target for a message
-instead of an individual registration ID (or array of registration IDs). The maximum
-number of members allowed for a {@code notification_key} is 10. For more discussion
-of this topic, see <a href="notifications.html">User Notifications</a>. Optional.
-</td>
-<td style="width:100px">HTTP. This feature is supported in CCS, but you use it by
-specifying a notification key in the &quot;to&quot; field.</td>
-</tr>
- <tr>
- <td><code>collapse_key</code></td>
- <td>An arbitrary string (such as &quot;Updates Available&quot;) 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 &quot;last&quot; message may not actually be the last
-message sent by the application server. Collapse keys are also called
-<a href="#s2s">send-to-sync messages</a>.
-<br>
-<strong>Note:</strong> GCM allows a maximum of 4 different collapse keys to be
-used by the GCM server
-at any given time. In other words, the GCM server can simultaneously store 4
-different send-to-sync messages per device, each with a different collapse key.
-If you exceed
-this number GCM will only keep 4 collapse keys, with no guarantees about which
-ones they will be. See <a href="adv.html#collapsible">Advanced Topics</a> for more
-discussion of this topic. Optional.</td>
-<td>CCS, HTTP</td>
-</tr>
- <tr>
- <td><code>data</code></td>
- <td>A JSON object whose fields represents the key-value pairs of the message's
-payload data. If present, the payload data it will be
-included in the Intent as application data, with the key being the extra's name.
-For instance, <code>"data":{"score":"3x1"}</code> would result in an intent extra
-named <code>score</code> whose value is the string <code>3x1</code>.
-There is no limit on the number of key/value pairs, though there is a limit on
-the total size of the message (4kb). The values could be any JSON object, but we
-recommend using strings, since the values will be converted to strings in the GCM
-server anyway. If you want to include objects or other non-string data types
-(such as integers or booleans), you have to do the conversion to string yourself.
-Also note that the key cannot be a reserved word (<code>from</code> or any word
-starting with <code>google.</code>). To complicate things slightly, there are
-some reserved words (such as <code>collapse_key</code>) that are technically
-allowed in payload data. However, if the request also contains the word, the
-value in the request will overwrite the value in the payload data. Hence using
-words that are defined as field names in this table is not recommended, even in
-cases where they are technically allowed. Optional.</td>
-<td>CCS, HTTP</td>
-</tr>
- <tr>
- <td><code>delay_while_idle</code></td>
- <td>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 <code>collapse_key</code> value will be
-sent. The default value is <code>false</code>, and must be a JSON boolean. Optional.</td>
-<td>CCS, HTTP</td>
-</tr>
- <tr>
- <td><code>time_to_live</code></td>
- <td>How long (in seconds) the message should be kept on GCM storage if the
-device is offline. Optional (default time-to-live is 4 weeks, and must be set as
-a JSON number).</td>
-<td>CCS, HTTP</td>
-</tr>
-<tr>
- <td><code>restricted_package_name</code></td>
- <td>A string containing the package name of your application. When set, messages
-will only be sent to registration IDs that match the package name. Optional.
- </td>
-<td>HTTP</td>
-</tr>
-<tr>
- <td><code>dry_run</code></td>
- <td>If included, allows developers to test their request without actually
-sending a message. Optional. The default value is <code>false</code>, and must
-be a JSON boolean.
- </td>
-<td>HTTP</td>
-</tr>
-</table>
-
-<p>If you want to test your request (either JSON or plain text) without delivering
-the message to the devices, you can set an optional HTTP or JSON parameter called
-<code>dry_run</code> with the value <code>true</code>. The result will be almost
-identical to running the request without this parameter, except that the message
-will not be delivered to the devices. Consequently, the response will contain fake
-IDs for the message and multicast fields.</p>
-
-<h3 id="plain-text">Plain text (HTTP only)</h3>
-
-<p>If you are using plain text instead of JSON, the message fields must be set as
-HTTP parameters sent in the body, and their syntax is slightly different, as
-described below:
-<table>
- <tr>
- <th>Field</th>
- <th>Description</th>
- </tr>
- <tr>
- <td><code>registration_id</code></td>
- <td>Must contain the registration ID of the single device receiving the message.
-Required.</td>
- </tr>
- <tr>
- <td><code>collapse_key</code></td>
- <td>Same as JSON (see previous table). Optional.</td>
- </tr>
- <tr>
- <td><code>data.&lt;key&gt;</code></td>
-
- <td>Payload data, expressed as parameters prefixed with <code>data.</code> and
-suffixed as the key. For instance, a parameter of <code>data.score=3x1</code> would
-result in an intent extra named <code>score</code> whose value is the string
-<code>3x1</code>. There is no limit on the number of key/value parameters, though
-there is a limit on the total size of the message. Also note that the key cannot
-be a reserved word (<code>from</code> or any word starting with
-<code>google.</code>). To complicate things slightly, there are some reserved words
-(such as <code>collapse_key</code>) that are technically allowed in payload data.
-However, if the request also contains the word, the value in the request will
-overwrite the value in the payload data. Hence using words that are defined as
-field names in this table is not recommended, even in cases where they are
-technically allowed. Optional.</td>
-
- </tr>
- <tr>
- <td><code>delay_while_idle</code></td>
- <td>Should be represented as <code>1</code> or <code>true</code> for
-<code>true</code>, anything else for <code>false</code>. Optional. The default
-value is <code>false</code>.</td>
- </tr>
- <tr>
- <td><code>time_to_live</code></td>
- <td>Same as JSON (see previous table). Optional.</td>
- </tr>
-<tr>
- <td><code>restricted_package_name</code></td>
- <td>Same as JSON (see previous table). Optional.
- </td>
-</tr>
-<tr>
- <td><code>dry_run</code></td>
- <td>Same as JSON (see previous table). Optional.
- </td>
-</tr>
-</table>
-
-<h2 id="receive">Receiving Messages</h2>
-
-<p>This is the sequence of events that occurs when an Android application
-installed on a mobile device receives a message:</p>
+<h3 id="appengine-setup">Using App Engine for Java</h3>
+<p>To set up the server using a standard App Engine for Java:</p>
<ol>
- <li>The system receives the incoming message and extracts the raw key/value
-pairs from the message payload, if any.</li>
- <li>The system passes the key/value pairs to the targeted Android application
-in a <code>com.google.android.c2dm.intent.RECEIVE</code> Intent as a set of
-extras.</li>
- <li>The Android application extracts the raw data
-from the <code>com.google.android.c2dm.intent.RECEIVE</code><code> </code>Intent
-by key and processes the data.</li>
+ <li>Get the files from the <a href="http://code.google.com/p/gcm">open source site</a>, as described above.</p>
+ </li>
+ <li>In a text editor, edit <code>samples/gcm-demo-appengine/src/com/google/android/gcm/demo/server/ApiKeyInitializer.java</code> and replace the existing text with the API key obtained above.
+
+ <p class="note"><strong>Note:</strong> The API key value set in that class will be used just once to create a persistent entity on App Engine. If you deploy the application, you can use App Engine's <code>Datastore Viewer</code> to change it later.</p>
+
+ </li>
+ <li>In a shell window, go to the <code>samples/gcm-demo-appengine</code> directory.</li>
+ <li>Start the development App Engine server by <code>ant runserver</code>, using the <code>-Dsdk.dir</code> to indicate the location of the App Engine SDK and <code>-Dserver.host</code> to set your server's hostname or IP address:</li>
+
+<pre class="prettyprint">
+$ ant -Dsdk.dir=/opt/google/appengine-java-sdk runserver -Dserver.host=192.168.1.10
+Buildfile: gcm-demo-appengine/build.xml
+
+init:
+ [mkdir] Created dir: gcm-demo-appengine/dist
+
+copyjars:
+
+compile:
+
+datanucleusenhance:
+ [enhance] DataNucleus Enhancer (version 1.1.4) : Enhancement of classes
+ [enhance] DataNucleus Enhancer completed with success for 0 classes. Timings : input=28 ms, enhance=0 ms, total=28 ms. Consult the log for full details
+ [enhance] DataNucleus Enhancer completed and no classes were enhanced. Consult the log for full details
+
+runserver:
+ [java] Jun 15, 2012 8:46:06 PM com.google.apphosting.utils.jetty.JettyLogger info
+ [java] INFO: Logging to JettyLogger(null) via com.google.apphosting.utils.jetty.JettyLogger
+ [java] Jun 15, 2012 8:46:06 PM com.google.apphosting.utils.config.AppEngineWebXmlReader readAppEngineWebXml
+ [java] INFO: Successfully processed gcm-demo-appengine/WebContent/WEB-INF/appengine-web.xml
+ [java] Jun 15, 2012 8:46:06 PM com.google.apphosting.utils.config.AbstractConfigXmlReader readConfigXml
+ [java] INFO: Successfully processed gcm-demo-appengine/WebContent/WEB-INF/web.xml
+ [java] Jun 15, 2012 8:46:09 PM com.google.android.gcm.demo.server.ApiKeyInitializer contextInitialized
+ [java] SEVERE: Created fake key. Please go to App Engine admin console, change its value to your API Key (the entity type is 'Settings' and its field to be changed is 'ApiKey'), then restart the server!
+ [java] Jun 15, 2012 8:46:09 PM com.google.appengine.tools.development.DevAppServerImpl start
+ [java] INFO: The server is running at http://192.168.1.10:8080/
+ [java] Jun 15, 2012 8:46:09 PM com.google.appengine.tools.development.DevAppServerImpl start
+ [java] INFO: The admin console is running at http://192.168.1.10:8080/_ah/admin
+</pre>
+
+ <li>Open the server's main page in a browser. The URL depends on the server you're using and your machine's IP address, but it will be something like <code>http://192.168.1.10:8080/home</code>, where <code>/home</code> is the path of the main servlet.</li>
+
+ <p class="note"><strong>Note:</strong> You can get the IP by running <code>ifconfig</code> on Linux or MacOS, or <code>ipconfig</code> on Windows.</p>
+
</ol>
+<p> You server is now ready.</p>
+
-<p>See the documentation for each connection server for more detail on how it
-handles responses.</p>