[AIチャットボット]Amazon Connect + Lexで、スロットタイプAMAZON.FreeFormInputをサンプル発話に関係なく呼び出す方法

2023.11.17

はじめに

Amazon Connect + Lexで、スロットタイプAMAZON.FreeFormInputをもつインテントをサンプル発話関係なく呼び出す方法についてまとめました

Lexでは、インテントを呼び出すためのサンプル発話を各インテントで定義する必要があります。

複数のインテントが定義されている場合は、ユーザーの発話によってインテントを振り分けるために、サンプル発話は必要です。

しかし、インテントが1つしかなく、そのインテントを必ず利用したい場合は、サンプル発話の定義する必要性があまりありません。

スロットタイプによっては、発話サンプルに{スロット名}と入れることで、スロットタイプの内容を即発話することができます。

ただし、AIチャットボットでよく利用する自由形式の入力を受け付けるスロットタイプAMAZON.FreeFormInputの場合、サンプル発話で上記の方法が利用できないと記載があります。

できない理由としては、AMAZON.FreeFormInputは自由形式の入力を受け付けるため、複数インテントがあった場合、インテントの振り分けができないためです。

今回は、サンプル発話が利用できないとドキュメントに記載がありますが、Lambdaを利用し、AMAZON.FreeFormInputをサンプル発話不要で利用する手順をまとめます。

構築

以下の流れで構築します。

  • Lexボットの構築
  • Lambdaの作成
  • Connectのフロー

会話のイメージは下記の通りです。サンプル発話をせず、即質問可能です。

Lexボットの構築

インテント名をOneVoiceとし、サンプル発話は適当に入れます。

スロット名はfree、スロットタイプはAMAZON.FreeFormInputを選択します。

Lambda関数を呼び出すため、下記にチェックを入れます。インテント名FallbackIntentにも同様にチェックします。

後で作成しますが、LambdaをLexから呼び出すため、適切なLambdaを指定し保存します。

Lambdaを呼び出す設定は、[エイリアス]→対象のエイリアス(TestBotAlias)→[言語:Japanese (Japan)]を順にクリックすると、呼び出す設定画面がでます。

これでビルドするとLexのボットの構築は完了です。

Lambdaの作成

ランタイムPython3.11で作成します。

コードは下記の通りです。

import json
from decimal import Decimal

def decimal_to_int(obj):
    if isinstance(obj, Decimal):
        return int(obj)

def input_slots_value(value):
    return {
        'shape': 'Scalar',
        'value': {
            'originalValue': value,
            'resolvedValues': [value],
            'interpretedValue': value
        }
    }

def elicit_intent(intent_name):
    return {
        "sessionState": {
            "dialogAction": {
                "type": "ElicitIntent",
            },
            "intent": {
                "name": intent_name,
                "state": "Fulfilled"
            }
        },
        "messages": [
                {
                    "contentType": "PlainText",
                    "content": ","
                }
            ]
    }
def confirm_intent(message_content, intent_name, slots):
    return {
        'messages': [{'contentType': 'PlainText', 'content': message_content}],
        'sessionState': {
            'dialogAction': {
                'type': 'ConfirmIntent',
            },
            'intent': {
                'name': intent_name,
                'slots': slots,
                'state': 'Fulfilled'
            }
        }
    }
def close(fulfillment_state, message_content, intent_name, slots):
    return {
        'messages': [{'contentType': 'PlainText', 'content': message_content}],
        "sessionState": {
            'dialogAction': {
                'type': 'Close',
            },
            'intent': {
                'name': intent_name,
                'slots': slots,
                'state': fulfillment_state
            }
        }
    }
def lambda_handler(event, context):
    print("Received event:" + json.dumps(event, default=decimal_to_int, ensure_ascii=False))

    if not event["inputTranscript"]:
        return elicit_intent("OneVoice")
    
    slots = event['sessionState']['intent']['slots']
    input_text = event['inputTranscript']
    intent_name = event['sessionState']['intent']['name']

    if slots['free'] is None:
        slots['free'] = input_slots_value(input_text)

    confirmation_status = event['sessionState']['intent']['confirmationState']

    if confirmation_status == "Confirmed":
        return close("Fulfilled", 'それでは、ご回答いたします。〇〇', intent_name, slots)

    elif confirmation_status == "Denied":
        return close("Failed", 'お力になれず、申し訳ありません。', intent_name, slots)

    return confirm_intent(
        f'お問い合わせ内容は、{input_text}。以上です。正しい場合は、はい、正しくない場合、いいえ、とお伝え下さい',
        intent_name, slots)
  • event["inputTranscript"]は、発話を文字起こししたテキストが入ります
  • 発話していない場合、インテントOneVoiceを呼び出します
  • 発話した場合、文字起こし内容は、スロット名freeに入ります

上記の処理によって、発話した際に、スロット名freeに必ず発話内容が入ります。

ちなみに、それでは、ご回答いたします。〇〇では、生成AIでの回答やRAGを用いた回答などの処理を加えるとよいです。

下記が参考になりますので、参考ください。

Connectフロー

Connectのフローはシンプルです。

「顧客の入力を取得する」のブロックでは、先程作成したLexボットを選択し、呼び出すインテントを記載するだけです。

これでフローは完了です。

後は電話番号とフローを紐つけて、電話をかけると下記の会話フローの通り、サンプル発話が不要で即質問が可能になります。

最後に

今回はLambdaを利用し、スロットタイプAMAZON.FreeFormInputをサンプル発話不要で利用する方法について解説しました。

自由形式の入力を受け付けるAMAZON.FreeFormInputは、AIチャットボットでよく利用されますので、開発する方の参考になれば幸いです。