目次
はじめに
AlexaのAPLドキュメントで、独自のレイアウトを作成し、パッケージ化することで複数のAPLドキュメントで再利用する方法について解説します。
APLドキュメントの基本構成やレイアウトについては、下記の記事を参照してください。
AlexaスキルのAPLドキュメントを作成する (以下「前記事」として参照)
APLドキュメント
ここでは前記事で作成した、下記の表示を行うAPLドキュメントを対象にパッケージ化を行い、カスタムパッケージとして再利用できるようにします。
まず元となるAPLドキュメントを再掲します。TextMessageというレイアウトが定義されており、そのレイアウトがmainTemplateで2回使用されています。これは前記事のバージョン8で作成されたものです。(ただしテーマはダークに戻されています)
APLドキュメント
{
"type": "APL",
"version": "1.6",
"license": "",
"theme": "dark",
"import": [
{
"name": "alexa-styles",
"version": "1.2.0"
}
],
"resources": [],
"styles": {
"titleStyle": {
"values": [
{
"fontSize": "@fontSize2XSmall",
"color": "red"
}
]
},
"messageStyle": {
"values": [
{
"fontSize": "@fontSize2XLarge",
"color": "${viewport.theme == 'dark' ? 'yellow' : 'blue'}"
}
]
}
},
"layouts": {
"TextMessage": {
"parameters": [
{
"name": "title",
"type": "string"
},
{
"name": "message",
"type": "string"
}
],
"items": [
{
"type": "Container",
"items": [
{
"type": "Text",
"text": "${title}",
"style": "titleStyle"
},
{
"type": "Text",
"text": "${message}",
"style": "messageStyle"
}
]
}
]
}
},
"mainTemplate": {
"parameters": [
"payload"
],
"items": [
{
"type": "Container",
"items": [
{
"type": "TextMessage",
"title": "${payload.data.title1}",
"message": "${payload.data.message1}"
},
{
"type": "TextMessage",
"title": "${payload.data.title2}",
"message": "${payload.data.message2}"
}
]
}
]
}
}
対応するデータソースを下記に示します。
データソース
{
"data": {
"title1": "タイトル1",
"message1": "メッセージ1",
"title2": "タイトル2",
"message2": "メッセージ2"
}
}
パッケージ化
前記事では、タイトルとメッセージを表示するコンポーネントを、MessageTextレイアウトとして部品化しました。今回はこれを更にパッケージとして別ファイルに分離して、他のAPLドキュメントで再利用できるようにします。
パッケージの構成はAPLドキュメントのうち、mainTemplateを除いたものとなります。つまり前掲のAPLドキュメントから、下記のようにmainTemplateを切り離せば良いことになります。(実はmainTemplateを残したままでもパッケージとして扱えます)
パッケージ
{
"type": "APL",
"version": "1.6",
"license": "",
"theme": "light",
"import": [
{
"name": "alexa-styles",
"version": "1.2.0"
}
],
"resources": [],
"styles": {
"titleStyle": {
"values": [
{
"fontSize": "@fontSize2XSmall",
"color": "red"
}
]
},
"messageStyle": {
"values": [
{
"fontSize": "@fontSize2XLarge",
"color": "${viewport.theme == 'dark' ? 'yellow' : 'blue'}"
}
]
}
},
"layouts": {
"TextMessage": {
"parameters": [
{
"name": "title",
"type": "string"
},
{
"name": "message",
"type": "string"
}
],
"items": [
{
"type": "Container",
"items": [
{
"type": "Text",
"text": "${title}",
"style": "titleStyle"
},
{
"type": "Text",
"text": "${message}",
"style": "messageStyle"
}
]
}
]
}
}
}
ネット上の解説記事を見ると、versionにこのパッケージのバージョンを記載する、としているものもありました。しかしAlexaの技術ドキュメントの説明を読む限りでは、これは対応するAPLのバージョンであるようです。
カスタムパッケージのホスティング
カスタムパッケージは、ネット上からAlexaデバイスにダウンロードされる必要があります。このためカスタムパッケージのファイルをどこかのサーバーでホスティングする必要があります。ここでは下記の3つの方法について説明します。
- 自前のWebサーバー
- S3ストレージ
- GitHub
参考: 視覚要素を簡単に作成する
「2.独自のAPLパッケージをホストする」にパッケージ化とホスティングについての説明があります。
自前のWebサーバーにホスティング
カスタムパッケージのファイル (本例ではsample-template.json) を自前のWebサーバーに配置します。ただしCORS (Cross Origin Resource Sharing) をサポートしている必要があります。
筆者の場合は、カスタムパッケージを配置したWebサーバーのディレクトリに.htaccess
ファイルを置いて、下記を記述しています。
Header set Access-Control-Allow-Origin "*"
CORSをサポートできるかどうかはWebサーバーの設定によります。ホスティングサービスを利用している場合は、そのサービスの仕様にも依存します。
対象のOriginとして、”*”で全てのホストを許可していますが、実際には*.amazon.com
を許可していれば良いようです。(特定のドメインに対してのみ、上記のヘッダを返す方法は、ネット上に紹介がありますが、筆者は力不足でうまく設定できませんでした)
Amazon S3ストレージにホスティング
AWSのAmazon S3ストレージにファイルを格納し、HTTPでアクセスすることができます。これを利用してカスタムパッケージをホスティングできます。ただしこの場合もCORSのサポートが必要になります。設定方法については下記に記述されています。
リソースのCross-Origin Resource Sharing(CORS)を設定する
参考:
Alexa-Hostedスキルから使えるS3ストレージは、CORSの許可が設定できないため、残念ながらこの用途には使えません。AWS上で別途プロビジョニングする必要があります。
GitHubでのホスティング
参考記事 (視覚要素を簡単に作成する) では、GitHubにカスタムパッケージのファイルを入れるとCORS対応でアクセスできると書かれています。調べて見るとGitHubのパブリックレポジトリにファイルを入れて、rawモードで開くと、CORSのヘッダがついて来ます。開発中に一時的に使うには良いかも知れません。
APLドキュメントへの組み込み
カスタマパッケージをAPLドキュメントで利用するには、APLドキュメントのimportセクションでカスタムパッケージをインポートします。
"import": [
{
"name": "sample-template",
"version": "1.0.0",
"source": "https://<domain>/<path-to-template>/sample-template.json"
}
]
name
[a-zA-Z][a-zA-Z0-9-]*の形式に従っていれば良い
version
セマンティックバージョン規則に従っていれば良い
カスタムパッケージ側にバージョンを持たないのでチェックはされない
source
カスタムパッケージのURL
Alexaデバイスでは、nameとversionの組み合わせで、パッケージをキャッシュをします。このため開発中にカスタムパッケージを更新したときは、versionを更新することでキャッシュを強制的にクリアできます。
APLドキュメントの全体定義を下記に示します。
APLドキュメント
{
"type": "APL",
"version": "1.6",
"license": "",
"theme": "dark",
"import": [
{
"name": "sample-template",
"version": "1.0.0",
"source": "https://pvision.jp/alexa/apl/sample-template.json"
}
],
"resources": [],
"styles": {},
"layouts": {},
"mainTemplate": {
"parameters": [
"payload"
],
"items": [
{
"type": "Container",
"items": [
{
"type": "TextMessage",
"title": "${payload.data.title1}",
"message": "${payload.data.message1}"
},
{
"type": "TextMessage",
"title": "${payload.data.title2}",
"message": "${payload.data.message2}"
}
]
}
]
}
}
オリジナルのAPLドキュメントと比べると、随分スッキリしたことが判ります。再利用性の他に、ドキュメントを整理する効果もありそうです。(セットアップが大変ですが …)
おわりに
APLのカスタムパッケージの作成方法について解説しました。この例のレイアウト自体は、再利用するまでもありません (あくまで説明用ということで …)。 しかしスキルの中で同じようなパターンが出てくることはよくあります。このパッケージ化の方法が使えるシーンは多そうです。
またデザインが得意な方は、カッコいいテンプレートを作って公開する、なんてことができると楽しそうです。
変更履歴
日付 | 内容 |
2021/07/09 | 初版公開 |