2017-08-24 2 views
2

私はbotフレームワークで遊んでいましたが、context.Call()を使用しているときにAutofacの使用法が正しいかどうかは不思議でした。私は、RootDialogからRatingDialogへ評価サービスのdepencyをこのように渡すべきですか(下記参照)、より良い方法がありますか?BotフレームワークAutofac DI - context.Call()使用時の依存関係の受け渡し

context.Call(new ReviewDialog(_ratingService), ChildDialogHasCompleted); 

MessagesController

[BotAuthentication] 
    public class MessagesController : ApiController 
    { 
     /// <summary> 
     /// POST: api/Messages 
     /// Receive a message from a user and reply to it 
     /// </summary> 
     public async Task<HttpResponseMessage> Post([FromBody]Activity activity) 
     { 
      if (activity.Type == ActivityTypes.Message) 
      { 
       using (var scope = DialogModule.BeginLifetimeScope(Conversation.Container, activity)) 
       { 
        await Conversation.SendAsync(activity,() => scope.Resolve<IDialog<object>>()); 
       } 
      } 

      var response = Request.CreateResponse(HttpStatusCode.OK); 
      return response; 
     } 
    } 

RootDialog

[Serializable] 
public class RootDialog : LuisDialog<object> 
{ 
    private IRatingService _ratingService; 

    public RootDialog(IRatingService ratingService) 
    { 
     this._ratingService = ratingService; 
    } 

    [LuisIntent("Movie")] 
    public async Task IntentSearch(IDialogContext context, LuisResult result) 
    { 
     // Do stuff 

     context.Call(new ReviewDialog(_ratingService), ChildDialogHasCompleted); 
    } 

    private async Task ChildDialogHasCompleted(IDialogContext context, IAwaitable<object> msg) 
    { 
     context.Done(true); 
    } 
} 

ReviewDialog

[Serializable] 
public class ReviewDialog : IDialog 
{ 
    private IRatingService _ratingService; 

    public ReviewDialog(IRatingService ratingService) 
    { 
     this._ratingService = ratingService; 
    } 

    public async Task StartAsync(IDialogContext context) 
    { 
     PromptDialog.Choice(context, ProcessRating, new List<string> { "1", "2", "3", "4", "5" }, "Please select your rating"); 
    } 

    public async Task ProcessRating(IDialogContext context, IAwaitable<string> msg) 
    { 
     var message = await msg; 

     context.UserData.TryGetValue("SelectedMovieId", out int movieId); 

     var rating = int.Parse(message); 

     _ratingService.Save(movieId, rating); 

     await context.PostAsync("Thank you"); 

     context.Done(true); 
    } 
} 

グローバル

public class WebApiApplication : System.Web.HttpApplication 
{ 
    protected void Application_Start() 
    { 
     GlobalConfiguration.Configure(WebApiConfig.Register); 

     var builder = new ContainerBuilder(); 

     builder.RegisterType<RootDialog>() 
       .As<IDialog<object>>() 
       .InstancePerDependency(); 

     builder.RegisterType<RatingService>() 
       .Keyed<IRatingService>(FiberModule.Key_DoNotSerialize) 
       .AsImplementedInterfaces(); 

     builder.Update(Conversation.Container); 
    } 
} 

任意の助けいただければ幸いです。

答えて

2

これを行う方法はまったく有効です。別の実装を見るにはAlarmBot

あなたがこれをやっている方法は、一般的にどのように私はダイアログでもDIを使用しています。コンテキストPrivateConversationData,ConversationDataおよびUserDataの中のデータバッグを使用してダイアログ間でデータ/クラスを渡す別の方法がありますが、それを行う方法に何も問題はありません

関連する問題