APLパッケージでレイアウト、グラフィックスなどのリソースをホストする

APLパッケージでレイアウト、グラフィックスなどのリソースをホストする

再利用可能なレイアウト、グラフィックスなどのリソースのセットをAlexa Presentation Language(APL)パッケージとして定義します。インターネット上にこのパッケージをホストすると、ほかのAPLドキュメントでもこのリソースを使用できます。パッケージにすることで、コードを複製することなく複数のAPLドキュメントで共通の項目を共有したり、スキル応答のコードを単純化してサイズを小さくしたりできます。

パッケージをAPLドキュメントとして定義する

パッケージは、APLドキュメントと同じJSON構造を使用します。パッケージは、mainTemplateプロパティを省略できます。存在する場合、mainTemplateプロパティは無視されます。最上位のプロパティにパッケージの項目を定義します。

  • commands
  • extensions
  • graphics
  • layouts
  • resources
  • styles

たとえば、layoutsプロパティにレイアウトのセットを定義し、それらのレイアウトをほかのAPLドキュメントで使用できます。

以下は、CircleWithTextと呼ばれるレイアウトを定義するパッケージの例です。

{
  "type": "APL",
  "version": "2022.1",
  "import": [
    {
      "name": "alexa-styles",
      "version": "1.4.0"
    }
  ],
  "layouts": {
    "CircleWithText": {
      "parameters": [
        {
          "name": "backgroundColor",
          "default": "green"
        },
        {
          "name": "textToDisplay",
          "default": "表示するテキストです。"
        }
      ],
      "items": [
        {
          "type": "Frame",
          "borderRadius": "@shapeCircle",
          "width": "300dp",
          "height": "300dp",
          "backgroundColor": "${backgroundColor}",
          "item": {
            "type": "Text",
            "width": "100%",
            "height": "100%",
            "padding": "@spacingSmall",
            "text": "${textToDisplay}",
            "textAlign": "center",
            "textAlignVertical": "center"
          }
        }
      ]
    }
  }
}

ほかのパッケージをインポートする

パッケージは、ほかのパッケージをインポートできます。たとえば、alexa-layoutsパッケージで提供されるレスポンシブ対応コンポーネントを使用したカスタムレイアウトを作成できます。標準のAPLドキュメントでパッケージを使うときと同じ方法で、インポートをimport配列に追加します。

{
  "import": [
    {
      "name": "alexa-layouts",
      "version": "1.5.0"
    }
  ]
}

前に示したCircleWithTextの例は、alexa-stylesパッケージをインポートして、スペースと境界線の丸みリソースを使用しています。

特定の項目を書き出す

exportプロパティを使って、パッケージをインポートしたときにほかのドキュメントで使用する項目を定義します。このプロパティは、一つのレイアウトを定義し、その中でコードをモジュール化するために複数の「内部用」レイアウトを使用していても、最後の「公開用」バージョンだけを使用するときなどに役立ちます。

オーサリングツールなどのツールは、exportプロパティを使ってドキュメントにエラーがないかどうかをチェックし、書き出した項目を利用可能として表示します。ただし、exportプロパティは情報提供用です。パッケージをインポートするAPLドキュメントも、パッケージに定義されたすべてのリソースにアクセスできます。exportに含まれていなくても、アクセス可能です。

以下の例は、2つのレイアウト(レイアウトのitemsは簡潔化のために省略されています)を持つパッケージを示しています。

  • CircleWithTextレイアウトは、指定したテキストを円内に表示します。
  • ListOfCirclesは文字列の配列をとり、CircleWithTextオブジェクトのリストを表示します。
  • この例は、具体的にはListOfCirclesレイアウトを書き出して、ListOfCirclesが使用するレイアウトであることを表しています。

オーサリングツールでドキュメントを作成する場合、CircleWithTextを直接使用すると、使用を想定されていないレイアウトとしてエラーが表示されます。ただし、APLではレイアウトがレンダリングされます。

{
  "type": "APL",
  "version": "2022.1",
  "import": [
    {
      "name": "alexa-styles",
      "version": "1.4.0"
    }
  ],
  "export": {
    "layouts": [
      {
        "name": "ListOfCircles",
        "description": "円のリストです。テキストと背景色を指定します。"
      }
    ]
  },
  "layouts": {
    "ListOfCircles": {
      "parameters": [
        {
          "name": "textItems",
          "type": "array"
        },
        {
          "name": "defaultColor",
          "type": "string",
          "default": "purple"
        }
      ],
      "items": []
    },
    "CircleWithText": {
      "parameters": [
        {
          "name": "backgroundColor",
          "default": "green"
        },
        {
          "name": "textToDisplay",
          "default": "表示するテキストです。"
        }
      ],
      "items": []
    }
  }
}

パッケージをホストする

ほかのAPLドキュメントでパッケージを使用するには、インターネット上でパブリックにJSONファイルをホストする必要があります。アマゾンウェブサービス(AWS)S3などのサービスを使って、パッケージをホストできます。ホストされるパッケージは、以下の要件を満たす必要があります。

  • JSONファイルへのリンクが完全にパブリックであること。
  • ホストのCross-Origin Resource Sharing(CORS)が*.amazon.comを許可していること。
  • JSONファイルに有効期限がないこと。

Amazon S3に保存されているオブジェクトをパブリックにする

Amazon S3のパッケージへのリンクをパブリックにするには、バケットポリシーを追加してアクセスを付与します。詳細については、ウェブサイトアクセスのアクセス許可の設定を参照してください。

または、AWS CloudFrontを使ってパッケージをアクセス可能にすることができます。ただし、ダイレクトS3 URLへのアクセスは制限します。以下のAWSリソースを参照してください。

S3 CORSポリシーを設定する

S3バケット上の以下のCORSポリシーにより、Alexaデバイスからパッケージにアクセスできるようになります。

[
    {
        "AllowedHeaders": [],
        "AllowedMethods": [
            "GET"
        ],
        "AllowedOrigins": [
            "*.amazon.com"
        ],
        "ExposeHeaders": []
    }
]

S3バケットでCORSを設定する方法について詳しくは、Cross−Origin Resource Sharing(CORS)の使用を参照してください。

パッケージをドキュメントにインポートする

外部パッケージを使用するには、パッケージをインポートします。sourceプロパティにパッケージのパブリックURLを指定します。versionnameには、パッケージに合った文字列を設定します。これらのプロパティは必須ですが、パッケージの実際のコンテンツと一致する必要はありません。便宜上、一貫した命名規則を使用してください。たとえば、JSONファイル名をパッケージ名として使用します。

{
  "import": [
    {
      "name": "circle-list",
      "version": "1.0",
      "source": "https://d111111abcdef8.cloudfront.net/circle-list.json"
    }
  ]
}

複数のパッケージをインポートできます。たとえば、ドキュメントがレスポンシブ対応コンポーネントだけでなくカスタムパッケージのレイアウトも使用している場合、独自のパッケージとalexa-layoutsの両方をインポートします。

パッケージの例

以下は、Lottieからインポートしたグラフィックを定義する外部パッケージの例です。

以下は、このパッケージをインポートしてAPLドキュメント内でグラフィックを使用する方法の例です。この例で示したCloudFront URLは架空のものです。

{
  "type": "APL",
  "version": "2022.1",
  "import": [
    {
      "name": "my-lottie-graphics",
      "version": "1.0",
      "source": "https://d111111abcdef8.cloudfront.net/my-lottie-graphics.json"
    }
  ],
  "mainTemplate": {
    "parameters": [
      "payload"
    ],
    "items": {
      "type": "VectorGraphic",
      "source": "blockTowerAnimation",
      "width": "100%",
      "height": "100%",
      "scale": "best-fit",
      "align": "center",
      "frame": "${(elapsedTime*0.06)%360}"
    }
  }
}

外部パッケージのトラブルシューティング

問題: 403 Error trying to fetch package

現象

パッケージで指定されたリソースは、APLドキュメントでアクセス可能ではありません。オーサリングツールは、「Request failed with status code 403」エラーを報告します。

解決方法

このエラーは通常、パッケージURLへのリンクがパブリックアクセス可能でないことを示します。ブラウザでリンクをテストし、JSONファイルのコンテンツを表示できることを確認してください。

ファイルをパブリックアクセス可能にする手順は、パッケージをホストしている方法によって異なります。Amazon S3の場合、CloudFrontを使ってリソースへのアクセスを提供することを検討してください。以下は参考資料です。

問題: リソースが見つからない

現象

パッケージはパブリックアクセス可能ですが、パッケージで指定されたリソースはAPLドキュメントでアクセス可能ではありません。たとえば、オーサリングツールは「Unable to find layout <layoutName>」と報告します。

解決方法

アップロードしたパッケージが有効なAPLドキュメントであることを確認してください。APLドキュメントがファイルの最上位にあり、ほかのプロパティ内に入っていないようにします。オーサリングツールの書き出し機能では、documentdatasourcessourcesのプロパティを使って、1つのJSONファイルにドキュメント、データソース、ソースを保存します。この形式は、APLドキュメントとして有効ではありません。

たとえば、書き出したAPLドキュメントは最初、以下のようになります。

{
  "document": {
    "type": "APL",
    "version": "1.8",
    "settings": {},
    "theme": "dark",
    "import": [],
    "resources": [],
    "styles": {},
    "onMount": [],
    "graphics": {},
    "commands": {},
    "layouts": {
      "ListOfCircles": {},
      "CircleWithText": {}
    },
    "mainTemplate": {
      "parameters": [
        "payload"
      ],
      "items": []
    }
  },
  "datasources": {},
  "sources": {}
}

これを有効なパッケージにするには、documentプロパティに割り当てられたオブジェクトを最上位に移動し、datasourcessourcesのプロパティを削除します。

{
  "type": "APL",
  "version": "1.8",
  "settings": {},
  "theme": "dark",
  "import": [],
  "resources": [],
  "styles": {},
  "onMount": [],
  "graphics": {},
  "commands": {},
  "layouts": {
    "ListOfCircles": {},
    "CircleWithText": {}
  },
  "mainTemplate": {
    "parameters": [
      "payload"
    ],
    "items": []
  }
}

解決方法

Cross-Origin Resource Sharing(CORS)を*.amazon.comを許可するように設定したことを確認します。

Amazon S3とAmazon CloudFrontを使用している場合、CORSの設定に関する情報を以下のリンクで参照してください。