公開と登録

Nearby Messages API は、付近のデバイスが小さなデータ ペイロードを交換できるようにするパブリッシュ / サブスクライブ API です。デバイスがメッセージをパブリッシュすると、近くのデバイスがそのメッセージを受信できます。良好なパフォーマンスを維持するため、メッセージのサイズはかなり小さくする必要があります。このサービスは、写真や動画などの大きなオブジェクトを交換するためのものではありません。

近くのデバイスのセットは、Bluetooth と近超音波(可聴範囲外)オーディオを介した小さなトークンの交換によって決定されます。デバイスが近くのデバイスからトークンを検出すると、そのトークンを Nearby Messages サーバーに送信して検証し、アプリケーションの現在のサブスクリプション セットに配信するメッセージがあるかどうかを確認します。

アプリケーションは、デバイスの検出に使用されるメディアのセットと、メディアがトークンのブロードキャストとトークンのスキャンに使用されるかどうかを制御できます。デフォルトでは、すべてのメディアでブロードキャストとスキャンが行われます。サブセットまたはメディアで検出を行い、ブロードキャストまたはスキャンを行うかどうかを制御するには、パブリケーションとサブスクリプションを作成するときに追加のパラメータを渡す必要があります。

このライブラリは iOS 7 以降で実行され、iOS 8 SDK でビルドされます。

メッセージ マネージャーを作成する

このコードは、パブリッシュとサブスクライブを可能にするメッセージ マネージャー オブジェクトを作成します。メッセージ交換は認証されていないため、iOS 用の公開 API キーを指定する必要があります。プロジェクトの Google Developers Console エントリを使用して作成できます。

Objective-C

#import <GNSMessages.h>

GNSMessageManager *messageManager =
    [[GNSMessageManager alloc] initWithAPIKey:@"API_KEY"];

Swift

let messageManager = GNSMessageManager(APIKey: "API_KEY")

メッセージをパブリッシュする

このコード スニペットは、名前を含むメッセージをパブリッシュする方法を示しています。 パブリケーション オブジェクトが存在する限り、パブリケーションは有効です。パブリッシュを停止するには、パブリケーション オブジェクトを解放します。

Objective-C

id<GNSPublication> publication =
    [messageManager publicationWithMessage:[GNSMessage messageWithContent:[name dataUsingEncoding:NSUTF8StringEncoding]]];

Swift

let publication =
    messageManager.publication(with: GNSMessage(content: name.data(using: .utf8)))

メッセージをサブスクライブする

このコード スニペットは、前のパブリケーション スニペットで共有されているすべての名前をサブスクライブする方法を示しています。サブスクリプション オブジェクトが存在する限り、サブスクリプションは有効です。サブスクライブを停止するには、サブスクリプション オブジェクトを解放します。

メッセージ検出ハンドラは、メッセージをパブリッシュしている近くのデバイスが検出されたときに呼び出されます。メッセージ消失ハンドラは、メッセージが観測されなくなったときに呼び出されます(デバイスが範囲外になったか、メッセージのパブリッシュを停止した)。

Objective-C

id<GNSSubscription> subscription =
    [messageManager subscriptionWithMessageFoundHandler:^(GNSMessage *message) {
      // Add the name to a list for display
    }
    messageLostHandler:^(GNSMessage *message) {
      // Remove the name from the list
    }];

Swift

let subscription =
    messageManager.subscription(messageFoundHandler: { (message: GNSMessage?) in
      // Add the name to a list for display
    },
    messageLostHandler: { (message: GNSMessage?) in
      // Remove the name from the list
    })

検出メディア

デフォルトでは、両方のメディア(オーディオと Bluetooth)を使用して近くのデバイスを検出し、両方のメディアでブロードキャストとスキャンが行われます。 場合によっては、アプリの Info.plist に次のエントリを追加する必要があります。

  • アプリがオーディオを使用してスキャンする場合は、マイクを使用する理由を説明する文字列である NSMicrophoneUsageDescription を追加します。 例: 「マイクは近くのデバイスから匿名トークンをリッスンします。」

  • アプリが BLE を使用してブロードキャストする場合は、BLE で広告を配信する理由を説明する文字列である NSBluetoothPeripheralUsageDescription を追加します。例: 「匿名トークンは Bluetooth を介して広告され、近くのデバイスを検出します。」

場合によっては、アプリが 1 つのメディアのみを使用する必要があり、そのメディアでブロードキャストとスキャンの両方を行う必要がないことがあります。

たとえば、オーディオのみでブロードキャストしているセットトップ ボックスに接続するように設計されたアプリは、オーディオでスキャンして検出するだけで済みます。次のスニペットは、検出にオーディオ スキャンのみを使用して、そのセットトップ ボックスにメッセージをパブリッシュする方法を示しています。

Objective-C

id<GNSPublication> publication = [messageManager publicationWithMessage:message
    paramsBlock:^(GNSPublicationParams *params) {
      params.strategy = [GNSStrategy strategyWithParamsBlock:^(GNSStrategyParams *params) {
        params.discoveryMediums = kGNSDiscoveryMediumsAudio;
        params.discoveryMode = kGNSDiscoveryModeScan;
      }];
    }];

Swift

let publication = messageManager.publication(with: message,
    paramsBlock: { (params: GNSPublicationParams?) in
      guard let params = params else { return }
      params.strategy = GNSStrategy(paramsBlock: { (params: GNSStrategyParams?) in
        guard let params = params else { return }
        params.discoveryMediums = .audio
        params.discoveryMode = .scan
      })
    })

デバッグ ロギングを有効にする

デバッグ ロギングでは、Nearby Messages をアプリに統合する際に発生する可能性のある問題を追跡するのに役立つ重要な内部イベントがコンソールに出力されます。テクニカルサポートにお問い合わせいただいた場合は、これらのログをご提供いただくようお願いすることがあります。

メッセージ マネージャーを作成する前に有効にする必要があります。 次のコード スニペットは、デバッグ ロギングを有効にする方法を示しています。

Objective-C

[GNSMessageManager setDebugLoggingEnabled:YES];

Swift

GNSMessageManager.setDebugLoggingEnabled(true)

Nearby の権限の状態をトラッキングする

デバイスの検出を有効にするには、ユーザーの同意が必要です。これは、Nearby の権限の状態によって示されます。パブリケーションまたはサブスクリプションを作成する最初の呼び出しで、ユーザーに同意ダイアログが表示されます。ユーザーが同意しない場合、デバイスの検出は機能しません。この場合、アプリはデバイスの検出が無効になっていることをユーザーに通知するメッセージを表示する必要があります。権限の状態は NSUserDefaults に保存されます。

次のスニペットは、権限の状態をサブスクライブする方法を示しています。 権限の状態が変更されるたびに権限の状態変更ハンドラが呼び出されます。ユーザーが権限を付与または拒否するまで、最初の呼び出しは行われません。 サブスクライブを停止するには、権限オブジェクトを解放します。

Objective-C

GNSPermission *nearbyPermission = [[GNSPermission alloc] initWithChangedHandler:^(BOOL granted) {
  // Update the UI here
}];

Swift

let nearbyPermission = GNSPermission(changedHandler: { (granted: Bool) in
  // Update the UI here
})

アプリでは、ユーザーが権限の状態を変更できるようにすることができます(設定ページの切り替えスイッチを使用するなど)。

権限の状態を取得して設定する方法の例を次に示します。

Objective-C

BOOL permissionState = [GNSPermission isGranted];
[GNSPermission setGranted:!permissionState];  // toggle the state

Swift

let permissionState = GNSPermission.isGranted()
GNSPermission.setGranted(!permissionState)  // toggle the state

Nearby に影響するユーザー設定をトラッキングする

ユーザーがマイクの権限を拒否した場合、Bluetooth の権限を拒否した場合、または Bluetooth がオフになっている場合、Nearby は正常に動作しないか、まったく動作しない可能性があります。 このような場合、アプリはニアバイシェアのオペレーションが妨げられていることをユーザーに通知するメッセージを表示する必要があります。次のスニペットは、メッセージ マネージャーの作成時にハンドラを渡すことで、これらのユーザー設定の状態をトラッキングする方法を示しています。

Objective-C

GNSMessageManager *messageManager = [[GNSMessageManager alloc]
    initWithAPIKey:API_KEY
       paramsBlock:^(GNSMessageManagerParams *params) {
         params.microphonePermissionErrorHandler = ^(BOOL hasError) {
           // Update the UI for microphone permission
         };
         params.bluetoothPowerErrorHandler = ^(BOOL hasError) {
           // Update the UI for Bluetooth power
         };
         params.bluetoothPermissionErrorHandler = ^(BOOL hasError) {
           // Update the UI for Bluetooth permission
         };
}];

Swift

let messageManager = GNSMessageManager(
         APIKey: API_KEY,
    paramsBlock: { (params: GNSMessageManagerParams?) in
      guard let params = params else { return }
      params.microphonePermissionErrorHandler = { (hasError: Bool) in
        // Update the UI for microphone permission
      }
      params.bluetoothPowerErrorHandler = { (hasError: Bool) in
        // Update the UI for Bluetooth power
      }
      params.bluetoothPermissionErrorHandler = { (hasError: Bool) in
        // Update the UI for Bluetooth permission
      }
    })

Nearby の権限ダイアログをオーバーライドする

パブリケーションとサブスクリプションに渡すパラメータによっては、Nearby が機能する前に、iOS がさまざまな権限を要求することがあります。たとえば、デフォルトの戦略では、近超音波オーディオで送信されたデータをリッスンするため、iOS はマイクの使用権限を要求します。このような場合、ニアバイシェアは、ユーザーに権限の付与を求める理由を説明する「事前確認」ダイアログを表示します。

カスタムの「プリフライト」ダイアログを表示する場合は、パブリケーションまたはサブスクリプションのパラメータで permissionRequestHandler パラメータをカスタム ブロックに設定します。カスタム ブロックは、ユーザーが応答した後に permissionHandler ブロックを呼び出す必要があります。 次のスニペットは、パブリケーションでこれを行う方法を示しています。

Objective-C

id<GNSPublication> publication =
    [messageManager publicationWithMessage:[GNSMessage messageWithContent:[name dataUsingEncoding:NSUTF8StringEncoding]]
                               paramsBlock:^(GNSPublicationParams *params) {
                                 params.permissionRequestHandler = ^(GNSPermissionHandler permissionHandler) {
                                   // Show your custom dialog here.
                                   // Don't forget to call permissionHandler() with YES or NO when the user dismisses it.
                                 };
                               }];

Swift

let publication =
    messageManager.publication(with: GNSMessage(content: name.data(using: .utf8)),
        paramsBlock: { (params: GNSPublicationParams?) in
          guard let params = params else { return }
          params.permissionRequestHandler = { (permissionHandler: GNSPermissionHandler?) in
            // Show your custom dialog here.
            // Don't forget to call permissionHandler() with true or false when the user dismisses it.
          }
        })

バックグラウンド オペレーション

デバイスの検出に BLE を使用するパブリケーションとサブスクリプションは、バックグラウンドで動作できます。バックグラウンド モードを使用する場合は、次の点に注意してください。

  • バックグラウンド オペレーションでは BLE メディアのみを使用する必要があります。オーディオはサポートされていません。
  • バックグラウンド BLE にはバッテリーのコストが追加されます。 コストは低いですが、バックグラウンド モードを使用する前に測定する必要があります。
  • iOS は、バックグラウンドで BLE を介して広告を配信する権限をユーザーに要求します。

パブリケーションまたはサブスクリプションにバックグラウンド モードを追加するには、次の追加の手順を行います。

  • 適切に構成された GNSStrategy オブジェクトを渡して、パブリケーションまたはサブスクリプションでバックグラウンド モードと BLE のみ有効にします。 次のスニペットは、サブスクリプションでこれを行う方法を示しています。

    Objective-C

    id<GNSSubscription> subscription =
        [messageManager subscriptionWithMessageFoundHandler:^(GNSMessage *message) {
          // Add the name to a list for display
        }
        messageLostHandler:^(GNSMessage *message) {
          // Remove the name from the list
        }
        paramsBlock:^(GNSSubscriptionParams *params) {
          params.strategy = [GNSStrategy strategyWithParamsBlock:^(GNSStrategyParams *params) {
            params.allowInBackground = YES;
            params.discoveryMediums = kGNSDiscoveryMediumsBLE;
          }];
        }];
    

    Swift

    let subscription =
        messageManager.subscription(messageFoundHandler: { (message: GNSMessage?) in
          // Add the name to a list for display
        },
        messageLostHandler: { (message: GNSMessage?) in
          // Remove the name from the list
        },
        paramsBlock:{ (params: GNSSubscriptionParams?) in
          guard let params = params else { return }
          params.strategy = GNSStrategy(paramsBlock: { (params: GNSStrategyParams?) in
            guard let params = params else { return }
            params.allowInBackground = true
            params.discoveryMediums = .BLE
          })
        })
    

  • 次のエントリをアプリの Info.plist に追加します。

    • UIBackgroundModes エントリ:

      • bluetooth-central バックグラウンドでの BLE スキャン用。検出モードにスキャンが含まれている場合にのみ必要です。デフォルトでは含まれています。
      • bluetooth-peripheral バックグラウンドでの BLE 広告用。検出モードにブロードキャストが含まれている場合にのみ必要です。デフォルトでは含まれています。
    • NSBluetoothPeripheralUsageDescription BLE で広告を配信する理由を説明する 文字列。例: 「匿名トークンは Bluetooth を介して広告され、近くのデバイスを検出します。」 詳しくは、 Apple のドキュメント をご覧ください。

  • アプリは、バックグラウンドで実行中にシステムによっていつでも強制終了される可能性があります。 バックグラウンド モードがユーザーが有効または無効にできる設定である場合、アプリは次のことを行う必要があります。

    • ユーザーが変更するたびに、バックグラウンド モードの値を NSUserDefaults に保存します。
    • 起動時に、NSUserDefaults から読み取り、バックグラウンド モードが有効になっている場合は、Nearby のパブリケーションまたはサブスクリプションを復元します。

バックグラウンド通知

アプリがバックグラウンドでサブスクリプションがメッセージを受信したときにユーザーに通知する場合は、 ローカル通知を使用できます。

アプリに追加する手順は次のとおりです。

  • 起動時にローカル通知に登録します。

    Objective-C

    if ([UIApplication instancesRespondToSelector:@selector(registerUserNotificationSettings:)]) {
      [[UIApplication sharedApplication] registerUserNotificationSettings:
          [UIUserNotificationSettings settingsForTypes:
              UIUserNotificationTypeAlert | UIUserNotificationTypeBadge | UIUserNotificationTypeSound
                                            categories:nil]];
    }
    

    Swift

    UIApplication.shared.registerUserNotificationSettings(
        UIUserNotificationSettings(types: [.alert, .badge, .sound], categories: nil))
    

  • サブスクリプションのメッセージ検出ハンドラでローカル通知を送信します。

    Objective-C

    GNSMessageHandler myMessageFoundHandler = ^(GNSMessage *message) {
        // Send a local notification if not in the foreground.
        if ([UIApplication sharedApplication].applicationState != UIApplicationStateActive) {
          UILocalNotification *localNotification = [[UILocalNotification alloc] init];
          localNotification.alertBody = @"Message received";
          [[UIApplication sharedApplication] presentLocalNotificationNow:localNotification];
        }
        // Process the new message...
      };
    

    Swift

    let myMessageFoundHandler: GNSMessageHandler = { (message: GNSMessage?) in
      // Send a local notification if not in the foreground.
      if UIApplication.shared.applicationState != .active {
        let localNotification = UILocalNotification()
        localNotification.alertBody = "Message received"
        UIApplication.shared.presentLocalNotificationNow(localNotification)
      }
      // Process the new message...
    }