Amazon Echoに子供の生年月日を覚えておいてもらう。


やりたいこと

  • Amazon Echo Dotが我が家に届いたので、MyFirstSkill的なものを作りたい。
  • 子供の誕生日は覚えていても、何年生まれかわからなくなるので、Amazon Echoに聞いたら答えてもらえるようにしたい。

事前準備

Amazon開発者アカウントとAWSのアカウント作成。
下記のBlogに沿って進める。(記事内にあるAWSの画面構成が古いので注意)

完成したコード

下記の記事に沿って進めれば動くものが作れるので、ここで言及のないものについては、記事を参照して設定する。

インテントスキーマ
{
  "intents": [
    {
      "slots": [
        {
          "name": "family",
          "type": "myFamily"
        }
      ],
      "intent": "birthdayIntent"
    },
    {
      "intent": "AMAZON.HelpIntent"
    },
    {
      "intent": "AMAZON.StopIntent"
    },
    {
      "intent": "AMAZON.CancelIntent"
    }
  ]
}

インテント名は”birthdayIntent”として、スロットには家族の名前を入れる。

カスタムスロット「myFamily」
パパ
お父さん
ママ
お母さん
長男
Aくん
次男
Bくん

スロット"myFamily"に入る値を定義する。

サンプル発話
birthdayIntent {family} の 誕生日は
birthdayIntent {family} の 誕生日を教えて
birthdayIntent {family} の 誕生日はいつ
birthdayIntent {family} の 生まれた日は
birthdayIntent {family} は いつ生まれたの
birthdayIntent {family} の 生年月日は
birthdayIntent {family} は 何日生まれ
birthdayIntent {family} の 生年月日を教えて
birthdayIntent {family} の 生年月日はいつ

サンプル発話にそれっぽい文章を定義する。

index.js
"use strict";
const Alexa = require('alexa-sdk');

//家族の呼び名を定義
//もうちょっと良い書き方があると思っている。
const familyCalledAs = {
    'パパ':'dad',
    'お父さん':'dad',
    'ママ':'mom',
    'お母さん':'mom',
    '長男':'firstSon',
    'Aくん':'firstSon',
    '次男':'secondSon',
    'Bくん':'secondSon',
};

//誕生日を格納
const birthdayOfFamily = {
  'dad':'YYYY年MM月DD日',
  'mom':'YYYY年MM月DD日',
  'firstSon':'YYYY年MM月DD日',
  'secondSon':'YYYY年MM月DD日'
};

// Lambda関数のメイン処理
exports.handler = function(event, context, callback) {
    var alexa = Alexa.handler(event, context); // Alexa SDKのインスタンス生成
    //alexa.appId = process.env.APP_ID;
    alexa.registerHandlers(handlers); // ハンドラの登録
    alexa.execute();                  // インスタンスの実行
};

var handlers = {
    // インテントに紐付かないリクエスト
    'LaunchRequest': function () {
    this.emit('AMAZON.HelpIntent'); // AMAZON.HelpIntentの呼び出し
    },
    // スキルの使い方を尋ねるインテント
    'AMAZON.HelpIntent': function () {
        this.emit(':tell', '家族の誕生日をお知らせします' +
            'たとえば、パパの誕生日を教えてと聞いてください');
    },
    // 対話モデルで定義した、生年月日を応答するインテント
    'birthdayIntent': function () {
        var nameCalledAs = this.event.request.intent.slots.family.value; // スロットmyFamilyを参照
        var oneToCalled = familyCalledAs[nameCalledAs];
        var birthdayOfWhom = birthdayOfFamily[oneToCalled];
        var message = nameCalledAs + 'の生年月日は' + birthdayOfWhom + 'です'; // 応答メッセージ文字列の作成
        this.emit(':tell', message); // レスポンスの生成
        console.log(message);
    }
};

Amazon Echoで使う

Amazon開発者アカウントとEchoでログインしているアカウントが紐付いていれば、Skillに開発中のスキルが表示されるので、公開手続きは不要でそのまま使える。

「Alexa, 誕生日を開いて、ママの誕生日は?」
「ママの生年月日(せいねんがっひ)はYYYY年MM月DD日です。」

心残り

  • 「誕生日を開いて」という聞き方が不自然。最終的には「誕生日を教えて」「誰のですか?」「ママの誕生日」という対話式にしたほうがいいのかも。
    →対話式に改善したコードをGithubに置きました。

  • うまく拾えなかったり、定義されていない呼び名で呼ぶと、「Undefinedの生年月日はUndefinedです」と答える。

  • 呼び名と誕生日の紐付けはもうちょっとエレガントな書き方がきっとある。

参考にした記事

【保存版】開発部長が102時間かけてまとめたAlexaの落とし穴と習得方法 - Qiita