HOME > ソフテックだより > 第235号(2015年6月3日発行) 技術レポート「GCMでのプッシュ通知を利用してみた」

「ソフテックだより」では、ソフトウェア開発に関する情報や開発現場における社員の取り組みなどを定期的にお知らせしています。
さまざまなテーマを取り上げていますので、他のソフテックだよりも、ぜひご覧下さい。

ソフテックだより(発行日順)のページへ
ソフテックだより 技術レポート(技術分野別)のページへ
ソフテックだより 現場の声(シーン別)のページへ


ソフテックだより 第235号(2015年6月3日発行)
技術レポート

「GCMでのプッシュ通知を利用してみた」

1. はじめに

私は入社6年目の社員で、主に組み込みソフトとパソコン用ソフトを担当しています。
近年、制御システムの一環としてモバイル端末の利用が多くなってきているので、PHPやAndroidの開発を担当することが増えてきました。今回は、あるシステム開発の時、利用してみたGCMでのプッシュ通知について簡単にご紹介させていただきます。

2. GCMでのプッシュ通知とは

GCMとは、Google Cloud Messaging for Android のことで、開発者がサーバーから Android デバイス上の Android アプリケーションにデータを送信できるようにするサービスです。GCMでのプッシュ通知とは、システム側がGCMサーバーと連携して情報をユーザーに通知する方式のことです。ユーザーの端末がモバイル回線やWi-Fiに接続していればいつでもプッシュ通知を受け取ることができます。

3. プッシュ通知の利用目的

図1に示したように、ある監視システムにおいて、監視用PCが監視機器から収集したデータをアプリケーションサーバーに上げて蓄積しています。監視中、異常などのイベントが発生した場合、リアルタイムにユーザーのモバイル端末に通知したい機能の実現方法について検討した結果、プッシュ通知を利用することにしました。

図1に示したように、ある監視システムにおいて、監視用PCで常時に監視を行い、収集したデータをアプリケーションサーバーに蓄積しています。
図1.監視システムの通知仕組み

本システムにおいて、プッシュ通知を利用するメリットについて、以下の点が挙げられます。

  • 正しく設定すれば、リアルタイムに通知が受け取れる
  • ユーザーが操作しなくても端末がスリープ状態でも、通知が受け取れる
  • アプリの常駐が不要なので、通信量やバッテリ消費が抑えられる
  • 開発コストが比較的に少ない

4. GCMでのプッシュ通知の利用仕組み

4-1. APIキーなどの取得

プッシュ通知を利用するための手順を以下に簡単にまとめます。

(1)
Googleアプリの管理コンソールにログインし、「Google Cloud Messaging for Android」サービスを有効にする
(2)
GoogleのAPIコンソールからAndroidアプリを特定するためにAPIキーを取得する
(3)
同じくAPIコンソールのURLからProject IDを控える
(4)
GCM ID要求やプッシュ通知を受けるAndroidアプリを作成する
(5)
GCMサーバーへプッシュ通知を要求するサーバーアプリを作成する

4-2. GCMサーバーからID取得の仕組み

プッシュ通知を利用するためには、端末個別にAndroidアプリがGCMサーバーからIDを取得し、サーバーへ保存依頼を行う必要があります。図2ではその仕組みを示しています。GCMサーバーにおいてIDの有効期限が切れていない限り、次回からIDの再取得が不要です。ここで、端末アプリからGCMサーバーに対して登録依頼を行うときに、APIコンソールから控えたProject IDが使われます。

図2ではその仕組みを示しています。
図2.GCMサーバーからID取得の仕組み

Androidアプリの実装で一つの注意点として、GCMを使用するためにマニフェストに以下のようないくつかの内容を追加する必要があります。具体的なサンプルソースを下記に示します。

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="jp.co.softech.sample"
    ...(中略)
    
    <!--GCM利用のためのパーミッションを追加(インターネット、アカウント取得など-->
    <uses-permission android:name="android.permission.INTERNET" />
    <uses-permission android:name="android.permission.GET_ACCOUNTS" />
    <uses-permission android:name="android.permission.WAKE_LOCK" />
    <uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" />
    
    <permission
        android:name="jp.co.softech.sample.permission.C2D_MESSAGE"
        android:protectionLevel="signature" />
    <uses-permission
        android:name="jp.co.softech.sample.permission.C2D_MESSAGE" />
    
    <application
        ...(中略)
    
        <receiver
            android:name=".GcmBroadcastReceiver"
            android:permission="com.google.android.c2dm.permission.SEND" >
             <!--ブロードキャストレシーバに登録-->
             <intent-filter>
                <action android:name="com.google.android.c2dm.intent.RECEIVE" />
                <action android:name="com.google.android.c2dm.intent.REGISTRATION" />
                <category android:name="jp.co.softech.sample" />
            </intent-filter>
        </receiver>
        <!--ブロードキャストレシーバが受け取ったメッセージを処理するサービスを追加-->
        <service android:name=".GcmIntentService" />
        
    </application>

</manifest>

4-3. GCMサーバーへプッシュ通知要求の仕組み

異常発生時、アプリケーションサーバーから通知対象端末のIDと通知したい内容をGCMサーバーへ送信すれば、GCMサーバーから指定端末IDプッシュ通知を送信してくれます。図3ではその仕組みを示しています。ここで、アプリケーションサーバーからGCMサーバーへプッシュ通知を要求するときに、APIコンソールから控えたAPIキーが使われます。

ソニー製リーダー/ライター PaSoRi(RC-S380)
図3. プッシュ通知動作の仕組み

ここで、PHPアプリケーションサーバーから要求をかける場合のソースを例として下記に紹介いたします。

// Google APIキー
define("GOOGLE_API_KEY", "**********");
// GCMサーバーURL
$url = "https://android.googleapis.com/gcm/send";

$fields = array(
    "collapse_key" => date("Y/m/d H:i:s", time()),	// 折り畳みキー
                                                        // 同じキーの古いメッセージが破棄される
    'time_to_live' => 600,				// 有効期間(秒)
    "delay_while_idle" => false,			// 送信遅延あり/無し
    "registration_ids" => $registration_ids,		// 端末登録ID(複数可)
    "data" => $send_content				// 送信メッセージの文字列
);

$headers = array(
    "Authorization: key=".GOOGLE_API_KEY,
    "Content-Type: application/json"
);

$ch = curl_init();
curl_setopt($ch,CURLOPT_URL,$url);
curl_setopt($ch,CURLOPT_POST,true);
curl_setopt($ch,CURLOPT_HTTPHEADER,$headers);
curl_setopt($ch,CURLOPT_RETURNTRANSFER,true);
curl_setopt($ch,CURLOPT_SSL_VERIFYPEER,false);
curl_setopt($ch,CURLOPT_POSTFIELDS,json_encode($fields));
curl_exec($ch);
curl_close($ch);

5. 注意点

GCMでのプッシュ通知を利用する際に、前提条件や注意点を以下にまとめます。

(1)
Android4.04以前のバージョンの場合、Googleアカウントが登録されていること(Android4.04以降ならGoogleアカウントが必須ではない)
(2)
Google Play Storeがインストールされること
(3)
端末やルータにおいて、ポート5228、5229、5230が開かれていること
(4)
一回でプッシュ通知できるメッセージサイズは4KBまで
(5)
端末のスリープ状態でもプッシュ通知を受け取りたい場合、スリープ中モバイル回線やWi-Fiが無効にならないようにする必要がある
(6)
同時に多くの端末にプッシュ通知を送信する場合、届く順序の制御はできない

6. おわりに

プッシュ通知を確認するだけなら、Googleが提供しているサンプルソースを参考して、苦労せずに動作させることができました。しかし、設定の間違いや前節に記述したさまざまな注意点のことで、実際に様々な環境でリアルタイムにAndroid端末に正しく表示させるまでに大変苦労しました。

近年、プッシュ通知機能がますます重要視されています。さらに、最近リリースされたChromeにもプッシュ通知機能が搭載されることで特に注目が集まっています。そのため、今回はAndroidアプリで実現しなければいけませんでしたが、今後はPCでもモバイル端末でもChromeブラウザでプッシュ通知が利用できるようになるようです。

今後、プッシュ通知が様々な場面で役に立つことを期待したいと思っています。

(Y.N.)


関連ページへのリンク

関連するソフテックだより

ページTOPへ