Alexaスキル向け位置情報サービス



Alexaスキル向け位置情報サービス

このガイドでは、Alexaスキル開発者向けの位置情報サービス機能について紹介します。位置情報サービスは、Alexa搭載デバイスのリアルタイムの位置情報を使用する権限を、リクエストがあったときにのみ、ユーザーに要求することができます。これにより、スキルはより高度なサービスを提供できるようになります。位置情報サービスの使用を要求するスキルをユーザーが有効にすると、位置情報データをスキルと共有することに同意を求めるプロンプトがAlexaアプリに表示されます。ユーザーはいつでもAlexaアプリのAlexaプライバシー設定ページにアクセスして、スキルの権限を管理できます。

位置情報サービスの仕組み

次の図は、位置情報サービス機能による、Alexa、ユーザーデバイス、スキルの連携を示しています。

位置情報の連携
位置情報の連携


位置情報サービスの条件

位置情報を使用するスキルは、次の要件を満たす必要があります。スキルが以下の要件のいずれかに違反しているとAmazonが判断した場合、スキル認定の申請を却下または保留にし、開発者アカウントに紐づいたメールアドレスに通知することがあります。

  • スキルに適用するプライバシーポリシーへのリンクを開発者コンソールの公開ページに含める必要があります。
  • 子ども向けスキルでは使用できません。子ども向けスキルの詳細については、こちらを参照してください。
  • スキルで提供する機能やサービスをサポートするために必要な場合にのみ、位置情報を受け取る権限のリクエストが必要になることがあります。リクエストする個人情報は、ユーザーの許可、プライバシー通知、適用される法令に従ってのみ利用するようにしてください。
  • 位置情報やその他のユーザー情報を使用して、バックグラウンドでユーザーのアカウントをリンクすることはできません。つまり、1人のAlexaユーザーを同じ位置情報を持つアカウントプールのユーザーに関連付けることは認められません。ユーザーのAmazonアカウント情報は検証済みのものではなく、古い情報の可能性があります。
  • ユーザーが位置情報を必要とするリクエストを伴うスキルを呼び出すたびに、スキルは最新の位置情報を取得し、ユーザーの前回のリクエストで取得した位置データを上書きする必要があります(つまり、最新のデータのみを保存します)。

「現在のデバイスの位置情報」は、地理座標系(緯度、経度、高度など)で表されます。これは、スマートフォンや車載ナビゲーションシステムなどのモバイルデバイス向け位置情報のプロキシーとして使用されることもあります。

地理座標系を基準にしたデバイスのアドレス

「大通り585番地」のようなデバイスのアドレスは、デバイスの地理座標系とは異なるものです。モバイルデバイスは移動するので、モバイルデバイスの現在の位置情報が、登録されたデバイスアドレスと大きく異なる可能性もあります。Amazon Echoのような固定デバイスの場合、AlexaはデバイスアドレスAPIを使用してデバイスの物理アドレスを提供できます。固定デバイスが、位置情報サービスを介して地理座標系を提供することはありません。

モバイルデバイスの場合、スキルは、デバイスアドレスAPIの代わりに位置情報サービスを使用してデバイスの現在の位置情報を取得する必要がありますが、これにはいくつか例外があります。ピザ配達スキルの場合であれば、地理座標系ではなく実際のデバイスアドレスを使用することによって、正確な場所にピザを配達できます。地域検索やナビゲーションのスキルでは、ユーザーの現在地が自宅の住所と異なる場合があるため、デバイスのアドレスよりも地理座標系の方が便利です。

位置情報サービスを使用するスキルを設定する

次の手順で、位置情報サービスを使用するスキルを設定します。

  • ステップ1 – 位置情報サービスの権限を有効にする
  • ステップ2 – 位置情報サービスデータを処理できるようスキルサービスのロジックを変更する
  • ステップ3 – スキルをテストして、位置情報サービスが想定どおりに機能することを確認する

ステップ1 – 位置情報サービスの権限を有効にする

  • 開発者コンソール(https://developer.amazon.com/ja/alexa)に移動してサインインし、右上のSkillsをクリックします。

  • 開発者コンソールのスキルページで編集をクリックし、スキルを開きます。

  • ビルド > アクセス権限を選択し、位置情報サービスボタンを有効にします。このボタンを有効にしないと、スキルは位置情報を使用する権限をユーザーに要求できません。

開発者コンソールで位置情報権限を有効にした状態
開発者コンソールで位置情報権限を有効にした状態

このコンフィギュレーションにより、スキルでユーザーの動的な位置情報を使用することをAlexaが認識します。スキルで位置情報サービスが設定されており、ユーザーの権限が許可されている場合、Alexaはサービスプロバイダーインターフェース(SPI)内のユーザーの位置情報を渡します。位置情報サービスボタンが有効になっていない場合、スキルはユーザーの位置情報データを受け取ることができません。

ステップ2 – 位置情報サービスデータを処理できるようスキルサービスのロジックを変更する

スキル関数内では、ユーザーの位置情報データは、カスタムスキルのコンテキストで確認できます。これは、AWS Lambda関数またはWebサービスに送信されるJSONオブジェクトです。

具体的には、このデータは、contextオブジェクトの「Geolocation」セクション、context.Geolocationに含まれます。

次のコードサンプルでは、ユーザーのデバイスの地理座標系を出力しています。適切な権限が付与されている場合、Alexa搭載デバイスと位置情報サービスを使用しているユーザーのみが、地理座標系をスキルと共有できます。ユーザーのデバイスが位置情報を共有できるかどうかを判断するには、context.System.device.supportedInterfacesオブジェクトにGeolocationフィールドがあるかどうかを確認します。Geolocationフィールドがない場合、ユーザーのデバイスは位置情報データを提供できません。Amazon Echoなどの固定デバイスがこれに該当します。そのような場合、位置情報を必要としないユーザーエクスペリエンスを提供する必要があります。たとえば、ユーザーのリアルタイム位置情報を受け取ることができないことを知らせるプロンプトを表示します。

var isGeoSupported = context.System.device.supportedInterfaces.Geolocation;
var geoObject = context.Geolocation;
if (isGeoSupported) {
	var ACCURACY_THRESHOLD = 100; // 100メートルの精度が必要
                if (geoObject && geoObject.coordinate && geoObject.coordinate.accuracyInMeters < ACCURACY_THRESHOLD ) {
                         console.log(geoObject);  // 精度が100メートル以内であれば、地理座標系オブジェクトを印刷
                }
}

次に、サンプルのペイロードを示します。coordinateオブジェクトには、latitudeInDegreeslongitudeInDegreesaccuracyInMetersが必須ですが、Alexaと共有するデバイスではaltitudeheadingspeedはオプションのオブジェクトです。そのため、これらのオプションフィールドがスキルで使用できない場合があります。それぞれのフィールドの詳細については、地理座標系インターフェースの詳細を参照してください。

     "Geolocation":{
        "locationServices": {
            "access": "ENABLED",
            "status": "RUNNING",
        },
        "timestamp": "2018-03-25T00:00:00Z+00:00",
        "coordinate": {
            "latitudeInDegrees": 38.2,
            "longitudeInDegrees": 28.3,
            "accuracyInMeters": 12.1
        },
        "altitude": {
            "altitudeInMeters": 120.1,
            "accuracyInMeters": 30.1
        },
        "heading": {
            "directionInDegrees": 180.0,
            "accuracyInDegrees": 5.0
        },
        "speed": {
            "speedInMetersPerSecond": 10.0,
            "accuracyInMetresPerSecond": 1.1
        }
      }
   }

ステップ3 – スキルをテストする

地理座標系を処理するスキルのロジックを記述したら、Alexaアプリなどのモバイルデバイスを使用してテストできます。ユーザーが発話するたびに、ユーザーの位置情報(有効な場合)がスキルに渡されます。たとえば、次のやり取りでは、ユーザーの位置情報がAlexaに2回送信されます。ユーザーが移動中の場合、各発話には異なるユーザー位置情報データが含まれることがあります。位置情報サービスは、位置情報データのリアルタイムストリーミングをサポートしていません。

次に、サンプルのテストダイアログを示します。

ユーザー: アレクサ、いちばん近くにある喫茶店に行きたいんだけど。
地理座標系テスト: 目黒区下目黒2008番地の喫茶店Aへの道順を伝えます。
ユーザー: アレクサ、近くに映画館はある?
最寄りの映画館は、品川区上大崎1100番地にあります。

地理座標系情報は、最終的には、位置情報サービスを使用してこのデータを取得するハードウェアデバイスから提供されます。 Alexaでは、このデータのソースを制御しません(GPSから来たものか、IP由来のものかなど)。つまり、Alexaは、スキルに送信されるユーザーの位置情報の粒度や精度を制御しません。ただし、スキルの目的を果たすだけの精度があるかどうかをスキルが判断できるように、Alexaを搭載したモバイル機器は、精度のレポート(メートル単位の精度、context.Geolocation.coordinates.accuracyInMeters)を提供する必要があります。

位置情報インターフェースのプロパティ

ペイロードには、少なくとも1つのlocationServicesオブジェクトまたはcoordinateオブジェクトが必要です。

パラメーター 説明 有効値 オプション
locationServices ユーザーデバイスで位置情報の共有が有効になっているかどうかを示します。 オブジェクト
locationServices.access 位置情報の共有アクセスが有効か無効かを示します。 列挙型文字列 以下のいずれかになります。 「ENABLED」または「DISABLED」 ✕(locationServicesがある場合)
locationServices.status locationServices.accessが「ENABLED」に設定され、locationServices.statusが「RUNNING」に設定されている場合、位置情報の共有アクセスが有効になり、実行されます。 列挙型文字列 以下のいずれかになります。 「RUNNING」または「STOPPED」 ✕(locationServicesがある場合)
timestamp デバイスでGPSデータが更新されたときのデバイス時間です 文字列
例:
2016-09-09T21:28:45+00:00
ISO 8601
(RFC 3339を推奨)
coordinate デバイスの座標を提供します オブジェクト ✕(locationServicesがない場合)
coordinate.latitudeInDegrees 赤道からの角度です ダブル [-90.0, 90.0] ✕(coordinateがある場合)
coordinate.longitudeInDegrees 本初子午線からの角度です ダブル [-180.0, 180] ✕(coordinateがある場合)
coordinate.accuracyInMeters 緯度および経度の不確かさ(メートル単位)です ダブル [0, MAX_INTEGER] ✕(coordinateがある場合)
altitude デバイスの標高を示します オブジェクト
altitude.altitudeInMeters GPS制限内の海抜距離(メートル単位)です ダブル [-6350, 18000]
altitude.accuracyInMeters 標高の不確かさ(メートル単位)です ダブル [0, MAX_INTEGER]
heading デバイスの向いている方位を示します オブジェクト
heading.directionInDegrees 真北からの角度です ダブル (0.0, 360.0]
heading.accuracyInDegrees 方向のオプションの精度パラメーターです ダブル [0, MAX_INTEGER]
speed デバイスの速度を示します オブジェクト
speed.speedInMetersPerSecond GPS制限内の速度(メートル/秒)です ダブル [0, 1900] ◯ 自動車を除く(契約が必要)
speed.accuracyInMetersPerSecond 速度のオプションの精度パラメーターです ダブル [0, MAX_INTEGER]

データ鮮度と精度を確認する

スキルでこのデータを使用する前に、位置情報データの鮮度と精度の両方を確認することが大切です。運転中など、ユーザーの場所が急激に変わることがあります。そのような場合、10分前のGPSデータでは精度が非常に低くなってしまいます。

鮮度をチェックするには、Geolocation.timestampとIntentRequestのtimestamp(request.timestamp)の差を確認します。差が小さいと、データの鮮度が高くなります。Geolocation.timestamp値は、ユーザーの位置情報がデバイス内部で測定された時刻です。request.timestamp値は、スキルが呼び出されたときとほぼ同時刻になります。

鮮度と精度のチェックを組み合わせることによって、位置情報データが使用可能かどうかを判断するロジックを作成できます。100メートルの精度と1分の鮮度のデータが必要な場合のサンプルコードを次に示します。

var isGeoSupported = context.System.device.supportedInterfaces.Geolocation;
var geoObject = context.Geolocation;
if (isGeoSupported) {
	var freshness = ( new Date(request.timestamp) - new Date(geoObject.timestamp) ) / 1000; // 鮮度(秒単位)
	var ACCURACY_THRESHOLD = 100; // 100メートルの精度が必要
                if ( geoObject && geoObject.coordinate && geoObject.coordinate.accuracyInMeters < ACCURACY_THRESHOLD && freshness < 60 ) {
                          //  ユーザーのコードはこちら
                }
}

スキルペイロードに地理座標データがない場合があります。これは、context.Geolocationがnullであるかどうかをテストすることで確認できます。開発者コンソールで位置情報サービスを有効にしていると、このデータが不足している場合は、context.Geolocationは次の3つの理由からnullになります。

  • ケース1: ユーザーのデバイスがAmazon Echoなどの固定デバイスであるか、位置情報をAlexaに送信するように設定されていません。この場合、有効なモバイルデバイスではないため、デバイスの座標はデフォルトで使用できません。

  • ケース2: ユーザーが、スキルと位置情報を共有するよう設定していません。この場合、AskForPermissionsConsentカードを使用してユーザーに権限を要求して、この問題を解決することもできます。

  • ケース3: ユーザーのハードウェアで位置情報の共有が無効になっているか、ユーザーがAlexaと位置情報と共有するよう設定していません。たとえば、ユーザーのデバイス(携帯電話など)の位置情報サービスが無効になっている可能性があります。この場合、Alexaとの位置情報共有を有効にするようにユーザーに依頼することもできます。

また、同時に複数のケースが該当することがあります。たとえば、ユーザーが位置情報共有の権限をスキルに付与しておらず、デバイスの位置情報共有も無効になっていることも考えられます。

ケース1に該当するかどうかを確認するには、context.System.device.supportedInterfaces.Geolocationフィールドをチェックし、trueに設定されているかどうかを確認します(前述のコードサンプルを参照)。ケース1に該当しない場合、ケース2のテストに進みます。

ケース2の場合、位置情報を取得するための権限をAlexaやスキルに提供するようユーザーに依頼します。ユーザーに依頼するには、AskForPermissionsConsentカードを応答として返します。このカードは、ユーザーのAlexaアプリに手順カードを送信します。このカードには、Alexaまたはスキルの位置情報の共有を有効にする手順が記載されています。

位置情報の権限をリクエストするためのカード
位置情報の権限をリクエストするためのカード

このサンプルコードは、FindMyWayHomeという仮想スキルにAskForPermissionsConsentカードを生成する応答を返します。

var context = this.event.context;
var isGeolocationSupported = context.System.device.supportedInterfaces.Geolocation;
if ( isGeolocationSupported ) {   //  デバイスが位置情報ベースの機能をサポートするかどうか 
	var geoObject = context.Geolocation;
	if ( ! geoObject || ! geoObject.coordinate ) {
return {  // 応答
"version": "1.0",
"response": {
	"outputSpeech": {
		"type": "PlainText",
		"text": "FindMyWayHomeは、お客様の位置情報を使用します。位置情報の共有を有効にするには、Alexaアプリに移動し、指示に従って操作してください。"
	},
	"card": {
		"type": "AskForPermissionsConsent",
		"permissions": [ "alexa::devices:all:geolocation:read"]
	}
}
};
	} else {
		// 位置情報データを使用
	}
}

応答には、cardoutputSpeechの2つのセクションがあります。カードのタイプはAskForPermissionsConsentであり、ユーザーに送信する手順カードの種類をAlexaに指示します。このカードでは、権限リストで権限の範囲のリストを指定できます。位置情報の場合、スキルは権限のリストの一部としてalexa::devices:all:geolocation:readを渡す必要があります。

この手順カードを送信する以外に、スキルでは、Alexaからユーザーに伝えるメッセージを指定する必要があります。たとえば、次のようなメッセージになります。「FindMyWayHomeは、お客様の位置情報を使用します。位置情報の共有を有効にするには、Alexaアプリに移動し、指示に従って操作してください。」応答のoutputSpeechセクションで音声を指定します。口頭による指示がなければ、ユーザーはスキルにエラーが発生していると思うかもしれません。

この応答が返されると、次の一連のイベントが発生します。

1.ユーザーに次のメッセージが読み上げられます。「FindMyWayHomeは、お客様の位置情報を使用します。位置情報の共有を有効にするには、Alexaアプリに移動し、指示に従って操作してください。」

2.位置情報の共有を行うための権限で不足しているものがないか、Alexaが個別に確認します。

3.位置情報の共有を有効にするための手順が記載されたホームカードがAlexaから送信され、セッションが終了します。

不足している権限によっては、AlexaからユーザーのAlexaアプリに別の手順カードが送信されます。スキルにはユーザーの位置情報を使用する権限があるがAlexaにはない場合と、スキルにユーザーの位置情報を使用する権限がない場合とでは、カードの内容が異なります。

位置情報の権限をリクエストするためのカード
位置情報の権限をリクエストするためのカード

ただし、Alexaにもスキルにもユーザーの権限がない場合は、次のような手順カードが作成されます。

スキルによってリクエストされた位置情報の権限
スキルによってリクエストされた位置情報の権限

4.ユーザーがカードで指示されたアクションを実行し、スキルを再度使用すると、context.Geolocationオブジェクトに有効なcoordinatesオブジェクトが含まれます。

Amazonがデバイスの
位置情報を受け取れるか
スキルが位置情報を
Amazonから受け取れるか
スキルによる位置情報へのアクセス 開発者のアクション
TRUE TRUE なし
TRUE FALSE 位置情報の権限をリクエストするための権限カードを表示させます
FALSE TRUE ユーザーにAlexaとの位置情報の共有を有効にするように依頼します
FALSE FALSE 位置情報の権限をリクエストするための権限カードを表示させます

必要となる特定の権限を検出する

すでに述べたように、スキルとAlexaのそれぞれにデバイスの位置情報へのアクセス権限があるかどうかを確認できます。スキルでこの情報を使用すれば、AskForPermissionsConsentカードが返されたときの読み上げをさらにカスタマイズできます。

スキルに位置情報を読み取る権限があるかどうかを確認するには、context.System.userの値を確認します。このオブジェクトには、現在のユーザーに関するメタデータが含まれます。たとえば、ユーザーがスキルに付与した権限のセットを追跡するpermissions.scopesオブジェクトなどです。個々のスコープの値を調べることができます。たとえば、スキルに権限がある場合、scopes['alexa::devices:all:geolocation:read'].statusは「GRANTED」となります。

したがって、スキルに権限が不足している場合にのみ手順カードを送信するには、次のようなコードを使用します。

if ( isGeolocationSupported ) {   //  デバイスが位置情報ベースの機能をサポートするかどうか
	var geoObject = context.Geolocation;
	if ( ! geoObject || ! geoObject.coordinate ) {
var skillPermissionGranted = context.System.user.permissions.scopes['alexa::devices:all:geolocation:read'].status === "GRANTED";
if ( !skillPermissionGranted) {
			// AskForPermissionsConsentカードをここで返す
	

スキルに権限があっても地理座標系データがリクエストで利用できない場合は、スキルからユーザーに再度プロンプトを表示する必要があります。

モバイルデバイスで位置情報の共有が無効になっているかどうかを検出する

ケース1とケース2に該当しない場合は、ケース3を検討します。ケース3は、Alexaやスキルには権限の問題が発生していないが、スキルがデバイスの位置情報を取得できないケースです。この場合、ユーザーのデバイスで位置情報の共有が有効になっているか、または、その他の技術的な問題が発生していないかどうかを確認してください。たとえば、ユーザーがトンネル内を運転している場合は、GPSが受信できなくなることがあります。

デバイスの位置情報サービスが有効になっているかどうかを調べるには、context.GeolocationlocationServicesオブジェクトを調べます。このオブジェクトが存在する場合、このオブジェクトは、デバイスが位置情報を共有しているかどうかを示すことを目的としています。ただし、ユーザーのデバイスが提供していない場合は、locationServicesオブジェクトが使用できないことがあります。

context.Geolocation.locationServices.accessが「ENABLED」、context.Geolocation.locationServices.statusが「RUNNING」になっている場合、デバイスは位置情報を共有しています。それ以外の状態の場合は、デバイスには位置情報の共有が設定されていません。

位置情報の共有が有効になっているが、スキルがデバイスの位置情報を受信できない場合は、ユーザーに状況を知らせる必要があります。その場合は、次のようなメッセージを使用します。「FindMyWayHomeが、お客様の位置情報にアクセスできません。しばらく待ってから、後でもう一度試してみてください。」

ただし、位置情報の共有が無効になっている場合は、位置情報の共有を有効にするようにスキルからユーザーにリクエストすることができます。その場合は、次のようなメッセージを使用します。「FindMyWayHomeが、お客様の位置情報にアクセスできません。デバイスの設定に移動し、位置情報の共有を有効にして、もう一度お試しください。」