ちょっと話題の記事

[Alexa] 遂にでた! Alexa Skill Kit のCLIでデプロイまでやってみた

2017.09.10

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

1 はじめに

先日(日本時間で9月6日)、新しく次の3つの機能追加が発表され、スキルをプログラムで管理したり、テストすることが、できるようになったと言うことです。

  • Alexa Skill Management API(SMAPI)スキルの管理
  • Alexa Skill Kit Command-line Interface(ASK-CLI)コマンドラインツール
  • Alexa Skill Kit Event スキルイベント


Announcing Alexa Skill Management API, Alexa Skills Kit Command-line Interface, and Events in the Alexa Skills Kit

今回は、とりあえず、Alexa Skill Kit Command-line Interface(以下、ASK-CLI)を使って、新しくSkillを生成してデプロイする所まで試してみました。

2 ASK-CLI

ASK-CLIは、Alexaスキルと接続されたAWS Lambda(以下、Lambda)の作成、読み込み、更新、そして、スキルのテストや、提出、撤回を行うことができます。

ASK-CLIでは、AWS CILと同様に、認証情報等はプロファイルで管理され、プロファイルを切り替えることで、簡単に作業環境を切り替えることができます。

ASK-CLIの各プロファイルで管理されているのは、次の3つです。

  • AWS-CLIのプロファイル名
  • Amazon開発者コンソールのアカウント(Login with Amazonのトークン)
  • Amazon開発者アカウントで紐づくベンダー(複数のベンダーに紐づいている場合、それを区別するため)

3 インストールとプロファイル作成

インストールは、npmで行うことができます。

$ npm install -g ask-cli
$ ask --version
1.0.0-beta.0


参考:https://www.npmjs.com/package/ask-cli

続いて、initコマンドで、プロファイルを作成します。

$ ask init
? Please type in your new profile name:
 furuya02    <=プロファイル名を指定する
-------------------- Initialize CLI --------------------
Setting up ask profile: [furuya02]
? Please choose one from the following AWS profiles for skill's Lambda function deployment.
 default  <= AWS-CLIで設定されているプロファイル名を指定する
Switch to 'Login with Amazon' page...
Tokens fetched and recorded in ask-cli config.
Vendor ID set as MKXXXXXXXXXG3Y

Profile [furuya02] initialized successfully.

途中で、Amazon開発者コンソールへアクセスするためのLogin with Amazonの認可のためのウインドウが表示されます。 002

そして、認可した場合、Login with AmazonにASK-CLIが追加されていることを確認できます。

003

プロファイルは、~/.ask/cli_configに作成されます。

{
  "profiles": {
    "furuya02": {
      "aws_profile": "default",
      "token": {
        "access_token": "Atza|XXXXXXXXXX",
        "refresh_token": "Atzr|XXXXXXXXXX",
        "token_type": "bearer",
        "expires_in": 3600,
        "expires_at": "2017-09-10T00:24:22.390Z"
      },
      "vendor_id": "MKXXXXXXXXG3Y"
    }
  }
}

プロファイルは、initコマンドで複数設定でき、-lで一覧されます。

$ ask init -l
  Profile              Associated AWS Profile
  [furuya02]                "default"

4 スキルの作成

newコマンドで、新規にスキルを作成できます。

$ ask new -p furuya02
? Please type in your new skill name:
 hello-world
New project for Alexa skill created.

作成されたスキルは、次のようになっています。

└── hello-world
    ├── .ask
    │   └── config
    ├── lambda
    │   └── custom
    │       ├── index.js
    │       ├── node_modules 
    │       ├── package-lock.json
    │       └── package.json
    ├── models
    │   └── en-US.json
    └── skill.json

/lambda/custom/index.jsが、alexa-adkを利用したスキルの本体です。alexa-sdkは、既にnode_modulesにインストールされています。

'use strict';
var Alexa = require("alexa-sdk");

exports.handler = function(event, context) {
    var alexa = Alexa.handler(event, context);
    alexa.registerHandlers(handlers);
    alexa.execute();
};

var handlers = {
    'LaunchRequest': function () {
        this.emit('SayHello');
    },
    'HelloWorldIntent': function () {
        this.emit('SayHello');
    },

// ・・・略・・・

    'Unhandled' : function() {
        this.response.speak("Sorry, I didn't get that. You can try: 'alexa, hello world'" +
            " or 'alexa, ask hello world my name is awesome Aaron'");
    }
};

/models/en-US.jsonは、Interaction Modelの設定です。Skill Builder(BETA)Codeで表示したものと同じようです。

{
    "interactionModel":{
        "languageModel":{
            "invocationName":"hello world",
            "types":[],
            "intents":[
// ・・・略・・・

                {
                  "name": "AMAZON.StopIntent",
                  "samples": []
                },
                {
                    "name":"HelloWorldIntent",
                    "slots":[

                    ],
                    "samples":[
                        "hello",
                        "say hello",
                        "say hello world"
                    ]
                }
// ・・・略・・・
            ]
        }
    }
}

skill.jsonには、Publishing Informationの内容などが記載されています。

{
  "skillManifest": {
    "publishingInformation": {
      "locales": {
        "en-US": {
          "summary": "Sample Short Description",
          "examplePhrases": [
            "Alexa open hello world",
            "Alexa tell hello world I am Jeff",
            "Alexa tell hello world my name is Peter"
          ],
          "name": "hello-world",
          "description": "Sample Full Description"
        }
      },
      "isAvailableWorldwide": true,
      "testingInstructions": "Sample Testing Instructions.",
      "category": "EDUCATION_AND_REFERENCE",
      "distributionCountries": []
    },
    "apis": {
      "custom": {
        "endpoint": {
          "sourceDir": "lambda/custom"
        }
      }
    },
    "manifestVersion": "1.0"
  }
}

/.ask/configは、スキルのApplication IDや、Lambdaのファンクション名を記録したファイルです。新規作成した時点では、skill_idが空ですが、deployが成功すると、Application Idが保存されます。

{
  "deploy_settings": {
    "furuya02": {
      "skill_id": "",
      "was_cloned": false,
      "merge": {
        "skillManifest": {
          "apis": {
            "custom": {
              "endpoint": {
                "uri": "ask-custom-hello-world-furuya02"
              }
            }
          }
        }
      }
    }
  }
}

5 デプロイ

deployで、全て一気にデプロイされます。

$ cd hello-world/
$ ask deploy -p furuya02
-------------------- Create Skill Project --------------------
Profile for the deployment: [furuya02]
Skill Id: amzn1.ask.skill.ecc95f78-f6e0-4c61-a9be-34a68e5cb0b1
Skill deployment finished.
Model deployment finished.
Lambda deployment finished.

それでは、デプロイされた状況を順に見てみます。

(1) Lambda

AWS-CLIのプロファイルに従って、対象リージョンにdeployされています。

004

Triggerも設定されています。

006

(2) AMI

Lambda用のRoleも、AWSLambdaBasicExecutionRoleの権限で生成されてます。

007

(3) スキル

Amazon開発者コンソールを開くと、スキルもちゃんと作成されています。

009

Skill Informationでは、Nameには、作成時に指定したスキル名が入りますが、Invocation Nameは、hello worldに固定されているようです。

010

Interaction Modelは、先ほどの/models/en-US.jsonが設定されています。

011

Configrationでは、Endpointがしっかりと設定されていました。

012

(4) テスト

ここまで、全部できているので、テストタブで試してみると、ちゃんとLambdaが応答していることを確認できました。

013 014

6 Application ID

ここまでで、雛形としては完璧ですが、強いて言うと、生成されたコードには、Application Idがセットされていないので、とりあえず追加しておいた方がいいでしょう。

015

const ALEXA_APPLICATION_ID = 'amzn1.ask.skill.ecc95f78-f6e0-4c61-a9be-34a68e5cb0b1';

exports.handler = function(event, context) {
    var alexa = Alexa.handler(event, context);
    alexa.appId = ALEXA_APPLICATION_ID;
    alexa.registerHandlers(handlers);
    alexa.execute();
};

7 最後に

今回、新規作成からDeployまでやってみましたが、非常に素晴らしいです。

比較的煩雑な作業であったAmazon開発者コンソールでの作業と、Lambdaとの紐付けなどが簡単に終わってしまうので、初めてスキルを作成するという方でも、導入は非常にハードルの低いものになるのではないでしょうか。

個人的には、Interraction Model も、Publishing Informationも、手元で一元管理できる所が、気に入っちゃいました。

8 追加(小ネタ)

profile (-p) の指定をしないで、ASK-CLIを使用すると、[Error]: Cannot resolve profile [default]というエラーになります。

$ ask new
? Please type in your new skill name:
 test
[Error]: Cannot resolve profile [default]

デフォルトプロファイルの指定は環境変数ASK_DEFAULT_PROFILEで行うことが可能です。

$ export ASK_DEFAULT_PROFILE=furuya02
$ env | grep ASK
ASK_DEFAULT_PROFILE=furuya02
$ ask new
? Please type in your new skill name:
 test
New project for Alexa skill created.

8 参考リンク


Announcing Alexa Skill Management API, Alexa Skills Kit Command-line Interface, and Events in the Alexa Skills Kit
ASK Command-Line Interface とスキル管理API
ASK Command-Line Interface Quick Start