VoiceXML でのプロンプト キューイング
VoiceXML では、プロンプトが実行されるたびに、実際にはキューに入れられます。VoiceXML インタープリターは、ユーザー入力を待っているとき、または終了するときにのみ、プロンプト キューをフラッシュ (再生) します。この動作については、VoiceXML W3C ドキュメントの「プロンプト キューイングと入力コレクション」セクションで詳しく説明されています。
あなたの場合、プロンプトは長い操作を行う前にキューに入れられ、次の対話中にのみ再生されます。これは典型的な状況であり、 Rivrに相当する従来の VoiceXML ソリューションがあります。
解決策 1: を使用してプロンプト キューを強制的にフラッシュするfetchaudio
VoiceXML の仕様では、プロンプト キューがフラッシュされると記載されています...
fetchaudio が指定されたリソース (ドキュメントなど) のフェッチをインタープリターが開始したとき。この場合、fetchaudio の前にキューに入れられたプロンプトが最後まで再生されます。次に、リソースを実際に取得する必要がある場合 (つまり、キャッシュ内で有効期限が切れていない場合)、fetchaudio は取得が完了するまで再生されます。
<submit>
したがって、プロンプトが確実に再生されるようにするには、長い操作の結果を取得するために使用される要素に fetchaudio を設定するだけです。「少々お待ちください」という効果です。メッセージが再生され、サーバーが結果を返すまで、fetchaudio で指定されたファイルがループ再生されます。通常、何かが処理されていることを示唆する音を使用します。
VoiceXML が操作の完了を待っている間に何も聞こえないようにする場合は、無音のオーディオ ファイルを提供できます。別のハックは、存在しないファイルを指定することです。これは、一部の VoiceXML プラットフォームで機能します。YMMV。
VoiceXML は次のようになります。
<?xml version="1.0" encoding="UTF-8"?>
<vxml version="2.1" xmlns="http://www.w3.org/2001/vxml">
<form id="form">
<block>
<prompt>Please wait a moment.</prompt>
<submit fetchaudio="/audio/fetch.wav" method="post" next="/long-operation" />
</block>
</form>
</vxml>
Rivr を使用すると、次のようになります。
context.getFetchConfiguration().getDocumentFetchConfiguration()
.setFetchAudio("/audio/fetch.wav");
Message message = new Message("wait-message",
new SpeechSynthesis("Please wait a moment."));
DialogueUtils.doTurn(message, context);
performLongOperation();
解決策 2: 人為的な待機状態を挿入する
プロンプト キューの再生を強制するもう 1 つの方法は、タイムアウトが 0 のダミーのインタラクションを作成することです。これは、インタープリターにメッセージを再生させることです。プロンプトでバージインを無効にするように注意する必要があります。そうしないと、DTMF 入力によってメッセージが中断される可能性があります。ダミー入力の例を次に示します。
<?xml version="1.0" encoding="UTF-8"?>
<vxml version="2.1" xmlns="http://www.w3.org/2001/vxml">
<form id="form">
<field name="dummy">
<property name="timeout" value="0ms" />
<grammar src="builtin:dtmf/digits" />
<prompt>Please wait a moment.</prompt>
<filled>
<goto nextitem="submit" />
</filled>
<noinput>
<goto nextitem="submit" />
</noinput>
<nomatch>
<goto nextitem="submit" />
</nomatch>
</field>
<block name="submit">
<submit fetchaudio="audio/fetch.wav" method="post" next="/long-operation" />
</block>
</form>
</vxml>
そして、これがRivrに相当するものです:
DtmfRecognition dummyRecognition = new DtmfRecognition(new GrammarReference("builtin:dtmf/digits"));
SpeechSynthesis message = new SpeechSynthesis("Please wait a moment.");
Interaction interaction = OutputTurns.interaction("wait-message")
.addPrompt(dummyRecognition, message).build();
DialogueUtils.doTurn(interaction, context);
performLongOperation();
このパターンをアプリケーションで再利用したい場合は、関数を作成できます。
private void forcePlayMessage(VoiceXmlDialogueContext context,
String messageName,
AudioItem... audioItems)
throws Timeout, InterruptedException {
DtmfRecognition dummyRecognition = new DtmfRecognition(new GrammarReference("builtin:dtmf/digits"));
Interaction interaction = OutputTurns.interaction(messageName)
.addPrompt(dummyRecognition, audioItems).build();
DialogueUtils.doTurn(interaction, context);
}
操作が非常に長い場合は、Java クラスを使用してリクエストをバックグラウンドで処理するのが賢明な場合がありFutureTask
ます。これにより、ブロックする代わりに、ダイアログが X 秒ごとに発信者にメッセージを送信できるようになります。performLongOperation()