1. 始める前に
この Codelab では、会話型 UI を構築するための会話型 AI プラットフォーム(CAIP)である Dialogflow CX を使用して、小売チャットボットを構築する方法を学習します。Dialogflow CX では、chatbot、音声ボット、電話ゲートウェイなどの仮想エージェントを実装できます。また、50 を超える言語で複数のチャネルをサポートできます。
この Codelab では、小売店向けのウェブサイトの chatbot を作成する方法について説明します。chatbot を構築する架空のビジネスは G-Records という名前です。G-Records は、カリフォルニアを拠点とするロック レコードレーベルです。このレーベルには、Alice Googler、G's N' Roses、The Goo Fighters、The Google Dolls の 4 つのロックバンドが所属しています。G-Records は、すべてのロック ファンにバンドのグッズを販売しています。
この Codelab の最後に、chatbot を使用してシャツや音楽を注文したり、注文について問い合わせたりできます。
学習内容
実際に試しながら、Dialogflow ES と比較した Dialogflow CX のメリットを学びます。次のコンセプトが含まれます。
- Google Cloud 内で Dialogflow CX 仮想エージェントを作成する方法
- フローの作成方法
- エンティティを作成する方法
- インテントの作成方法
- 状態ハンドラを使用してページを作成し、ページを遷移する方法
- インテント ルートを使用してページを遷移する方法
- パラメータと条件ルートを使用してページを遷移する方法
- システム関数を使用して条件付きレスポンスを返す方法を学習する
- フォールバック メッセージの作成方法
- シミュレータの使い方を学ぶ
- テストケースとテストカバレッジを作成する方法を学習する
最終的な Dialogflow CX エージェントの設計は次のようになります。
必要なもの
- Dialogflow CX エージェントを作成するには、Google ID または Gmail のメールアドレスが必要です。
- Google Cloud へのアクセス。
2. 環境設定
Google Cloud プロジェクトを作成する
Dialogflow CX は Google Cloud で実行されるため、Google Cloud プロジェクトを作成する必要があります。プロジェクトを使用して、すべての Google Cloud のリソースがまとめられます。プロジェクトは、共同編集者、有効化された API などのリソース、モニタリング ツール、お支払い情報、認証とアクセス制御で構成されます。
新しいプロジェクトを作成するときに、プロジェクト名を入力する必要があります。既存の請求先アカウントと組織にリンクする必要があります。
請求先アカウントは、特定のリソースセットに対する支払いをだれが行うかの定義に使用され、1 つ以上のプロジェクトにリンクできます。プロジェクトの利用料金は、リンクされた請求先アカウントに請求されます。ほとんどの場合、プロジェクトの作成時に請求情報を構成します。詳細については、お支払いとご請求に関するドキュメントをご覧ください。Cloud プロジェクトで課金が有効になっていることを確認します。
Dialogflow API を有効にする
Dialogflow を使用するには、プロジェクトで Dialogflow API を有効にする必要があります。
- API を有効にするプロジェクトを選択し、[続行] をクリックします。
- [API とサービス] のメニューを閉じて、[認証情報を作成] をクリックします。
- [アプリケーション データ] をクリックします。
- Kubernetes Engine、App Engine、Cloud Functions を現在使用していないため、いいえ、使用していませんと伝えます。
- [完了] をクリックします
新しい Dialogflow CX エージェントを作成する
新しい Dialogflow CX エージェントを作成するには、まず Dialogflow CX コンソールを開きます。
- 前に作成した Google Cloud プロジェクトを選択します。
- [Create Agent(エージェントを作成)] をクリックします。
基本的なエージェント設定に関するフォームに入力します。
- 任意の表示名を選択できます。
- ロケーションとして us-central1 を選択します。
- 使用するタイムゾーンを選択します。
- デフォルトの言語として [en - 英語] を選択します。
[作成] をクリックします。
準備が整いました。これで、バーチャル エージェントのモデリングを開始できます。
3. フロー
複雑な会話には、複数のトピックが含まれていることがよくあります。G-Records 用に作成する chatbot では、バンドのグッズを販売するため、商品カタログ、支払い、注文ステータス、カスタマーケアに関する質問について対話します。これらの会話トピックをフローに分割できます。
フローを使用すると、チームが個々の会話パスで作業できます。フローを簡素化して、画面に簡単に収まり、モジュラー化を進めることをおすすめします。
フローとは、Dialogflow CX の新しいコンセプトです。Dialogflow Essentials には、フローと同様の概念であるメガ エージェントがあります。ただし、フローの方がはるかに頻繁に使用されます。
このラボの後半では、フローを終了できる状態ハンドラを使用します(これにより、次のフローまたは前のフローにジャンプします)。また、エージェント セッション全体を終了することもできます。
では、フローを作ってみましょう。
フローの作成
- Dialogflow CX で、+ アイコン > [フローを作成] をクリックします。
- 名前
Catalog
を指定して Enter キーを押します。
最初のフロー「カタログ」が作成されました。次に、他のフローを作成します。
Order Process
My Order
Customer Care
このラボの後半で、ページ状態ハンドラを設定します。これにより、最終的に可視化は次のようになります。
シミュレータ
Dialogflow CX コンソールの右側にある組み込みのシミュレータを使用して、仮想エージェントをテストできます。会話の最初から、または特定のフローから会話をテストできます。
- 画面右上にある [エージェントをテストする] ボタンをクリックします。
- [talk to agent] フィールドに「
Hello
」と入力します。仮想エージェントは、デフォルトのウェルカム テキスト「Greetings!
このデフォルトのウェルカム テキストを変更してみましょう。
デフォルトの開始フロー
まず、仮想エージェントに挨拶したときにトリガーされるインテント ルートを作成します。
- 左側の [Build > Flows] サイドバーで [Default Start Flow] をクリックし、[Start] ツリーノードを選択します。
[開始] ページが開きます。サイドバーの [Build > Pages] セクションで、自動的に [Start page] が選択されました。
- [Start > Routes](開始 > ルート)で、[Default Welcome Intent](デフォルトのウェルカム インテント)をクリックします。
インテントは、1 回の会話ターンにおけるエンドユーザーの意図を分類します。Dialogflow CX では、インテントを状態ハンドラの一部として、次のアクティブなページまたはフルフィルメントに転送できます。
- [エージェントが言う] のエントリをすべて削除し、次の新しいテキストを追加します。
Welcome, I am the virtual agent of G-Records, a fictional rock label. You can order artists merchandise, ask questions about your order or shipping, and I can tell you more which artists are currently signed with us. How can I help?
会話を効率化するために、クイック返信ボタンや候補チップも必要になります。
- [Add dialogue option > Custom payload] をクリックし、以下のコード スニペットを使用します。
- 以下のコード スニペットをカスタム ペイロードとして使用し、[保存] をクリックします。
カスタム ペイロードの詳細については、ドキュメントをご覧ください。
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Which artists?"
},
{
"text": "Which products?"
},
{
"text": "About my order..."
}
]
}
]
]
}
- シミュレータでウェルカム インテントをテストします。
リッチ コンテンツが表示されない理由について、ご不明な点があると思います。これは、候補チップなどのリッチ コンテンツが統合に依存しているためです。次の手順では請求先アカウントが必要ですが、請求先アカウントがない場合はスキップできます。
- 左側のサイドバーで、[管理] > [統合] をクリックします。
- [Dialogflow Messenger] を選択し、[接続] をクリックします。
- ポップアップで [有効にする] をクリックします。
別のポップアップが表示されます。今回は、ウェブサイトに貼り付けて Dialogflow Messenger コンポーネントをウェブサイトに統合できる統合 JavaScript コードが表示されます。まだウェブサイトがないため、ツールで直接仮想エージェントをテストします。
- [今すぐ試す] リンクをクリックします。
- 右下の chatbot アイコンをクリックして、チャット ウィンドウを開きます。
Hello
と入力して会話を開始します。
現時点では、候補チップをクリックしても、仮想エージェントはユーザーの意図を理解できません。これは、仮想エージェントがまだ状態を切り替えていないためです。Dialogflow CX では、ページを使用してこれを実現できます。ラボを続行します。まず、エンティティとインテントを作成します。
4. エンティティ タイプ
エンティティ タイプは、エンドユーザー入力からデータを抽出する方法を制御するために使用されます。Dialogflow CX エンティティ タイプは、Dialogflow ES エンティティ タイプとよく似ています。Dialogflow には、多数の一般的なデータタイプに対応する事前に定義されたシステム エンティティが用意されています。たとえば、日付、時刻、色、メールアドレスなどをマッチングするためのシステム エンティティがあります。カスタムデータに対応する独自のカスタム エンティティを作成することもできます。
フロー内のページを設計する前に、まずすべてのカスタム エンティティを準備しましょう。次のエンティティを作成します。
エンティティの作成
アーティスト エンティティを作成しましょう。
- [管理] > [エンティティ タイプ] をクリックします。
- [+ 作成] をクリックします。
- 表示名:
Artist
- エンティティ:
The Google Dolls
(類義語:Google Dolls
)The Goo Fighters
(類義語:Goo Fighters
)G's N' Roses
(類義語:Gs and Roses
)Alice Googler
- [詳細オプション] をクリックし、[ファジー一致] をオンにします。(バンド名のスペルが間違っていても、正しいエンティティと一致することがあります)。
- [詳細オプション] で [ログで削除] もオンにします。(バンド名のスペルが間違っている場合は、ログ内の名前が修正されます)。
- [保存] をクリックします。
また、Merch アイテムのエンティティも必要です。
- [管理] > [エンティティ タイプ] をクリックします。
- [+ 作成] をクリックします。
- 表示名:
Merch
- エンティティ:
T-shirt
Longsleeve
(類義語:Longsleeve shirt
)Tour Movie
Digital Album
(類義語:MP3 Album
、MP3
)CD
(類義語Disc
、Physical CD
を含む)
- [保存] をクリックします。
また、アルバムのエンティティも必要になります。
- [管理] > [エンティティ タイプ] をクリックします。
- [+ 作成] をクリックします。
- 表示名:
Album
- エンティティ:
Live
Greatest Hits
(類義語:Hits
)
- [保存] をクリックします。
また、衣料品のサイズのエンティティも必要です。
- [管理] > [エンティティ タイプ] をクリックします。
- [+ 作成] をクリックします。
- 表示名:
ShirtSize
- エンティティ:
XS
(類義語:Extra Small
)S
(類義語:Small
)M
(類義語:Medium
)L
(類義語:Large
)XL
(類義語:Extra Large
)2XL
(類義語:Extra Extra Large
)3XL
- [保存] をクリックします。
注文番号のエンティティ。通常は 4 桁の英数字と 3 桁の数字で構成されます。(ABCD123 など)
- [管理] > [エンティティ タイプ] をクリックします。
- [+ 作成] をクリックします。
- 表示名:
OrderNumber
- 正規表現エンティティ
- エンティティ: [A-Z]{4}[0-9]{3}
- [保存] をクリックします。
エンティティの構成は次のようになります。
@アーティスト:
@Merch:
@アルバム:
@ShirtSize:
@OrderNumber:
カスタム エンティティを準備したら、インテントを準備できます。ラボを続けましょう。
5. インテント
インテントは、1 回の会話ターンにおけるエンドユーザーの意図を分類します。Dialogflow CX では、これらの機能が大幅に簡素化され、会話制御の構成要素ではなくなりました。Dialogflow CX は、ユーザーの発言を一致させるためにインテントのみを使用します。Dialogflow ES では、パラメータ、イベント、フルフィルメントなど、すべてをインテントに関連付ける必要がありました。Dialogflow CX のインテントにはトレーニング フレーズのみが含まれるため、再利用できます。会話の制御は行われなくなります。インテントの作成プロセスは簡単です。
インテントのトレーニング フレーズでは、エンティティを使用して「変数」入力を抽出できます。そのため、エンティティ タイプを事前に作成することをおすすめします。これは、前ページのラボの手順で行ったことです。
インテントの作成
フロー内のページを設計する前に、まずすべてのインテントを準備しましょう。
- [管理] > [Intents] をクリックします。
- [+ 作成] をクリックします。
次の詳細を使用します。
- 表示名
redirect.artists.overview
- 説明文
Artists overview: The bands supported by the label
下にスクロールして、次のトレーニング フレーズを作成します。
Which bands are signed?
Which bands
Which artists
Which artists are part of the record label
Who is part of the label
From which bands can I buy merchandise
Band merchandise
Which music do you have?
I would like to know who are signed to the label
Who are supported by the label
From who can I buy shirts
What music can I order
Can I get an overview of all the artists
- [保存] をクリックします。
- 次に、他のすべてのインテントを作成します。独自の想像力を使って、トレーニング フレーズをさらに考え出してください。ベスト プラクティスとしては、ユーザーがそのインテントをトリガーするさまざまな方法に対応できるように、インテントごとに 10 個以上のトレーニング フレーズを用意することをおすすめします。このラボでは、それより少ない数でも問題ありません。
注意すべき点は次のとおりです。
- トレーニング フレーズを入力すると、Dialogflow CX によってエンティティにアノテーションが自動的に付けられます。エンティティが更新されない場合は、(類義語を追加して)エンティティを更新するか、トレーニング フレーズに手動でアノテーションを付ける必要があります。
- 短いトレーニング フレーズ: Dialogflow の NLU システムは、短いトレーニング フレーズでも動作します。ここでは、いくつかの例を示します。
- 過剰トレーニング: インテントに対してトレーニング フレーズが多すぎると、過剰トレーニングが発生し、望ましくない結果になる可能性があります。反復的なテストと増分テストを使用し、一致するインテントがない場合にトレーニング フレーズを追加することをおすすめします。
表示名 | トレーニング フレーズ |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
再利用可能な要素(フロー、エンティティ、インテント)が準備できたので、ページと状態ハンドラを作成して、これらをまとめることができます。
6. ページと状態ハンドラ
Dialogflow CX の会話(セッション)は、有限状態機械として記述し、可視化できます。自動販売機を例に取ると、有限状態機械としてモデル化できます。状態は、コインの待ち受け、キャンディの選択、キャンディの提供の 3 つで、入力に応じて状態を遷移します。たとえば、コインを挿入すると、自動販売機は「コインを待機中」から「キャンディを選択」に移行します。ページは、Dialogflow CX 仮想エージェントのこれらの状態をモデル化するためのものです。
エンドユーザーが会話で Dialogflow CX を操作すると、会話はページ間で移動します。そのため、どの時点でも、正確に 1 つのページが現在のページであり、現在のページがアクティブとみなされ、そのページに関連付けられたフローがアクティブとみなされます。
フローごとに多数のページを定義します。結合されたページでは、フローが設計されたトピックに関する完全な会話を処理できます。すべてのフローには特別なスタートページがあります。フローが最初にアクティブになると、スタートページが現在のページになります。会話の各ターンでは、現在のページがそのまま表示されるか、別のページに遷移します。このコンセプトを使用すると、多くのページと複数の会話ターンを持つ大規模なエージェントを作成できます。
ページには、フルフィルメント(静的エントリ ダイアログや Webhook)、パラメータ、状態ハンドラが含まれます。会話の制御は状態ハンドラによって行われます。これにより、別の Dialogflow CX ページに遷移するためのさまざまな遷移ルートを作成できます。条件付き(会話の分岐用)にすることもできます。
会話の状態は、次の 3 種類のルートを使用してページ間の遷移を処理することで制御されます。
- インテント ルート: インテントを照合する必要がある場合(エンドユーザーの発言に基づいてページを変更する場合など)。(図の青い線)。
- 条件ルート: 条件を確認する必要がある場合(セッションに保存されている特定のパラメータに基づいてページを変更する場合など)(ビジュアル ダイアグラムの橙色の線)。
- イベント ハンドラ: 特定のフォールバック イベントを処理する必要がある場合(例: 入力なし、一致なしを処理して、エンドユーザーがインテント ルートまたは条件ルートのどちらに該当するかを明確にするため)(図の緑色の線)。
会話の発話(ユーザーへのコンテンツまたはレスポンス)は、フルフィルメントによって定義されます。フルフィルメントは静的または動的です。
- 静的フルフィルメント: 静的フルフィルメント レスポンスが提供された場合
- 動的フルフィルメント: 動的レスポンスに対してフルフィルメント Webhook が呼び出された場合
小売 bot では、インテント ルートを作成し、静的エントリ フルフィルメントのレスポンスを提供します。このレスポンスは、ページが有効になるとすぐにユーザーに表示されます。後で、条件ルートを使用してパラメータを作成し、商品注文に必要な情報を収集します。
ページ インテント ルート
デフォルトの開始フローでページを作成する
デフォルトの開始フローのフローチャートを以下に示します。
一緒にクリックしましょう。
- [Build] > [Default Start Flow] をクリックします。
- [Start Page] をクリックします。
- [ルート] の横にある [+] アイコンをクリックします。
- redirect.artists.overview を追加
- [移行] までスクロールして、[カタログ] フローに移行します。
- [保存] をクリックします。
redirect.product.overview
と、このテーブルの他の 11 行に対して上記の手順を繰り返します。
ページ(フロー内) | [Routes] > [Intent] | [ルート] > [移行先] |
開始 |
| - |
開始 |
| フロー: カタログ |
開始 |
| フロー: カタログ |
開始 |
| フロー: カタログ |
開始 |
| フロー: カタログ |
開始 |
| フロー: カタログ |
開始 |
| フロー: カタログ |
開始 |
| フロー: カスタマーケア |
開始 |
| フロー: カスタマーケア |
開始 |
| フロー: カスタマーケア |
開始 |
| フロー: 注文履歴 |
開始 |
| フロー: 注文履歴 |
開始 |
| フロー: 注文履歴 |
開始 |
| ページ: セッションを終了 |
デフォルトの開始フローは、コールセンターに電話をかけたときのオプション メニューのように機能します。ただし、この仮想エージェントは、インテントのトレーニング フレーズを使用して自然言語でトレーニングされます。そのため、DTMF オプションではなく会話によって操作が決まり、より自然で人間らしいやり取りが可能になります。
カタログフローでページを作成する
次のチャット トランスクリプトはカタログ フローに属しています。
> "Hi"
"Welcome, I am the virtual agent of G-Records, a fictional rock label.
You can order artists merchandise, ask questions about your order or shipping,
and I can tell you more which artists are currently signed with us. How can I help?"
> "Which bands are signed with this record label?"
"The following bands are signed with G-Records:
Alice Googler, G's N' Roses, The Goo Fighters and The Google Dolls.
From which of these artists would you like to order merchandise?"
> "Alice Googler"
"You want to rock with Alice Googler merchandise. Awesome!
We sell shirts, music or the tour movie.
Which merchandise item do you want?"
"(Suggestion chips: [Shirts] [Music] [Tour Movie])"
> "I would like to buy a Shirt"
"Do you want a longsleeve or a t-shirt?"
"(Suggestion chips: [T-shirt, Longsleeve, Price?])"
> "What's the price difference?"
"A t-shirt costs $25 and a longsleeve costs $30.
Do you want a longsleeve or a t-shirt?"
> "A t-shirt",
"What shirt size do you want?"
"(Suggestion chips: [XS, S, M, L, XL, 2XL, 3XL])"
> "M"
"A T-shirt of Alice Googler size: M costs $25. Shall I continue to order?"
[音楽] と [ツアー動画] を選択した場合、ダイアログは異なります。音楽の場合は、次のようなダイアログが表示されます。
> "Music"
"We have a Greatest Hits Album or the Live Album. Which one do you want?"
"(Suggestion chips: [Greatest Hits, Live, Price?])"
> "The Live Album"
"Do you want this album on CD or MP3?"
"(Suggestion chips: [CD, MP3])"
> "What's the price difference?"
"A CD costs $15. The digital album on MP3 costs $10.
Do you want this album on CD or MP3?"
> "Digital Album",
"The Digital Album: Alice Googler - Live costs $10. Shall I continue to order?"
ツアー動画の場合、ダイアログは次のようになります。
> "Tour Movie"
"The Tour Movie of G's N' Roses costs $25. Shall I continue to order?
カタログ フロー内のすべてのページのフローチャートは次のとおりです。
このフローの複雑さに注目してください。
- アーティストに関する質問をスキップして、すぐに「どのようなグッズが購入できますか?」と尋ねることができます。
- デフォルトの開始フローから、「The Google Dolls の T シャツを買いたい」や「何か買いたい」と尋ねることができます。つまり、仮想エージェントは、これらの必須パラメータのスロットを埋めるために、フォローアップの質問をします。商品ページに直接移動します。
- [価格] ダイアログは、再利用される [価格] ページから取得されます。
- ツアー動画の台詞は最もシンプルな台詞のように見えますが、実際には特別な処理を行います。この部分はダイアログで再利用されるため、エンドユーザーは、すべての情報を一度に指定する場合、他のいずれかのプロダクトに直接入力することもできます。
> "I want The Goo Fighters longsleeve size S."
"The longsleeve of The Goo Fighters size S costs $30. Shall I continue to order?"
まず、ページを接続しましょう。
- [Build] > [Catalog] をクリックします。
- [Start Page] をクリックします。
- [ルート] の横にある [+] アイコンをクリックします。
- redirect.artists.overview を追加
- [Transition] までスクロールし、[Page] を選択して、[+ new Page] を選択します。
- ページ名
Artist Overview
を使用して [保存] をクリックします。
残りのフローを完成させましょう。
- 上記の手順は、次のページ、インテント、フルフィルメントで繰り返すことができます。このテーブルを引き継ぎます。[ページ] は、フロー内で選択するページです。[ルート > 遷移先] は、作成して遷移先とする新しいフローまたはページです。
ページ(フロー内) | [Routes] > [Intent] | [ルート] > [移行先] |
カタログの開始 |
| アーティストの概要 |
カタログの開始 |
| プロダクト |
カタログの開始 |
| プロダクトの概要 |
カタログの開始 |
| プロダクトの概要 |
カタログの開始 |
| シャツ |
カタログの開始 |
| 音楽 |
カタログの開始 |
| セッションを終了 |
カタログの開始 |
| フローを終了する |
アーティストの概要 |
| プロダクトの概要 |
次に、静的フルフィルメントをさらに追加します。
- カタログ フローで、[アーティストの概要] ページをクリックします。
- [Entry fulfillment] セクションで [Edit fulfillment] をクリックします。
- 次の静的フルフィルメント(エージェントが伝える)を使用します。
The following bands are signed with G-Records: Alice Googler, G's N' Roses, The Goo Fighters and The Google Dolls.
- [保存] をクリックします。
- カタログのフローで、[商品の概要] ページをクリックします。
- [Entry fulfillment] セクションで [Edit fulfillment] をクリックします。
- 次の静的フルフィルメントを使用します(エージェントが伝える):
We sell shirts, music or the tour movie.
- [保存] をクリックします
ページ パラメータ
パラメータは、セッション中にエンドユーザーが指定した値を取得して参照するために使用されます。各パラメータには名前とエンティティ タイプがあります。@Artist
と @Merch
は、グッズを注文するために収集する必要がある最小限のパラメータです。T シャツや長袖シャツの場合は @ShirtSize
も収集する必要があります。音楽を注文する場合は、@Carrier
と @Album
の名前も必要になります。
これらのパラメータは「必須」としてマークする必要があります。必要な場合は、エンドユーザーを記憶し、正しい回答を提供してこれらのパラメータを収集できるように、カスタム プロンプトを用意する必要があります。Dialogflow CX には、この目的で使用できるメカニズムがいくつかあります。
たとえば、[パラメータ] セクションでカスタムの静的フルフィルメント メッセージを指定できます。パラメータが必須の場合、これらのパラメータのフルフィルメントが表示されます。これらのレスポンス メッセージはレスポンス キューに追加されます。エージェントのターンの間に、複数のフルフィルメントを呼び出して、それぞれがレスポンス メッセージを生成することが可能です(生成が必要な場合もあります)。Dialogflow は、こうしたレスポンスをレスポンス キューに保持します。ページのライフサイクルと、これらのフルフィルメントがレスポンス キューに追加される順序について詳しくは、Dialogflow CX ページのドキュメントをご覧ください。
アーティストの概要ページでパラメータを作成する
ページ パラメータを定義しましょう。
- [カタログ] フローから、[アーティストの概要] ページをクリックします。
- [Parameters] ブロックの [+] をクリックします。artist パラメータを追加します。
- 表示名:
artist
- 事業体タイプ:
@Artist
- 必須: チェック
- ログ内での秘匿化: チェック
- 次に、カスタム パラメータのフルフィルメント メッセージを追加します。artist パラメータが仮想エージェントによってまだ収集されていない場合、エンドユーザーには、レスポンス キューに追加された次のエージェント レスポンスが届きます。
From which of these artists would you like to order merchandise?
- 豊富な候補ワードを提供する 2 つ目のダイアログ オプションを追加します。[Add dialogue option] をクリックし、次のコード(JSON)を使用します。
{
"richContent": [
[
{
"options": [
{
"text": "The Google Dolls"
},
{
"text": "The Goo Fighters"
},
{
"text": "Alice Googler"
},
{
"text": "G's N' Roses"
}
],
"type": "chips"
}
]
]
}
エンドユーザーが回答を試みた回数に応じて、さまざまなフォールバック フルフィルメント プロンプトを処理できます。これは、パラメータ イベント ハンドラで行うことができます。無効なパラメータ、発話が長すぎる、入力なし、1 回目の試行で入力なし、2 回目の試行、一致なしなど、さまざまな組み込みイベント ハンドラから選択できます。入力なしと一致なしの違いは、入力なしの場合、ユーザーが回答を提供しなかったことに対し、一致なしの場合、ユーザーは回答を提供したものの、Dialogflow CX がページとインテントを一致させることができなかったことです。
- [リプロンプト イベント ハンドラ] セクションまでスクロールします。
- [イベント ハンドラを追加] をクリックし、イベント
No-match default
を選択します。 - 次のイベントの静的テキスト フルフィルメントを使用します。
I missed that. Please, specify the artist. You can choose between: Alice Googler, G's N' Roses, The Google Dolls or The Goo Fighters. Which artist do you want to buy merchandise from?
- [保存] をクリックします。
- [イベント ハンドラを追加] をクリックし、イベント
No-input default
を選択します。 - 次のイベントの静的テキスト フルフィルメントを使用します。
I am sorry, I could understand the artist's name. You can choose between Alice Googler, G's N' Roses, The Google Dolls or The Goo Fighters. Which artist do you want to buy merchandise from?
- [保存] をクリックします。
ページ条件ルート
パラメータは、ページ条件ルートと組み合わせると非常に強力です。条件が true と評価されると、関連するページルートが呼び出されます。条件には、パラメータが特定の値に等しい、パラメータが欠落している、フォームが完了しているなどがあります。パラメータと条件の詳細については、Dialogflow CX のドキュメントをご覧ください。
小売のバーチャル エージェントでは、一連のパラメータを収集する必要があります。そのため、「フォーム」が完了したかどうかを確認する条件を作成する必要があります。フォームは、ページのエンドユーザーから収集する必要があるパラメータのリストです。仮想エージェントは、必要なすべてのフォーム パラメータ(ページ パラメータとも呼ばれます)を収集するまで、複数の会話ターンでエンドユーザーとやり取りします。
Dialogflow CX では、フォームの入力中にエンドユーザーから提供されたパラメータ値が自動的に設定されます。現在のページのすべてのフォームが入力されているかどうかを確認するには、次の条件を使用します。$page.params.status = "FINAL"
アーティストの概要ページで条件付きルートを作成する
アーティストが判明したら次のページに遷移する条件付きルートを作成しましょう。
- [アーティストの概要] ページの [ルート] セクションで、+ アイコンをクリックします。
- [状態] セクションまで下にスクロールします。
- [1 つ以上](OR)を選択します。
- 次に、次のような式を記述します。
- パラメータ:
$page.params.status
- 演算子:
=
- 値:
"FINAL"
- 次に、エンドユーザーの選択を確認する、ルート上の特定の静的フルフィルメント メッセージを作成します。[Fulfillment] ブロックまで下にスクロールし、次のフルフィルメント メッセージを記述します。
$session.params.artist, great choice! Rock on!
You want to rock with $session.params.artist merchandise. Awesome!
- 条件が true の場合、[商品の概要] ページに移動する必要があります。[Transition] セクションまでスクロールし、次のページ
Product Overview
を使用します。 - [保存] をクリックします
[プロダクトの概要] ページでルートを作成する
パラメータと条件付きルートの作成方法を理解したところで、次のページのパラメータを作成しましょう。
プロダクトの概要
- [プロダクトの概要] ページで
artist
パラメータを作成します。
- 表示名:
artist
- 事業体タイプ:
@Artist
- 必須: チェック
- ログ内での秘匿化: チェック
- 初期プロンプト フルフィルメント:
From which of these artists would you like to order merchandise?
{
"richContent": [
[
{
"options": [
{
"text": "The Google Dolls"
},
{
"text": "The Goo Fighters"
},
{
"text": "Alice Googler"
},
{
"text": "G's N' Roses"
}
],
"type": "chips"
}
]
]
}
- イベント ハンドラ >
No-match default
:To buy merchandise you can choose between the following artists: Alice Googler, G's N' Roses, The Google Dolls or The Goo Fighters. Which artist do you want to buy merchandise from?
- カスタム ペイロード:
{
"richContent": [
[
{
"options": [
{
"text": "The Google Dolls"
},
{
"text": "The Goo Fighters"
},
{
"text": "Alice Googler"
},
{
"text": "G's N' Roses"
}
],
"type": "chips"
}
]
]
}
- イベント ハンドラ >
No-input default
:To buy merchandise you can choose between the following artists: Alice Googler, G's N' Roses, The Google Dolls or The Goo Fighters. Which artist were you trying to mention?
- カスタム ペイロード:
{
"richContent": [
[
{
"options": [
{
"text": "The Google Dolls"
},
{
"text": "The Goo Fighters"
},
{
"text": "Alice Googler"
},
{
"text": "G's N' Roses"
}
],
"type": "chips"
}
]
]
}
merch
パラメータを作成します。
- 表示名:
merch
- 事業体タイプ:
@Merch
- 必須: チェック
- ログ内での秘匿化: チェック
- フルフィルメント:
Which merchandise item do you want?
- [Add dialogue option] > [Custom payload] をクリックします。
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Shirts"
},
{
"text": "Music"
},
{
"text": "Tour movie"
}
]
}
]
]
}
- イベント ハンドラ >
No-match default
- イベント ハンドラのフルフィルメント:
We sell Shirts, Music or the Tour movie. Which of these items do you want?
- カスタム ペイロード:
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Shirts"
},
{
"text": "Music"
},
{
"text": "Tour movie"
}
]
}
]
]
}
- イベント ハンドラ >
No-input default
- イベント ハンドラのフルフィルメント:
I couldn't understand which merchandise item you wanted to buy. You can choose between: Shirts, Music or the Tour movie. Which item do you want?
- カスタム ペイロード:
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Shirts"
},
{
"text": "Music"
},
{
"text": "Tour movie"
}
]
}
]
]
}
artist
が提供され、merch
アイテムが提供された場合に [商品] ページに遷移するルートを作成します。
- 条件:
- すべてのルールに一致(AND)
- 式:
$session.params.artist != null
- 式:
$session.params.merch != null
- フルフィルメント:
Alright! $session.params.merch of $session.params.artist, let's go!
- 遷移: ページ:
Product
- ユーザーが「シャツ」と言ったときのルートを作成する
- インテント: redirect.shirts
- 遷移: ページ:
Shirts
- ユーザーが「音楽」と言った場合のルートを作成する
- インテント: redirect.music
- 遷移: ページ:
Music
- ユーザーが料金情報を尋ねてきた場合のルートを作成する
- インテント: redirect.price
- 遷移: 新しいページを作成:
Price
上記の設定を行うと、次の画像のような可視化が表示されます。図では、インテントのルートは青色、条件ルートはオレンジ色になっています。イベント ハンドラは緑色で、複数のルートタイプがページに遷移する場合は、線がグレーになります。
ここまでで、パラメータに基づくインテント ルートや条件ルートなどのステート ハンドラを使用して、フロー、エンティティ、インテント、ページを作成する方法を学びました。このラボの後半では、フルフィルメントで条件付き分岐を使用して、入力に基づいて異なるダイアログを提供します。
次の構成を使用して、仮想エージェントを完成させることができます。
シャツのページ:
- [Shirts] ページで、次の構成を作成します。
- エントリのフルフィルメント:
Do you want a longsleeve or a t-shirt?
- エントリのフルフィルメント カスタム ペイロード:
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "T-shirt"
},
{
"text": "Longsleeve"
},
{
"text": "Price?"
}
]
}
]
]
}
- インテント ルート
redirect.price
を作成して、Price
ページに遷移します。 - 次のパラメータを作成します。
- パラメータ:
merch
- エンティティ タイプ:@Merch
、Required
、Redact in log
- パラメータ > イベント ハンドラ >
No-match default
- パラメータ > イベント ハンドラのフルフィルメント:
You can choose between a t-shirt or a longsleeve. Which of these do you want?
- [Parameter] > [Event Handler Fulfillment Custom payload](パラメータ > イベント ハンドラのフルフィルメント カスタム ペイロード):
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "T-shirt"
},
{
"text": "Longsleeve"
}
]
}
]
]
}
- パラメータ > イベント ハンドラ >
No-input default
- パラメータ > イベント ハンドラのフルフィルメント:
I couldn't understand if you want the t-shirt or the longsleeve. Which of these do you want?
- [Parameter] > [Event Handler Fulfillment Custom payload](パラメータ > イベント ハンドラのフルフィルメント カスタム ペイロード):
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "T-shirt"
},
{
"text": "Longsleeve"
}
]
}
]
]
}
- エントリのフルフィルメントをクリックし、[パラメータのプリセット] までスクロールします。[シャツ] ページがアクティブになるたびに、カテゴリ パラメータが [シャツ] に設定されます。
パラメータ | 値 |
|
|
- 条件付きルートを追加します。
- 少なくとも 1 つのルールに一致(OR)
- 式:
$session.params.merch = "T-shirt"
- 式:
$session.params.merch = "Longsleeve"
- 新しいページへの遷移:
Shirt Size
料金ページ:
価格に関するメッセージは、選択した商品アイテムまたはカテゴリ(音楽またはシャツ)によって異なるため、この部分は後ほどラボで修正します。現時点では、プレースホルダを入力するだけで十分です。
- [料金] ページで、次の構成を作成します。
- エントリのフルフィルメント:
PRICE TODO
会話のさまざまな場所で料金をリクエストできるため、常に回答が返され、会話の前の部分に戻って注文を続行できます。ダイアログ ツリーには、料金情報を取得するために分岐できる場所が 5 か所あります。(シャツ、シャツのサイズ、音楽、携帯通信会社、インテント ルート経由の直接アクセス)があるため、戻るには条件付きルートが必要です。
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$session.params.category = "shirts"
- 式:
$session.params.merch = "null"
- 新しいページへの遷移:
Shirts
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$session.params.category = "shirts"
- 式:
$session.params.size = "null"
- 新しいページへの遷移:
Shirt Size
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$session.params.category = "music"
- 式:
$session.params.album = "null"
- 新しいページへの遷移:
Music
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$session.params.category = "music"
- 式:
$session.params.merch = "null"
- 新しいページへの遷移:
Carrier
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$session.params.category = "null"
- 新しいページへの遷移:
Product Overview
シャツのサイズページ:
- [Shirt Size] ページで、次の構成を作成します。
- エントリのフルフィルメント:
What shirt size do you want?
- エントリのフルフィルメント カスタム ペイロード:
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "XS"
},
{
"text": "S"
},
{
"text": "M"
},
{
"text": "L"
},
{
"text": "XL"
},
{
"text": "2XL"
},
{
"text": "3XL"
}
]
}
]
]
}
Price
ページへの遷移を含むインテント ルートredirect.price
を作成します。- 次のパラメータを作成します。
- パラメータ:
shirtsize
- エンティティ タイプ:@ShirtSize
-Required
、Redact In Log
- パラメータ > イベント ハンドラ >
No-match default
- パラメータ > イベント ハンドラのフルフィルメント:
Please tell me the shirt size, such as XL.
- [Parameter] > [Event Handler Fulfillment Custom payload](パラメータ > イベント ハンドラのフルフィルメント カスタム ペイロード):
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "XS"
},
{
"text": "S"
},
{
"text": "M"
},
{
"text": "L"
},
{
"text": "XL"
},
{
"text": "2XL"
},
{
"text": "3XL"
}
]
}
]
]
}
- パラメータ > イベント ハンドラ >
No-input default
- パラメータ > イベント ハンドラのフルフィルメント:
I couldn't understand the shirt size. What size do you want?
- [Parameter] > [Event Handler Fulfillment Custom payload](パラメータ > イベント ハンドラのフルフィルメント カスタム ペイロード):
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "XS"
},
{
"text": "S"
},
{
"text": "M"
},
{
"text": "L"
},
{
"text": "XL"
},
{
"text": "2XL"
},
{
"text": "3XL"
}
]
}
]
]
}
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$page.params.shirtsize != "null"
- ページへの遷移:
Product
音楽ページ:
- [音楽] ページで、次の構成を作成します。
- エントリのフルフィルメント:
We have a Greatest Hits Album or the Live Album. Which one do you want?
- エントリのフルフィルメント カスタム ペイロード:
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Greatest Hits"
},
{
"text": "Live"
},
{
"text": "Price?"
}
]
}
]
]
}
- ページ:
Price
への遷移を含むインテント ルート:redirect.price
を作成します。 - 次のパラメータを作成します。
- パラメータ:
album
- エンティティ タイプ:@Album
-Required
、Redact In Log
- パラメータ > イベント ハンドラ >
No-match default
- パラメータ > イベント ハンドラのフルフィルメント:
You can choose between Greatest Hits and Live Album. Which of these do you want?
- [Parameter] > [Event Handler Fulfillment Custom payload](パラメータ > イベント ハンドラのフルフィルメント カスタム ペイロード):
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Greatest Hits"
},
{
"text": "Live"
}
]
}
]
]
}
- パラメータ > イベント ハンドラ >
No-input default
- パラメータ > イベント ハンドラのフルフィルメント:
I couldn't understand if you want the album: Greatest Hit or Live. Which of these do you want?
- [Parameter] > [Event Handler Fulfillment Custom payload](パラメータ > イベント ハンドラのフルフィルメント カスタム ペイロード):
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Greatest Hits"
},
{
"text": "Live"
}
]
}
]
]
}
- エントリのフルフィルメントをクリックし、[パラメータ プリセット] までスクロールします。音楽ページが有効になるたびに、カテゴリ パラメータが music に設定されます。
パラメータ | 値 |
|
|
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$page.params.album != "null"
- ページへの遷移:
Carrier
携帯通信会社ページ:
- [Carrier] ページで、次の構成を作成します。
- エントリのフルフィルメント:
Do you want this album on CD or MP3?
- エントリのフルフィルメント カスタム ペイロード:
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "CD"
},
{
"text": "MP3"
},
{
"text": "Price?"
}
]
}
]
]
}
- インテント ルート
redirect.price
を作成します。このルートは、Price
ページに遷移します。 - 次のパラメータを作成します。
- パラメータ:
merch
- エンティティ タイプ:@Merch
-Required
、Redact In Log
- パラメータ > イベント ハンドラ >
No-match default
- パラメータ > イベント ハンドラのフルフィルメント:
Do you want a physical CD or the digital album?
- [パラメータ] > [イベント ハンドラのフルフィルメント: カスタム ペイロード] に移動します。
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "CD"
},
{
"text": "Digital Album"
}
]
}
]
]
}
- パラメータ > イベント ハンドラ >
No-input default
- パラメータ > イベント ハンドラのフルフィルメント:
I couldn't understand if you mean CD or MP3. Which one do you want?
- [Parameter] > [Event Handler Fulfillment: Custom payload](パラメータ > [イベント ハンドラのフルフィルメント: カスタム ペイロード]):
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "CD"
},
{
"text": "MP3"
}
]
}
]
]
}
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$page.params.merch != "null"
- ページへの遷移:
Product
商品ページ:
- 次のパラメータを作成します。
パラメータの表示名 | パラメータ エンティティ タイプ | チェック |
|
| 必須、ログ内での秘匿化 |
|
| 必須、ログ内での秘匿化 |
- artist パラメータには、アーティストが不明な場合に表示される次の初期プロンプト フルフィルメントが必要です。
You didn't mention which artist you are interested in. You can ask me to buy the $session.params.merch of the artist you like or ask which artists we signed. How can I help?
{
"richContent": [
[
{
"options": [
{
"text": "Which artists?"
}
],
"type": "chips"
}
]
]
}
- また、フルフィルメント
I couldn't understand what you just said. Ask me which artists are signed.
を持つNo-input default
イベント ハンドラを追加します。 - フルフィルメントを含む
No-match default
イベント ハンドラ:I missed that. Please ask me which artists are signed.
- merch パラメータには、リプロンプト イベント ハンドラも必要です。
- フルフィルメント
I couldn't understand what you just said. Which merchandise item do you want?
を使用してNo-input default
イベント ハンドラを追加します。 - フルフィルメントを含む
No-match default
イベント ハンドラ:I missed that. Which merchandise item do you want?
次のルートは、アーティストが判明し、ユーザーが [ツアー ムービー] を選択すると、確認ページに移動します。
- 条件付きルートを追加します。
- すべてのルールに一致(AND)
- 式:
$session.params.artist != null
- 式:
$session.params.merch = "Tour Movie"
- パラメータ プリセット [パラメータを追加] >
price = 25
- 新しいページへの遷移:
Confirmation
次のルートは、アーティストが判明し、ユーザーが [T シャツ] を選択し、シャツのサイズを選択すると、確認ページに遷移します。
- 条件付きルートを追加します。
- カスタム式:
$session.params.artist != null AND $session.params.merch = "T-shirt" AND $session.params.shirtsize != null
- パラメータ プリセット [パラメータを追加] >
price = 25
- ページへの遷移:
Confirmation
次のルートは、アーティストが判明し、ユーザーが [長袖] を選択し、シャツのサイズを選択すると、確認ページに移動します。
- 条件付きルートを追加します。
- カスタム式:
$session.params.artist != null AND $session.params.merch = "Longsleeve" AND $session.params.shirtsize != null
- パラメータ プリセット [パラメータを追加] >
price = 30
- ページへの遷移:
Confirmation
次のルートは、アーティストが判明し、ユーザーが [CD] を選択してアルバム名を選択すると、確認ページに移行します。
- 条件付きルートを追加します。
- カスタム式:
$session.params.artist != null AND $session.params.merch = "CD" AND $session.params.album != null
- パラメータ プリセット [パラメータを追加] >
price = 15
- ページへの遷移:
Confirmation
次のルートは、アーティストが判明し、ユーザーが [デジタル アルバム] を選択し、アルバム名を選択すると、確認ページに移行します。
- 条件付きルートを追加します。
- カスタム式:
$session.params.artist != null AND $session.params.merch = "Digital Album" AND $session.params.album != null
- パラメータ プリセット [パラメータを追加] >
price = 10
- ページへの遷移:
Confirmation
次に、不足している情報を検出するプロンプトを使用して、高度な条件を作成します。次のルートは、アーティストが判明し、ユーザーが [CD] または [デジタル アルバム] を選択したがアルバム名を選択しなかった場合に、音楽ページに戻ります。
- 条件付きルートを追加します。
- カスタム式:
$session.params.artist != null AND ($session.params.merch = "CD" OR $session.params.merch = "Digital Album") AND $session.params.album = null
- フルフィルメント:
I would also need to know which album you would like to buy!
- ページへの遷移:
Music
最後のルートは、アーティストが判明し、ユーザーが「T シャツ」または「長袖」を選択したが、T シャツのサイズを選択しなかった場合に、確認ページに遷移します。
- 条件付きルートを追加します。
- カスタム式:
$session.params.artist != null AND ($session.params.merch = "T-shirt" OR $session.params.merch = "Longsleeve") AND $session.params.shirtsize = null
- フルフィルメント:
I would also need to know which shirt size you need!
- ページへの遷移:
Shirt Size
ラボの次のパートでは、条件付きフルフィルメントを使用して、入力に応じて異なるフルフィルメント メッセージを返します。
7. 条件付きレスポンス
一部のレスポンスは、入力に基づいて異なるダイアログを返します。ダイアログは分岐します。これを条件付きレスポンスと呼びます。これは、Webhook フルフィルメントを使用しておらず、条件付きレスポンスがバックエンドで決定されている場合に役立ちます。例を次に示します。
if [condition]
[response]
elif [condition]
[response]
elif [condition]
[response]
else
[response]
endif
- [condition] の例:
$session.params.user-age >= 21
。ルートの条件と同様の形式を使用します。 - [response] は静的テキスト レスポンスを受け取ります
- 条件付きレスポンスは常に
if
で始まります。 elif
ブロックとelse
ブロックは省略可能です。
Dialogflow CX は、組み込みのシステム関数も使用できます。たとえば、日付や時刻の形式設定、現在の時刻の表示($sys.func.NOW()
)
カタログ フローを完成させるため、[確認] ページと [価格] ページを修正しましょう。
確認ページ:
次に、確認ページを作成します。次の要件があります。
- merch が CD または Digital Album の場合。確認画面には、[アーティスト]、[グッズ]、[アルバム]、[価格] の各フィールドが表示されます。
- merch が [T-shirt] または [Longsleeve] の場合。確認画面には、[アーティスト]、[グッズ]、[サイズ]、[価格] の各フィールドが表示されます。
- それ以外の場合(merch が Tour Movie の場合)。確認画面には、[アーティスト]、[グッズ]、[価格] の各フィールドが表示されます。
- [確認] ページをクリックします。
- [Fulfillment の編集] > [エージェント レスポンス] > [Add dialogue] オプション > [Conditional Response] をクリックします。
if ($session.params.merch = "CD" OR $session.params.merch = "Digital Album")
The $session.params.merch: $session.params.artist - $session.params.album costs $$session.params.price. Shall I continue to order?
elif ($session.params.merch = "T-shirt" OR $session.params.merch = "Longsleeve")
A $session.params.merch of $session.params.artist size: $session.params.shirtsize costs $$session.params.price. Shall I continue to order?
elif $session.params.merch = "Tour Movie"
The $session.params.merch of $session.params.artist costs $$session.params.price. Shall I continue to order?
else
It looks like something went wrong with your order. You can say "Reset", to restart the order process.
endif
- Create the following Custom payload:
- Custom payload:
{
"richContent": [
[
{
"options": [
{
"text": "Yes, confirm"
}
],
"type": "chips"
}
]
]
}
Next, create two intent routes:
confirm.proceed.order
transitions to:Order Process
Flow.decline.proceed.order
transitions toEnd Flow
When the user declines the order, and does not want to proceed the order process, we will have to transition back to the welcome page, but all the parameters have to be cleared. We can do this by specifically setting null to all the possible parameters. You can do this with Parameter presets.
- In the decline.proceed.order intent route, scroll down to Parameter presets and add the following parameters:
Parameter | Value |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Notice that we have created an additional parameter called restart
. If this parameter is present, the Default Start Flow, should know to continue the conversation by showing a customized message.
- Click on the Default Start Flow, Start Page, and create another Conditional Route:
$session.params.restart = "true"
- Fulfillment:
"Welcome back, as the virtual agent of G-Records, I can help you order artists merchandise, you can ask questions about your order or shipping, and I can tell you more which artists are currently signed with us. How can I help?"
- Custom payload:
{
"richContent": [
[
{
"type": "chips",
"options": [
{
"text": "Which artists?"
},
{
"text": "Which products?"
},
{
"text": "About my order..."
}
]
}
]
]
}
- Select the Start Page and click on the
redirect.end
intent. Create the following fulfillment:Thank you for contacting G-Records! Have a nice day!
Price Page:
Let's also fix the Price TODOs. The price information will be static for now. Click on the Price Page in the Catalog Flow, and use the following entry fulfillment:
- Delete the Agent Says entry fulfillment.
- Create a new Conditional Response:
if $session.params.category = "shirts"
A t-shirt costs $25 and a longsleeve costs $30.
elif $session.params.category = "music"
A CD costs $15. The digital album on MP3 costs $10.
else
A t-shirt costs $25 and a longsleeve costs $30. A CD costs $15 and a digital album on MP3 $10. In case you are interested in the Tour Movie, that one is $25.
endif
Well done, by now you completed the Catalog flow. Your flow should look similar to this diagram:
8. Wrapping up the agent
We are almost at the end of this lab. Let's configure the last flows together, and take in practice all the new things that we have learned.
Creating the My Order Flow
- Go to the My Order Flow, and create the following intent transitions:
Page (In Flow) | Routes > Intent | Routes > Transition To |
My Order Start |
| My Order |
My Order Start |
| My Order Status |
My Order Start |
| My Order Cancellation |
My Order Start |
| End Session |
My Order Start |
| End Flow |
My Order |
| My Order Status |
My Order |
| My Order Cancellation |
Default Start Flow |
| Flow: My Order |
Default Start Flow |
| Flow: My Order |
- Let's create the following entry fulfillment for the My Order Page:
- Entry fulfillment:
I can look up the status of your order, or I can cancel an order.
- In the My Order Page create the following parameter:
- Displayname:
ordernumber
- Entity Type:
@OrderNumber
- Required: checked
- Initial prompt fulfillment:
What's the order number? For example ABCD123.
- Event Handler:
No-match default
:To proceed with your order I will need an order number. Order numbers start with 4 characters and end with 3 numbers, such as ABCD123. Which order number may I use?
- Event Handler:
No-input default
:I missed that. To proceed with your order I will need an order number. Order numbers start with 4 characters and end with 3 numbers, such as ABCD123. Which order number may I use?
- Create the following conditional route:
- Customize Expression:
$page.params.status = "FINAL"
- Fulfillment:
And do you want to Cancel your order, or should I look up the status?
- Click on Add state handler > Event Handlers and create the Event Handler:
No-input default
- Fulfillment:
I'm sorry, what was that? Would you like me to cancel an order or look up the status?
- Custom payload:
{
"richContent": [
[
{
"options": [
{
"text": "Status"
},
{
"text": "Cancel"
}
],
"type": "chips"
}
]
]
}
- Create the Event Handler:
No-match default
- Fulfillment:
Would you like me to cancel an order or lookup the status?
- Custom payload:
{
"richContent": [
[
{
"options": [
{
"text": "Status"
},
{
"text": "Cancel"
}
],
"type": "chips"
}
]
]
}
- In the My Order Status Page create the following parameter:
- Displayname:
ordernumber
- Entity Type:
@OrderNumber
- Required checked
- Initial prompt fulfillment:
What's the order number? For example ABCD123.
- Event Handler:
No-match default
:To proceed with your order I will need an order number. Order numbers start with 4 characters and end with 3 numbers, such as ABCD123. Which order number may I use?
- Event Handler:
No-input default
:I missed that. To proceed with your order I will need an order number. Order numbers start with 4 characters and end with 3 numbers, such as ABCD123. Which order number may I use?
- In the My Order Status Page create the following conditional route:
- Customize Expression:
$session.params.ordernumber != null
- Fulfillment:
Your order $session.params.ordernumber has been shipped, it can take up to approx 2 weeks before you will receive your items.
- Add dialogue option > Text:
Is there anything else I can help you with?
- In the My Order Cancelation Page create the following parameter:
- Displayname:
ordernumber
- Entity Type:
@OrderNumber
- Required checked
- Initial prompt fulfillment:
What's the order number? For example ABCD123.
- Event Handler:
No-match default
:To proceed with your order I will need an order number. Order numbers start with 4 characters and end with 3 numbers, such as ABCD123. Which order number may I use?
- Event Handler:
No-input default
:I missed that. To proceed with your order I will need an order number. Order numbers start with 4 characters and end with 3 numbers, such as ABCD123. Which order number may I use?
- In the My Order Cancelation Page create the following conditional route:
- Customize Expression:
$session.params.ordernumber != null
- Fulfillment:
Your order $session.params.ordernumber has been canceled.
- Add dialogue option > Text:
Is there anything else I can help you with?
- Test the flow and create the following two test scenarios:
>"About my order"
>"ABCD123"
>"Status"
And:
>"What's the status of order DEFG222"
- Select the Start Page and click on the
redirect.end
intent. Create the following fulfillment:Thank you for contacting G-Records! Have a nice day!
- Select the Start Page and click on the
redirect.home
intent. Create the following parameter preset:restart = true
Default Negative intents (Fallback)
When you create a virtual agent, a default negative intent is created for you. You can add training phrases to this intent that act as negative examples that will trigger a No-match event. There may be cases where end-user input has a slight resemblance to training phrases in normal intents, but you do not want these inputs to match any normal intents.
- Try in the simulator:
I don't like Alice Googler
.
You will see that the virtual agent answers with the Product Overview Page, to continue ordering Alice Googler merchandise. However, your end user does not like that artist. Let's use the Default Negative Intent for this.
- Go to Manage > Intents and select the Default Negative Intent.
- Add the following training phrases that will trigger the No-match event.
I don't like Alice Googler
I am not a fan of G's N' Roses
I can't stand the music of the Google Dolls
- Hit Save and test the following sentence in the simulator:
I am really not a fan of the Goo Fighters
This time the No-match
event was triggered, you stayed on the Start Page.
Default Fallback Messages
- Click the Default Start Flow, select the
sys.no-input-default
event handler.
The No-input fallback basically means: No text or speech answers were detected. Likely no answers were given, or the system couldn't hear it. Therefore, let's make the fallback messages more specific. Use the tab key, to create alternative dialogues:
- Remove all answers, and add these text dialogues:
I'm sorry, I didn't receive an answer. Can you say it again?
I missed your answer, can you say it again?
Sorry, I didn't hear anything. Can you say it again?
I couldn't hear what you were saying, what was that?
I'm sorry, I missed your answer. What were you trying to say?
Don't forget to click Save.
- Click the Default Start Flow, select the
sys.no-match-default
event handler.
The No Match fallback basically means: Text or speech answers were detected but nothing in Dialogflow CX got matched.
- Remove all answers, and add these text dialogues:
Sorry, I didn't get that. Can you please rephrase?
I'm sorry, I don't understand. Can you please rephrase?
I don't understand, please rephrase.
Sorry, I didn't get that. What was that?
I didn't get that, can you please rephrase?
Don't forget to click Save.
- It's advised to repeat these steps for the Catalog, My Order, Order Process and Customer Care flows.
Here's a tip: when creating fallback messages, make them more explicit, by rephrasing the previous question or by mentioning an example. You could create these type of No-match and No-input events on Page level when creating parameters. In our labs, we have already done this.
Creating the Order Process Flow
- Go to the Order Process Flow, and create the following intent transitions:
Page (In Flow) | Routes > Intent | Routes > Transition To |
Order Process Start |
| End Session |
Order Process Start |
| End Flow |
Order Process Start |
| New Page: Shipping Details |
- Let's create the following entry fulfillment for the Shipping Details Page:
- Entry fulfillment:
To complete your order I will first need to collect your shipping details.
- Create the following parameters:
These parameters will make use of built-in system entities. System entity support differs for each language. See the docs for more information.
Parameter Display name | Entity | Required? | Initial prompt fulfillment | No-match default | No-input default |
| @sys.person | Required |
|
|
|
| @sys.person | Required |
|
|
|
| @sys.address | Required |
|
|
|
| @sys.any | Required |
|
|
|
| @sys.geo-city | Required |
|
|
|
| @sys.geo-country | Required |
|
|
|
| @sys.email | Required |
|
|
|
- Create the following conditional route:
- Customize Expression:
$page.params.status = "FINAL"
- Transition to new Page:
Payment Details
- Create the following entry fulfillment.
Let's fake it that this virtual agent makes use of Google Pay. Don't worry this tutorial won't make real transactions. Create the following entry dialogues:
- Agent Says:
Alright $session.params.firstname! We will make use of Google Pay, that's connected to your email account: $session.params.email.
- Conditional Response
if $session.params.merch != "Digital Album"
Shipping costs an additional 5 dollars. This will make the total price $$sys.func.TO_TEXT($sys.func.ADD($session.params.price, 5)).
Your merchandise will be shipped to:
$session.params.firstname $session.params.lastname
$session.params.address
$session.params.zipcode $session.params.city
$session.params.country
To continue the order process please explicitly say "I confirm". Do you want to confirm your $session.params.artist $session.params.merch order?
else
The total costs will be: $$session.params.price.
After purchasing the digital album, you will receive an email with the download link.
To continue the order process please explicitly say "I confirm".
Do you want to confirm your $session.params.artist $session.params.merch order?
endif
- 次のインテント ルートを作成します。
- インテント:
confirm.proceed.order
- エージェントの発話:
Thank you for your order! Your merchandise will be shipped today!
- [Add Dialogue Option] > [Text] に
Here's the order number: ABCD123
を入力します。 - 会話オプションを追加 > テキスト:
Have a good day!
- 切り替え:
End Session
- [Start] ページを選択し、
redirect.end
インテントをタップします。次のフルフィルメントを作成します。Thank you for contacting G-Records! Have a nice day!
- [Start] ページを選択し、
redirect.home
インテントをタップします。次のパラメータ プリセットを作成します。restart = true
問題ないようです。これで、実店舗の小売店の chatbot が完全に機能するようになりました。次のラボでは、仮想エージェントのパフォーマンスをテストします。
9. 仮想エージェントをテストする
組み込みのシミュレータを使用して、仮想エージェントの会話をテストできます。シミュレータでフローをテストする利点は、フロー、ページ、パラメータ、(DTMF)イベントの概要を、シミュレータがフロー実行中に収集した内容に基づいて確認できることです。このような情報はエンドユーザーには表示されないため、統合で直接テストするよりもテストが容易になります。テストケースを作成して保存し、再利用することもできます。これは、フローを長期にわたって維持または編集する際に、変更によって以前の作業が破損しないようにするために非常に有用です。
以前に作成したテストケースをエクスポートしてインポートすることもできます。テストを Google Cloud Storage またはローカルに保存します。テストをエクスポートすると、Blob ファイルがダウンロードされます。シミュレータとテストケースの詳細については、シミュレータ / テストケースのドキュメントをご覧ください。
テストケースを作成する前に、まず仮想エージェントの残りの部分を完成させましょう。
カスタマーケア フローの作成
- [カスタマーケア] フローを開き、次のインテントの遷移を作成します。
ページ(フロー内) | [Routes] > [Intent] | [ルート] > [移行先] |
カスタマーケアの開始 |
| 送料 |
カスタマーケアの開始 |
| 払い戻し |
カスタマーケアの開始 |
| スワップ |
カスタマーケアの開始 |
| フローを終了する |
カスタマーケアの開始 |
| セッションを終了 |
- [配送] ページに次のエントリ フルフィルメントを作成します。
Shipping physical merchandise items can take up to 2 weeks.
Is there anything else I can help you with?
- [Refund] ページに次のエントリ フルフィルメントを作成します。
We offer free returns and refunds. We provide one free return label for each order. You can use it within 30 days from receiving your order. If your refund is accepted, we will refund the price you paid for your item back to your original payment method.
Is there anything else I can help you with?
- [交換] ページに次のエントリ フルフィルメントを作成します。
If you would like to change your item for a different one, please return your unwanted item and place a new order. If your refund is accepted, we will refund the price you paid for your item back to your original payment method.
Is there anything else I can help you with?
- [Start] ページを選択し、
redirect.end
インテントをタップします。次のフルフィルメントを作成します。Thank you for contacting G-Records! Have a nice day!
- [Start] ページを選択し、
redirect.home
インテントをタップします。次のパラメータ プリセットを作成します。restart = true
テストケースを作成する
- 画面の右側にある [エージェントをテストする] ボタンをクリックします。
シミュレータを初めて開くときは、エージェント環境とアクティブなフローを選択する必要があります。ほとんどの場合、下書き環境とデフォルトの開始フローを使用する必要があります。
- タイプ:
Hi
- 質問:
Which artists are signed with your label?
- 「
The Google Dolls
」と言ってください - 「
I am interested in buying a shirt
」と言ってください - 「
A t-shirt
」と言ってください - 「
Medium
」と言ってください - テストケースの保存ボタンをクリックします。シミュレータの上部(やり直し矢印とリセット ゴミ箱アイコンの横)にあります。
- 次の情報を指定します。
- テストケース名:
Buy Google Dolls t-shirt size M
- タグ: #catalog、#shirts、#t-shirt、#TheGoogleDolls
- [保存] をクリックします。
テストケースをさらに作成しましょう。
- まず、リセット(ゴミ箱)アイコンをクリックして現在のダイアログを消去します。
- 次のテストケースを作成します。
Alice Googler の T シャツを購入する:
>"Buy the Alice Googler t-shirt."
>"XL"
- テストケース名:
Buy the Alice Googler t-shirt
- タグ:
#catalog, #shirts, #t-shirt, #AliceGoogler
M サイズの T シャツを購入する:(アーティスト名は言及されていないが、バンドの概要、商品の概要、シャツとシャツのサイズのページはスキップする)
>"Buy a t-shirt size M"
>"The Google Fighters"
- テストケース名:
Buy a t-shirt size M
- タグ:
#catalog, #shirts, #t-shirt, #TheGoogleFighters
- 説明:(アーティスト名は言及されていないが、バンドの概要、商品の概要、シャツとシャツのサイズのページはスキップする)
Guns N' Roses の音楽を購入する(バンドの概要と商品の概要ページはスキップされます)
>"Purchase music of G's N' Roses"
>"Live"
>"CD"
- テストケース名:
Purchase music of G's N' Roses
- タグ:
#catalog, #music, #CD, #GsNRoses, #live
- 説明:(バンドの概要とプロダクトの概要ページはスキップされます)
料金情報を確認する:
>"Which products"
>"Shirts"
>"What's the price difference?"
>"Longsleeve"
>"What does it cost?"
>"M"
>"The Google Dolls"
>"No"
>"Which bands"
>"The Gooo Fighters"
>"Music"
>"How much does it cost?"
>"Greatest Hits"
>"What's the price difference?"
>"Mp3"
>"No"
>"I want to buy the tour movie"
>"Alice Googler"
>"Yes"
- テストケース名:
Price info
- タグ:
#catalog, #music, #tourmovie, #shirts
- 説明: 会話のさまざまなポイントで価格情報をテストする
事前録画されたテストケースをテストする
- 左側の Dialogflow メインメニューで、[管理] > [テストケース] を選択します。
- すべてのテストケースを選択し、表の上にある [実行] ボタンをクリックします。
Dialogflow CX は、選択したすべてのテストケースを「ゴールデン テストケース」として保存された録音に対して実行します。結果が保存した内容と同じであれば、テストは合格です。- フロー内で何かが変更された場合(ページが正しく設定されていない、またはインテントのページが間違っているなど)、テストは失敗します。
- シミュレータで次の質問をします。
How long will shipping take?
- 結果をメモし、テストケースを
Shipping
として保存し、タグ#shipping
を付けます。 - [管理] > [テストケース] パネルに移動し、グリッドの右上にある [実行] ボタンを押して、
Shipping
テストケースのみを実行します。
このテストは合格するはずです。
- カスタマーケア フローに移動し、[開始] ページを選択して、[ルート] ヘッダーをクリックします。
すべてのルートが表示されたグリッドの画面が表示されます。
redirect.shipping.info route
を削除する- [管理] > [テストケース] パネルに移動し、グリッドの右上にある [実行] ボタンを押して、
Shipping
テストケースのみを実行します。
このテストは失敗します。
- 失敗したテストをクリックすると、失敗の詳細を確認できます。
この場合、テストは失敗し、次のエラー メッセージが表示されます。
Page: Page mismatch:
Expected: Shipping
Actual: Start Page
これは、そのページがフロー内に存在しなくなったためです。Shipping
ページが表示されるはずが、Start
ページから移動しなかった。(または、エンドユーザーにフォールバック メッセージが表示されます)。
つまり、これは検出できなかったリクエストであり、偽陰性のテスト結果です。テストは失敗しました。[配送] ページが表示されるはずが、何も起こらない、またはフォールバック メッセージが表示される。
- カスタマーケア フローに移動し、[開始] ページに
redirect.shipping.info
をインテント ルートとして追加します。忘れずに [配送] ページに移動して [保存] をクリックしてください。 - シミュレータで次のテストケース
I want to swap my item
を記録し、このテストケースをSwapping
#swapping
として保存します。 - [管理] > [Intents] > [redirect.refund.info] を開き、次のトレーニング フレーズを追加します。
I want to swap this item for a refund
このトレーニング フレーズがないと、ユーザーが払い戻しのために商品の変更をリクエストすると、redirect.swapping.info インテントにヒットします。しかし、Google は商品の変更に関する情報ではなく、払い戻しに関する情報を提供したいのです。
- シミュレータで次のゴールデン テストケース
I want to swap this item for a refund
を作成し、このテストケースをSwap for Refund
#refund
として保存します。 - [管理] > [インテント] > [redirect.refund.info] インテントに戻り、
I want to swap this item for a refund
行を削除します。 - [管理] > [テストケース] に戻り、[Swap for Refund] テストケースを選択して実行します。
最新のテストが失敗し、次のエラー メッセージが表示されました。
If you would like to change your item for a different one, please return your unwanted item and place a new order. If your refund is accepted, we will refund the price you paid for your item back to your original payment method.`
Is there anything else I can help you with?
Page: Page mismatch:
Expected: Refund
Actual: Swapping
つまり、これはリクエストが誤って認識された偽陽性のテスト結果です。テストは失敗しました。[払い戻し] ページが表示されるはずが、[交換] ページが表示された。
対象範囲
Dialogflow CX では、テストのカバレッジは、特定のテストスイートを実行するときに仮想エージェントのダイアログ(ページとインテント)が実行される程度を示す指標です。テストカバレッジ(割合)が高いバーチャル エージェントは、テスト中に実行されたダイアログが多いため、テストカバレッジが低いバーチャル エージェントと比較して、検出されていないバグ(理解されていないリクエストの見落としなど)が含まれている可能性が低くなります。
- すべてのテストケースのテスト カバレッジ レポートを表示するには、[Coverage] をクリックします。
- [切り替え] タブをクリックします。
すべてのページ遷移のテスト カバレッジが表示されます。
- [Intents] タブをクリックします。
すべてのインテントのテストカバレッジが表示されます。
これで、小売店ボットの完全な実例を構築してテストできました。次のラボページに移動して、結論を確認し、便利なリファレンスを確認しましょう。
10. まとめ
Dialogflow CX は、チャットボットや音声ボットなどの仮想エージェントを作成するための会話型 AI プラットフォーム(CAIP)です。Dialogflow CX を使用すると、ビジュアル bot ビルダー、再利用可能なインテント、マルチターンの会話に対応する機能により、エンタープライズ レベルの会話エクスペリエンスの構築を加速できます。
この Codelab では、実店舗のバーチャル エージェントを構築する方法を学びました。以下のコンセプトに対応しました。
- フロー
- パラメータ、カスタム エンティティ、システム エンティティ
- ページ
- インテント ルートや条件ルートなどの状態ハンドラ
- 静的フルフィルメント メッセージと条件付きレスポンス
- フォールバック インテント
- シミュレータ、テストケース、カバレッジ
参照
Dialogflow CX について詳しくは、以下のブログとドキュメントをご覧ください。