Help us understand the problem. What is going on with this article?

Azure Notification Hubsを使用してiOSとAndroidにPush通知を行う (3) ~配信編~

More than 3 years have passed since last update.

配信編

前回の実装編では、iOS/AndroidのTokenをAzure Notification Hubsに登録し、コンソールからPush通知を送信/受信できることを確認しました。

今回は、プログラムでAzure Notification HubsnのPush通知の送信や登録の管理等を行って行きます。

Azure Notification Hubsには、Notification Hubs REST APIsが提供されていおり、JavaとNode.jsのSDKも提供されています。
REST APIを直接使用するには、認証,アクセストークンなどの仕組みを理解しなければならないため、それらをラップしたSDKを使用することで効率的に開発することが出来ます。

※ PHPとPythonはラッパーサンプルが提供されています。

JavaからPush通知

SDKのビルド

  1. GitHubからAzure/azure-notificationhubs-java-backend をPCローカルにcloneする。

    $ git clone https://github.com/Azure/azure-notificationhubs-java-backend.git
    
  2. Maven構成のプロジェクトとなっているので、以下のコードでビルド。

    $ mvn clean package
    
  3. TESTが失敗し、"BUILD FAILURE"となる場合は、暫定的に以下の行をコメントアウトして、再ビルド。

    <!--
    <testSourceDirectory>test</testSourceDirectory>
    <testResources>
        <testResource>
            <directory>test</directory>
            <excludes>
                <exclude>**/*.java</exclude>
            </excludes>
        </testResource>
    </testResources>
    -->
    
  4. ビルドに成功すると、target ディレクトリにjarファイルが作成される。
    NotificationHubs-0.0.3.jar

アプリの実装

  1. Notification Hubのクライアントのインスタンスを作成

    String connectionString = "Endpoint=sb://x.servicebus.windows.net/;SharedAccessKeyName=DefaultFullSharedAccessSignature;SharedAccessKey=...";
    String hubPath = "AzureNotificationHubsExample";
    NotificationHub hub = new NotificationHub(connectionString, hubPath);
    
    • connectionString に、Notification Hubの[DefaultFullSharedAccessSignature]の文字列を指定
    • hubPath に、Notification Hubの名前を指定
  2. Push通知の送信

    1. iOSへ送信する

      String message = "Hello Azure World!";
      String body = String.format("{\"aps\":{\"alert\":\"%s\"}}", message);
      
      Notification notifiation = Notification.createAppleNotifiation(body);
      
      hub.sendNotification(notifiation);
      
    2. Androidへ送信する

      String message = "Hello Azure World!";
      String body = String.format("{\"data\":{\"message\":\"%s\"}}", message);
      
      Notification notifiation = Notification.createGcmNotifiation(body);
      
      hub.sendNotification(notifiation);
      
  3. タグを使って指定した範囲にPush通知を送信
    iOS/Android アプリからAzure Notification HubsへのPush通知のトークンの登録時にタグを指定することが出来ます。
    タグに、カテゴリーやグループの識別子や、ユーザー、デバイス識別子(UUID等)を設定しておくことで、送信先の範囲を絞り込むことに使用すること出来ます。

    1. iOS/Android アプリからタグを指定してPush通知のトークンを登録
      Azure Notification Hubsを使用してiOSとAndroidにPush通知を行う (2) ~実装編~で、実装したコードの登録のロジックに、UUIDのタグを追加します。

      1. iOS

        func application(application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: NSData) {
            // NotificationHubへ登録
            let hub = SBNotificationHub(
                connectionString: "Endpoint=sb://x.servicebus.windows.net/;SharedAccessKeyName=DefaultListenSharedAccessSignature;SharedAccessKey=...",
                notificationHubPath: "AzureNotificationHubsExample")
        
            // タグにUUIDを追加
            let uuid = NSUUID().UUIDString;
            let tags: Set<String> = ["UUID:\(uuid)"]
        
            hub.registerNativeWithDeviceToken(deviceToken, tags: tags) { (error) in
                if (error != nil) {
                    print("Error registering for notifications.", error)
                } else {
                    print("Success registering for notifications.", deviceToken)
                }
            }
        }
        
      2. Android

        private void sendRegistrationToServer(String refreshedToken) {
            NotificationHub hub = new NotificationHub(
                    "AzureNotificationHubsExample",
                    "Endpoint=sb://x.windows.net/;SharedAccessKeyName=DefaultListenSharedAccessSignature;SharedAccessKey=...",
                    this);
        
            try {
                // タグにUUIDを追加
                String uuid = UUID.randomUUID().toString();
                String[] tags = {"UUID:" + uuid};
        
                Registration registration = hub.register(refreshedToken, tags);
                String registrationId = registration.getRegistrationId();
        
                Log.d(TAG, "Registration ID: " + registrationId);
            } catch (Exception e) {
                e.printStackTrace();
            }
        } 
        
    2. タグを指定してPush通知を送信
      タグにUUIDを指定

      Set<String> tags = new HashSet<String>();
      tags.add("UUID:4151CA6C-FE7B-48C4-83AC-F1FEDD8C37AA");
      
      hub.sendNotification(notifiation, tags);
      

      UUIDのデバイスにのみPush通知が送信されます。

  4. 登録の編集
    タグに設定したカテゴリーやグループの識別子を編集することが可能です。

    • 登録を取得
    RegistrationIdで取得
    Registration registration = hub.getRegistration(registrationId);
    
    Tagで検索
    CollectionResult collectionResult = hub.getRegistrationsByTag("SINGLE");
    for (Registration registration:collectionResult.getRegistrations()) {
        // do logic
    }
    
    
    • 登録を更新
    // タグを編集
    Set<String> tags = new HashSet<String>();
    tags.add("AGE_GROUP:F2");
    tags.add("FEMALE");
    tags.add("SINGLE");
    
    registration.setTags(tags);
    
    hub.updateRegistration(registration);
    
    • 登録を削除
    hub.deleteRegistration(registrationId);
    
  5. デバイスの登録
    SDKからもPush通知のトークンの登録が出来ます。

        Registration reg = null;
        switch (platform) {
            case IOS:
                reg = new AppleRegistration(oken);
                break;
            case ANDROID:
                reg = new GcmRegistration(token);
                break;
            default:
        }
        reg.getTags().add("UUID:" + uuid);
        reg.getTags().add("PLATFORM:" + platform);
        Registration registration = hub.createRegistration(reg);
    
        String registrationId = registration.getRegistrationId();
    
    
  6. 補足とまとめ

    • Azure Notification Hubsは、同時に複数デバイスにPush通知の送信が出来る。
    • 送信対象のデバイスはタグで絞り込むことが出来る。
    • プラットフォーム毎にPush通知を送信しなければならない。
      • プラットフォームを意識しないで送信することも出来れば良かったのだが...
    • APNS/FCMのPushのトークンを使用して、Push通知の送信は出来ない。
    • 登録時に発行されるRegistrationIdを指定して、Push通知の送信は出来ない。
    • デバイス個々にPush通知を送信をしたい場合は、タグにデバイス識別子を設定する工夫が必要。
    • 登録の更新でトークンを更新することは出来ない。Pushのトークンのリフレッシュが発生した場合、登録は削除と作成しなければならない。
    • 登録時に発行されるRegistrationIdが、iOSのSDKでは取得できない...
      • アプリのサービスを想定すると、個人情報やデバイス情報などとPush通知をまとめて管理する必要があると思うので、各プラットフォームが直接Azure Notification Hubsに登録するのではなく、Web App サーバでAPIで登録を管理した方がよいと考える。

Push通知は、バックエンドのAnalyticsの情報を元にターゲットの絞込やメッセージの作成をすることが想定されるので、mBaaSとしてそのあたりの強化を期待したい

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away