Chatbotの開発環境を整える
エミュレーターの使い方
作成したアプリケーションがChatbotとしてきちんと動作していることを、エミュレーターを使って確認してみましょう。スタートメニューから「botframework-emulator」を選択します。
「Enter your endpoint URL」をクリックして、ChatbotのWebアプリケーションPIとしてのURL「http:// localhost:3979」に「/api/messages」を追加した「http:// localhost:3979/api/messages」をエンドポイントURLとして入力します。この段階では「Microsoft App」の設定は不要なので、このまま「CONNECT」ボタンをクリックします。このとき右下のLogウィンドウに赤字でエラーが表示された場合はエンドポイントのURLやポートが間違っているか、ファイアウォールの設定でポートが許可されていない可能性がありますので、再度確認をしましょう。
では、早速Chatbotを使ってみましょう。Bot Applicationのテンプレートにあらかじめ作成されているサンプルアプリケーションは、ユーザーが入力した文字の文字数を返す簡単なものです。エミュレーター下部のテキストボックスに「こんにちは」と入力してEnterキーを押すか、右の入力ボタンをクリックしてメッセージを送ります。Chatbotアプリケーションから「『こんにちは』の文字数は5文字」との返事が返ってきます。この「メッセージを送る」と「答えが返ってくる」というのが、Chatbotアプリケーションの基本的な使い方となります。Chatbotアプリケーションは、軽量なデータ交換用フォーマットのJSONを使ってデータのやりとりを行っています。エミュレーターで入力したメッセージや、返答されたメッセージをクリックするとアプリケーションとやりとしているJSONの内容をDetailsウィンドウで確認することができるようになっています。エンドポイントURL横のメニューからは、チャットの初期化や、各種設定、テスト項目など必要に応じで利用することができます。
Chatbotの構成確認
サンプルのChatbotアプリケーションが問題なく動くことを確認したら、実際にChatbotの開発にとりかかりましょう。まずは、Visual Studioでファイル構成を確認してみましょう。Chatbotに特化した特徴としては、Controllersフォルダの中に、MessagesController.csファイルがあります。Chatbotとの会話はこのMessagesControllerクラスのPostメソッドがメッセージを受け取るところから始まります。
以下がMessagesControllerクラスのPostメソッドが、ユーザーからのメッセージを受け取る部分となります。if文でユーザーからの入力がメッセージ(ActivityTypes.Message)の場合、Dialogs.RootDialogクラスを作成して処理しています。
public async Task<HttpResponseMessage> Post([FromBody]Activity activity) { if (activity.Type == ActivityTypes.Message) { await Conversation.SendAsync(activity, () => new Dialogs.RootDialog()); } else { HandleSystemMessage(activity); } var response = Request.CreateResponse(HttpStatusCode.OK); return response; }
ユーザーからのメッセージを処理するDialogs.RootDialogクラス(RootDialog.cs)を見てみましょう(※ダイアログの詳細については次回解説します)。
最初に実行されるStartAsyncメソッドは、下にあるMessageReceivedAsyncメソッドを非同期で呼び出しています。MessageReceivedAsync メソッドではactivity.Textがユーザーから入力されたメッセージ文字列となります。入力されたメッセージの文字数をカウントして、context.PostAsyncでユーザーにメッセージを送り返しています。最後のcontext.Wait(MessageReceivedAsync)はメッセージを送り返した後、次にユーザーからのメッセージがあるまで待機しています。再びメッセージが入力されたら、MessageReceivedAsyncメソッドを実行します。これによって、ユーザーが何か文字を入力するたびに、毎回入力文字数を返す仕組みになっています。
public Task StartAsync(IDialogContext context) { context.Wait(MessageReceivedAsync); return Task.CompletedTask; } private async Task MessageReceivedAsync(IDialogContext context, IAwaitable<object> result) { var activity = await result as Activity; // calculate something for us to return int length = (activity.Text ?? string.Empty).Length; // return our reply to the user await context.PostAsync($"You sent {activity.Text} which was {length} characters"); context.Wait(MessageReceivedAsync); }
この、MessageReceivedAsyncメソッドを少しだけ変更して、ユーザーの入力メッセージをそのまま返す「オウム返しChatbot」に変えてみましょう。
private async Task MessageReceivedAsync(IDialogContext context, IAwaitable<object> result) { var activity = await result as Activity; await context.PostAsync($"「{activity.Text}」"); context.Wait(MessageReceivedAsync); }
このようにBot FrameworkのBot Builder SDK、Bot Applicationテンプレートを利用することで、ユーザーインターフェースや細かいロジックの仕様を考慮することなく、メッセージのやり取りの部分に集中して開発を行うことができるので、とても効率良く開発を進めることができます。
次回は、サンプルを用いたBot BuilderのDialog(ダイアログに)ついて解説します。