IBM Cloud Docs
API を使用したダイアログの変更

API を使用したダイアログの変更

REST API は、プログラムによるダイアログの変更をサポートします。 /dialog_nodes API を使用して、ダイアログ・ノードを作成、削除、または変更できます。

ダイアログは、相互接続されたノードのツリーであり、有効であるためには特定の規則に準拠する必要があります。 ダイアログ・ノードに変更を加えると、他のノードやダイアログの構造にカスケード効果が生じる可能性があります。 /dialog_nodes API を使用してダイアログを変更する前に、変更がダイアログの残りの部分に与える影響を理解しておく必要があります。 現行ダイアログのバックアップ・コピーを作成できます。詳しくは、 データのバックアップとリストア を参照してください。

有効なダイアログは必ず以下の基準を満たしています。

  • ダイアログ・ノードごとに固有 ID があります (dialog_node プロパティー)。

  • 下位ノードはその親ノードを認識しています (parent プロパティー)。 一方、親ノードはその子を認識していません。

  • ノードは、その直前の兄弟が存在すればそれを認識しています (previous_sibling プロパティー)。 親を共有するすべての兄弟はリンク・リストを形成し、各ノードは前のノードを指します。

  • 最初の兄弟になることができるのは、親の 1 つの子のみです (つまり、その previous_sibling はヌルです)。

  • ノードは、異なる親の子である直前の兄弟を指すことはできません。

  • 直前の同じ兄弟を 2 つのノードが指すことはできません。

  • ノードは、次に実行される別のノードを指定できます ( next_step プロパティー)。

  • ノードは、自身の親にも自身の兄弟にもなれません。

  • ノードには、以下のいずれかの値を含むタイプ・プロパティーが必要です。 タイプ・プロパティーが指定されていない場合、タイプは standard になります。

    • event_handler: フレーム・ノードまたは個々のスロット・ノードに対して定義されたハンドラー。

    ツールから、スロット付きノードの**「ハンドラーの管理 (Manage handlers)」**リンクをクリックして、フレーム・ノードのハンドラーを定義できます。 (スロット・レベルのイベント・ハンドラーはツールのユーザー・インターフェースに表示されませんが、API を使用して定義できます。)

    • frame: slot タイプの子ノードを 1 つ以上持つノード。 必要なすべての子スロット・ノードに情報が取り込まれるまで、サービスはフレーム・ノードを終了できません。

    フレーム・ノード・タイプは、ツールではスロット付きのノードとして表されます。 スロットを含むノードは、タイプ =frameのノードとして表されます。これは各スロットの親ノードであり、slotタイプの子ノードとして表されます。

    • response_condition: 条件付き応答。

    ツールでは、1 つのノードに 1 つ以上の条件付き応答を追加できます。 定義した各条件付き応答は、基礎 JSON では、response_condition タイプの個々のノードとして表されます。

    • slot: frame タイプのノードの子ノード。

    このノード・タイプは、単一ノードに追加される複数のスロットの 1 つとしてツールに表示されます。 その単一ノードは、JSON では frame タイプの親ノードとして表されます。

    • standard: 標準的なダイアログ・ノード。 これがデフォルトのタイプです。
  • 同じ親ノードを持つタイプ slot のノードの場合、兄弟順序 ( previous_sibling プロパティーで指定) は、スロットが処理される順序を反映します。

  • slot タイプのノードには、frame タイプの親ノードが必要です。

  • frame タイプのノードには、slot タイプの子ノードが 1 つ以上必要です。

  • response_condition タイプのノードには、standard または frame タイプの親ノードが必要です。

  • response_condition および event_handler タイプのノードは、子ノードを持つことができません。

  • event_handler タイプのノードには、ノード・イベントのタイプを示す以下のいずれかの値を含む event_name プロパティーも必要です。

    • filled: スロットの 「チェック対象 (Check for)」 フィールドに指定されている条件を満たす値をユーザーが指定し、スロットが入力された場合の対処方法を定義します。 この名前のハンドラーは、Found 条件をスロットに定義した場合にのみ存在します。
    • focus: スロットに必要な情報を提供するようユーザーにプロンプトを出す質問を定義します。 この名前のハンドラーは、スロットが必要な場合にのみ存在します。
    • generic: スロットまたはスロット付きノードの入力中に、ユーザーが尋ねる可能性がある無関係の質問に対処する条件を定義します。
    • input: スロットに情報を取り込むためにユーザーから収集した値を持つコンテキスト変数を含むように、メッセージ・コンテキストを更新します。 この名前のハンドラーは、フレーム・ノードのスロットごとに存在する必要があります。
    • nomatch: スロット・プロンプトに対するユーザーの応答に有効な値が含まれていない場合の処理を定義します。 この名前のハンドラーは、Not Found 条件をスロットに定義した場合にのみ存在します。

    以下の図は、名前付きイベントごとにトリガーされるコードを定義するツール・ユーザー・インターフェース内の場所を示しています。

    名前付きイベント・ハンドラーによってトリガーされるコードが作成される UI ロケーション
    イベント・ハンドラー

  • イベント名が event_handlergeneric タイプのノードは、slot または frame タイプの親を持つことができます。

  • イベント名が event_handlerfocusinput、または fillednomatch タイプのノードには、slot タイプの親が必要です。

  • 同じ event_name を持つ複数の event_handler が同じ親ノードに関連付けられている場合、兄弟の順序は、イベント・ハンドラーが実行される順序になります。

  • 同じ親スロット・ノードを持つ event_handler ノードの実行順序は、ノード定義の配置に関係なく、同じです。 event_name による次の順序で、イベントはトリガーされます。

    1. フォーカス
    2. input
    3. filled
    4. generic*
    5. nomatch
    • event_name generic を持つ event_handler がこのスロットまたは親フレームに定義されている場合は、充てんされた event_handler ノードと nomatch event_handler ノードの間で実行されます。

以下の例は、さまざまな変更が加えられることによって連鎖的に変化が起こる場合に、それがどのように生じるかを示しています。

ノードの作成

次のシンプルなダイアログ・ツリーを考えてみます。

「例」ダイアログ
「例」ダイアログ

次の本体を含む POST 要求を /dialog_nodes に行うことによって、新しいノードを作成できます。

{
  "dialog_node": "node_8"
}

ダイアログは次のようになります。

ダイアログ 2 の例
ダイアログ 2 の例

node_8 は、parent の値も previous_sibling の値も指定せずに作成されたので、ダイアログ内の最初のノードになりました。 サービスは、 node_8 の作成に加えて、 node_1 も変更して、その previous_sibling プロパティーが新規ノードを指すようにしました。

次のように親と直前の兄弟を指定することにより、ダイアログ内の他の場所にノードを作成できます。

{
  "dialog_node": "node_9",
  "parent": "node_2",
  "previous_sibling": "node_5"
}

parent および previous_node に指定する値は、以下の有効な値でなければなりません。

  • 両方の値とも既存のノードを参照していなければなりません。
  • 指定した親は、直前の兄弟の親と同じでなければなりません (直前の兄弟に親がない場合は null)。
  • 親を response_condition または event_handler タイプのノードにすることはできません。

結果のダイアログは次のようになります。

ダイアログ 3 の例
ダイアログ 3 の例

node_9 を作成することに加えて、サービスは previous_siblingnode_6* の * プロパティーを自動的に更新して、新しいノードを指すようにします。

異なる親へのノードの移動

以下の本文を含む POST /dialog_nodes/node_5 メソッドを使用して、 node_5 を別の親に移動します。

{
  "parent": "node_1"
}

parent に指定する値は、次のとおり有効でなければなりません。

  • 既存のノードを参照していなければなりません。
  • 変更されるノードを参照していてはなりません (ノードはそれ自体の親であってはなりません)。
  • 変更されるノードの子孫を参照してはなりません。
  • response_condition または event_handler タイプのノードを参照していてはなりません。

この結果、次のような構造に変わります。

ダイアログ 4 の例
ダイアログ 4 の例

ここでいくつかのことが起こりました。

  • node_5 がその親に移動したとき、node_7 もそれと一緒に移動しました (parentnode_7** の ** 値が変わらなかったため)。 ノードを移動すると、そのノードのすべての子孫はそのノードに付き添います。
  • previous_siblingnode_5** の ** 値を指定しなかったので、このノードが node_1 の下の最初の兄弟になりました。
  • previous_siblingnode_4** の ** プロパティーが node_5 に更新されました。
  • node_9previous_sibling プロパティーは、 node_2 の下の最初の兄弟になったため、 null に更新されました。

兄弟の並べ直し

ここで、以下の本体を持つ POST /dialog_nodes/node_5 メソッドを使用して、 node_5 を最初の兄弟ではなく 2 番目の兄弟として設定します。

{
  "previous_sibling": "node_4"
}

previous_sibling を変更する場合、新しい値は次のとおり有効でなければなりません。

  • 既存のノードを参照していなければなりません。
  • 変更されるノードを参照することはできません (ノードをそれ自体の兄弟にすることはできません)。
  • 同じ親の子を参照していなければなりません (すべての兄弟に同じ親がなければなりません)。

次のように構造が変わります。

ダイアログ 5 の例
ダイアログ 5 の例

Node_7 は、その親のままです。 さらに、 node_4 が変更され、その previous_siblingnull になりました。これは、これが現在最初の兄弟であるためです。

ノードの削除

DELETE /dialog_nodes/node_1 メソッドを使用して、 node_1 を削除します。

結果は以下のようになります。

ダイアログ 6 の例
ダイアログ 6 の例

Node_1node_4node_5、および node_7 がすべて削除されました。 ノードを削除すると、そのノードのすべての子孫も削除されます。 したがって、ルート・ノードを削除すると、ダイアログ・ツリーのブランチ全体が削除されます。 削除されたノードへの他の参照 (next_step 参照など) はすべて、null に変更されます。

さらに、node_2 が更新されて、その新しい直前の兄弟として node_8 を指すようになります。

ノードの名前変更

以下の本体を持つ POST /dialog_nodes/node_2 メソッドを使用して、 node_2 の名前を変更します。

{
  "dialog_node": "node_X"
}

ダイアログ 7 の例
ダイアログ 7 の例

ダイアログの構造は変更されませんでしたが、変更された名前を反映するように複数のノードが変更されました。

  • parentnode_9** と node_6 の ** プロパティー
  • previous_siblingnode_3** の ** プロパティー

削除されたノードへの他の参照 (next_step 参照など) もすべて変更されます。