BotFramework PrivateConversationData设置问题

时间:2018-06-20 03:33:35

标签: c# botframework

我们正在尝试在PrivateConversationData的{​​{1}}中保存一个简单的可序列化对象,并从Dialog的状态访问它

由于某种原因,在对话框中执行MessagesController后,我们将无法取回状态中存储的数据

Context.Done

对话框代码很简单

    public static async Task SetUserAsync<T>(IActivity activity, T botUser) where T : IBotUser
    {
        if (botUser != null)
        {
            using (var scope = DialogModule.BeginLifetimeScope(Conversation.Container, activity.AsMessageActivity()))
            {
                var botDataStore = scope.Resolve<IBotDataStore<BotData>>();
                var key = new AddressKey()
                {
                    BotId = activity.Recipient.Id,
                    ChannelId = activity.ChannelId,
                    UserId = activity.From.Id,
                    ConversationId = activity.Conversation.Id,
                    ServiceUrl = activity.ServiceUrl
                };

                var privateData = await botDataStore.LoadAsync(key, BotStoreType.BotPrivateConversationData, CancellationToken.None);
                privateData.SetProperty<T>(Keys.CacheBotUserKey, botUser);

                await botDataStore.SaveAsync(key, BotStoreType.BotPrivateConversationData, privateData, CancellationToken.None);
                await botDataStore.FlushAsync(key, CancellationToken.None);

            }
        }
    }

,在MessagesController.cs中,我们只是调用

    public override async Task ProcessMessageAsync(IDialogContext context, IAwaitable<IMessageActivity> result)
    {
        BotUser user = new BotUser { UserId = "user1" };
        await StateHelper.SetUserAsync(context.Activity, user);

        var userFromState = await StateHelper.GetUserAsync<BotUser>(context.Activity);
        Debug.WriteLine("Within dialog (after set) >" + userFromState?.UserId);

        context.Done<object>(null);
    }

在这种情况下,我们得到以下输出

      await Conversation.SendAsync(activity, () => new DummyDialog()).ConfigureAwait(false);

      var user = await StateHelper.GetUserAsync<BotUser>(activity);
      System.Diagnostics.Debug.WriteLine("Within MC (end) >" + user?.UserId);

有什么问题吗?

1 个答案:

答案 0 :(得分:1)

在加载对话框时,状态会随之加载,并且可以使用Context对象上的方法进行访问/保存。对话框完成后,状态将由SDK保留。如果您创建一个新的作用域,嵌套在对话框中,并尝试加载/保留状态:那么对话框状态将覆盖它。要解决此问题,可以在StateHelper中添加一个接受 IDialogContext 的方法,并在Dialog中使用该方法。