Alexaスキルの対話部分設計と設定

# はじめに
この投稿はAmazonEchoのスキルを作成して申請するまでの基本的な方法の内、AlexaSkillKitを使用してスキルを構成する部分のものです。

**#2018/5/上旬頃の情報 #2018/5/20深夜に追記**

- 対話部分(Alexa Skills Kit)　←　ここ
- 実処理部分(AWS Lambda)　（まだ未記載です）
- テスト　（まだ未記載です）
- 申請　（まだ未記載です）
- 却下からの修正　（まだ未記載です）

# こんな方向けです

- これからAlexaのスキルを作成しようと思っている方
- GoogleHomeアプリを作成して、次にAlexaスキルを作ろうと思っている方
- 作ったことあるんだけど・・・・あれ？どうやって設定するんだっけ？と思い出したい方

# 環境
ブラウザを使用して設定するタイプと、ローカルで設定してコマンドラインツールを使用してデプロイする方法がありますが、ここではブラウザベースを前提として記載します。

ブラウザは次のどちらかを使用してください。

- Chrome
- FireFox

コマンドラインツールはこちら
[Alexaスキル管理APIについて](https://developer.amazon.com/ja/docs/smapi/ask-cli-intro.html)

# アカウントの準備
https://developer.amazon.com/ja/
こちらのサイトから右上の「サインイン」をクリックして開発者アカウントを作成するのですが・・・

(現時点でも同じかは分からないのですが)
Alexa Blogにも記載されていますが、実はこの最初の一歩に躓きポイントがあります。
https://developer.amazon.com/ja/blogs/alexa/post/9f852a38-3a44-48bd-b78f-22050269d7c7/hamaridokoro

気をつけるポイントは２点です。

- 日本のAmazonですでに使用しているアカウント(Eメールアドレス)を使用して「ログイン」する
- 何らかの事情で既存アカウントを使用しない場合は(今まで日本Amazonに接続したことのないEメールアドレスで**新たにアカウントを作成したい**場合は)、一度日本Amazonにアカウントを作成してから、AmazonDeveloperのサイトに「ログイン」する

日本向けにスキルを作成する場合は**日本Amazonのアカウント**である必要があるのですが、少し見えにくく。この開発者サイトからアカウントを作成するとUSのAmazonアカウントが作成されてしまって困った事態に陥ります。

アカウント作成時には充分気をつけて。もしアカウント作成後にテストの段階まで進んで「あれ？」となった場合は上記のブログを参考にしてアカウントの調整を行ってみましょう。

## アカウントの作成
日本のAmazonですでに使用しているEメールアドレスを使用する例です。

Amazonで使用しているEメールアドレスをパスワードを入力して「ログイン」ボタンを押すとこんな画面が出ますので、「Send code」を押して送られてくるメールに記載されたコードを画面に入力すればOKです。
<img width="453" alt="ask-login1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/ccccce24-7950-e5d3-783f-044f8160c2d8.png">

コードを入力するとログインした状態になるので、右上の「Developer Console」のリンクをクリックします。すると下記のような画面が表示されます。
<img width="923" alt="ask-login2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/6d61a102-00a5-f4ac-8813-637e109bc917.png">

３タブあって、それぞれ次のようなものです。特に悩むことはないかと思います。

- プロフィール情報：開発者としての個人情報
- App Distribution Agreement：契約の内容表示と同意
- 支払い：Amazonから開発者に支払いが発生するかどうかの選択など

入力が終わったら開発者コンソールに入ります！
<img width="1006" alt="ask-console1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/8bacbb54-9585-9869-90da-c14382f79e2b.png">


# スキルの作成
1. スキルの作成をするために、「ALEXA SKILLS KIT」をクリックします。
<img width="1006" alt="ask-console2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/a8c2e9d6-0bbd-0a51-e3da-62d99ab9846b.png">

2. するとこんな画面が表示されます。色々と気になるリンクがありますが「スキルの作成」をクリックします。
<img width="1184" alt="ask-console3.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/fb0add10-a983-3cda-f88a-56a080647f5f.png">

3. まず最初にスキルの名前を入力する画面です。スキル名の入力と言語の選択を行って「次へ」をクリックします。
<img width="722" alt="createSkill1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/0b372fad-9e07-a16e-7c21-36027afc4c41.png">

4. 続いてスキルの種類を選択します。今回は独自のスキルを作成するので「カスタム」を選択して「スキルの作成」をクリックします。
<img width="952" alt="createSkill2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/a182f409-6a67-f207-8807-7b7b14079d1f.png">

5. スキルを作成する環境が整いました！
<img width="1050" alt="createSkill3.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/9671171a-8f33-8b61-893f-485d4e4a95f6.png">

## 呼び出し名の設定
触れる場所がたくさんあって目移りしますが、右側にある「スキル ビルダーのチェックリスト」をなぞっていくとなんとなくスキルが出来上がりますので上から順にいきます。

1. 呼び出し名のリンクをクリックします。
<img width="355" alt="console1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/9fb0fb43-2810-fb1d-7d9c-22949270fdd3.png">

2. 呼び出し名を設定する画面が表示されるので編集していきます。
<img width="1055" alt="invitation.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/aa121281-3691-0673-ba64-0ffc317c3481.png">
 1. スキルの呼び出し名を入力します。
    
        呼び出し名はその名の通り、スキルを開始する時に利用者に言ってもらうスキルの名前です。スキルの顔であると同時に、覚えやすく、スキルの内容からイメージしやすい名前が望ましいです。スマホアプリには利用できるスキルが表示されますが、スマートスピーカーはPCどころかスマホを使わなくても情報が得られるのがメリットですが反面、画面が無いためスキル名を忘れられると使われなくなってしまいます。覚えやすくイメージしやすいスキル名を考えましょう。

  2. 続いて「モデルを保存」をクリックします。（スキルの呼び名を入力すると押せるようになります）

        「モデル」は要するにこのツールで設定する内容全般のことです。設定内容の保存をする程度に思っていればいいかと思います。「モデルをビルド」は後で行うので、ここではクリックしなくても大丈夫です。

  3. 左側の「カスタム」をクリックして最初の画面に戻ります。

## インテントの編集
いよいよ本編です！
右側の「インテント、サンプル、スロット」のリンクをクリックします。
<img width="355" alt="console2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/05e9e497-5ded-0d6e-715b-f6204ffc9e94.png">

### 1. インテントの追加

<img width="776" alt="addIntent1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/b6b5297b-38ab-650f-a02a-fd78543b8f07.png">

[こちら](https://qiita.com/edy_jaki/items/0b1f3234ce077e8d9372)でも簡単にインテントの説明をしていますし、この（↑）ページの「詳細はこちら」から表示されるページでも詳細に解説されていますが、**利用者がどういうことをしたいのか**を定義します。

今回は下記の対話フローを想定して、インテントの設定を考えていきます。

---

利用者：「世界時計を開いて」
スマートスピーカー：「世界時計へようこそ。このアプリでは世界中の今の時間や天気を聞くことができます。まずは聞きたい国名または都市名を話してみてください。」

利用者：「サンフランシスコで」
スマートスピーカー：「サンフランシスコですね？では続いて、聞きたいのは時間ですか天気ですか？」

利用者：「時間です」
スマートスピーカー：「サンフランシスコは今、午前１１時４８分です。」
〜〜アプリ終了〜〜

---

まず最初の、**利用者：「世界時計を開いて」**はスキルの起動部分なのでインテントの設定は必要ありません。（実装部分のみで動作します。）

インテントとして設定するのは次の二つになります。

- 利用者が国名／都市名を答える
- 利用者が時間か天気を選択して答える

それぞれを、**CountoryIntent**と**SelectIntent**という名前で定義することにして、作り方を見ていきます。

<img width="772" alt="addIntent2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/fd039c7e-f0c7-28ce-7d15-bf030190fadd.png">

「カスタムインテントを作成」を選択した状態のまま、作成するインテント名を入力して「カスタムインテントを作成」ボタンをクリックします。
すると**サンプル発話**を入力する画面が表示されます。
<img width="773" alt="addIntent3.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/1f517773-dfb9-9639-2ad4-5c277d9340a7.png">

この（↑）のページにも記載されていますが、**サンプル発話**とは利用者が何と言ったらこのインテント（**どういうことをしたいのか**）として認識するか、を定義するものです。

今回のように国（都市）名を話してもらう場面の場合、単純に「東京」と都市名だけを話す人もいれば、「東京で」や、「東京です」、「東京が聞きたい」、「じゃあ東京」など様々な言い方が考えられますよね。

このように、利用者がどういう言い回しで発話するのかを様々なパターンを考えて列挙していきます。すると列挙された内容を元にAlexaSkillsKitが発話内容をうまく解釈して多少の言い回しのズレを考慮してインテントに結びつけてくれます。

１インテントのサンプル発話は最低でも１０個。発話が長いようであればできれば２０個くらい用意できるといいかもしれません。


サンプル発話を入力したら「モデルを保存」ボタンを押します。
続けて他のインテントも作成する場合は左の「インテント」の横にある「追加」のリンクをクリックします。
<img width="1088" alt="addIntent4.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/5b0a8980-bae3-b69a-725a-a1a7c3d6cd96.png">

さて、今回のインテントでは国（都市）名を言ってもらいたいのですが、このまま各都市毎に同じような言い回しを登録していったら恐ろしい数の登録になりますし、（後述しますが）実はこのままだとせっかく話してもらった国（都市）名をプログラム側に渡せません。

このように利用者からすると何らかの選択をして言った単語（数値だったり名詞だったり動詞だったり）、製造者からすると受け取りたい値は**スロット**というものを使って定義していきます。

---

（ちょっと追記）
この例では発話内容が短く、また国（都市）名を聞く状態という発話が短いことが想定されているので例としてはあまりよく無いです。
例えばA地点からB地点までの移動時間を教えてくれるスキルを作る場合、製造者としてはこんな感じで話をしてもらいたいと思います。

「自宅から〜〜駅まで歩いて何分くらいかかるか教えて」

しかし、全ての利用者がこのような話し方をしてくれるわけではありませんよね。

「自宅から〜〜駅まで徒歩でどれくらい」

と言われるかもしれません。他にも色々とあるでしょう。

AlexaSkillsKitではある程度こういった言い回しはAIによってうま〜く解釈してくれますが、そのAIを手助けするために**考え得る限りの言い回しパターン**をこのサンプル発話に列挙する必要があります。

---

### 2. スロットの追加
開発者向けの記事なので分かりやすく言うとスロットは変数です。
変数名や変数の型、言ってほしい単語などを宣言します。


まずはインテントの設定からスロットの追加までの手順を追っていきます。
「サンプル発話」入力欄で**{**を入力してみましょう。すると「既存のスロットを選択」と言う小画面が表示されます。

<img width="378" alt="addSlot1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/5577af9c-e720-4f95-f03c-e4a4563249c5.png">

そのまま変数名となるものを入力して**}**で閉じます。
このスロットと文章を合わせてサンプル発話を構成します。今回の都市名を受け取る例の場合は、↓のような感じになります。

<img width="273" alt="addSlot2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/9355ad3b-7619-4a65-5443-4012801fd4a3.png">

こんな感じでサンプル発話にスロットを含めると、画面左のインテントが一覧で表示されている部分にスロットが追加されるので、これをクリックしてスロット設定画面を開きます。

<img width="627" alt="addSlot4.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/039d54ff-bf1a-ff3b-61fe-b1c81b6f5a83.png">

この「スロットのタイプ」が変数の型になります。
この型には色々種類があって、[こちらの公式](https://developer.amazon.com/ja/docs/custom-skills/slot-type-reference.html#list-types)にも記載があるので目を通しておくといいと思います。
数値を受け取ってくれたり日付を受け取ったりするには定義済みのスロットタイプを使用します。
独自の単語の集まりを使いたい場合は自分で作成することになります。今回は都市名を受け取りたいので「AMAZON.City」というのが使えると思うのですが、それでは説明にならないので・・・・独自で作成する例を書いていきます。

### 3. カスタムスロットタイプの作成

独自でスロットタイプを作成する時は、画面左の「スロットタイプ()」の右にある「追加」のリンクをクリックします。

<img width="320" alt="customSlot1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/6b27119b-ed64-9b37-be82-38043d9a9aeb.png">

すると↓のような追加する画面が表示されます。

<img width="984" alt="customSlot2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/ef947bae-32ed-720f-8b04-bd0fa8c9873a.png">

まずは作成するタイプの名前を入力します。どんな名前でも構いませんが、私はなんとなく先ほどインテントで入力したスロット名と同じにしちゃいます。。。
入力したら「カスタムスロットタイプを作成」をクリックします。
すると続いてスロットの値（入力してほしい単語）を登録する画面が表示されます。

<img width="986" alt="customSlot3.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/4a963a67-6d6e-b084-1e16-774a594c7403.png">

ここにスロット値を幾つも登録することで、独自の単語リストを作成していきます。
今回は都市名なので先の例の通り「東京」と「ロサンゼルス」を入れてみます。

<img width="978" alt="customSlot4.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/c9c07ce5-284f-991c-c8d7-6af360729a92.png">

↑のような感じでリスト化されていきます。
基本的にはこれでOKですがリストを見ると「ID」や「同義語」というオプション列がありますね。

IDはスロットの値と共にプログラム側に渡されます。（例えば東京のIDにTKYを設定しておくと、「東京」だけでなく「TKY」という値も渡されるような感じです。

同義語は、こちらもプログラム側に渡されますが少し特殊な効果を持ちます。
インテントの作成の際にも文章の言い回しを考慮して多種多様な文章を登録するようにしていますが、このスロット値のような単語についても言い回しは多く存在しますよね。
例えば「ロサンゼルス」を「ロス」と呼ぶ人も入れば「エルエー(LA)」なんて言う人もいるかもしれませんね。
こういった場合、それぞれをスロット値としてリストに追加しても処理できますが、同じ意味となる単語なので「同義語」として登録することができます。

<img width="716" alt="customSlot5.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/0f507359-a736-fe02-9975-b0a82ed1d774.png">

このように同義語に単語を設定しておくと、それに対応する値が言われたものとしてAlexaが処理してくれます。最終的にはプログラム側に「値」「ID」「言われた単語（値か同義語）」が渡されるので、処理の分岐が少し楽にできるようになります。

### 4. モデルをビルド

<img width="371" alt="customSlot6.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/b5154d8d-c28c-5a73-318f-5fbc455a38a0.png">

インテントの追加、編集、スロットの設定、カスタムスロットの作成など一連の対話設定ができたら、画面上部にある「モデルを保存」をクリックして、保存に成功したら「モデルをビルド」をクリックします。

設定に不足があったりすると保存時にエラーが表示されます。

<img width="451" alt="modelSaveError1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/9820da7d-7ca9-af02-70d2-f5a9a2ccd439.png">

エラー内容に従って修正しましょう。
保存に成功するとこんな感じで表示されます。

<img width="446" alt="modelSuccess1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/42ac5dc3-8178-e83a-9287-6cfad09f1d32.png">

ビルドを開始するとこのようなメッセージが表示されます。

<img width="444" alt="modelBuild1.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/41371783-c6b9-fba8-5c4e-860f858bf478.png">

その後、「モデルをビルド」のリンクがあった場所が押せなくなってビルド中になります。

<img width="387" alt="modelBuild2.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/e6952a08-c99a-f8d8-fa97-daa724e5ac03.png">

ビルドはしばらく時間がかかるので、しばらく待っていると終了メッセージが表示されます。

<img width="442" alt="slotBuild3.png" src="https://qiita-image-store.s3.amazonaws.com/0/115411/3a8d0581-2eb8-ea29-b304-95f2915fd000.png">

これでインテント周りの登録は終了です！

この後、プログラム側と繋げる設定を行うのですが、いったんプログラム側の説明に移りますね。