2017-08-24 47 views
2

我一直在與機器人框架玩耍,但我只是想知道如果我Autofac的使用使用使用context.Call時,正確的是()。我應該從RootDialog經過評級服務depency到ReviewDialog這樣的(如下圖),或者是有沒有更好的辦法?博特框架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

你這樣做的方式是完全有效的。看到另一個implementaiton請查看AlarmBot

的方式,你正在做的這通常是我如何在對話框中使用DI爲好。還有另一種方法可以使用上下文PrivateConversationData,ConversationDataUserData中的數據包在對話框之間傳遞數據/類,但是您的操作方式沒有任何問題