我正在使用Microsoft Bot Framework v4.4.5,并且在Azure /本地主机模拟器中运行bot时,似乎存储在blob存储中的UserState在turncontext / bot中为空。 状态对象仅包含默认数据,即字符串为空。
使用内存存储时,一切正常,状态数据存储在内存中并包含正确的值。
在OnMember⚓Async_userState中,SaveChangesAsync将正确的状态保存到Blob存储中。
在OnTurnAsync中获取客户端始终会返回ClientProfile的默认值。
Startup.cs:
public void ConfigureServices(IServiceCollection services)
{
// Error handling
services.AddSingleton<IBotFrameworkHttpAdapter, BotErrorAdapter>();
const string storageContainer = "#Name#";
IStorage dataStore = new AzureBlobStorage("#ConnectionString#", storageContainer);
// Bot registration
services.AddBot<Bot>(options =>
{
options.CredentialProvider = new ConfigurationCredentialProvider(_configuration);
});
services.AddHttpClient();
var conversationState = new ConversationState(dataStore);
var userState = new UserState(dataStore);
services.AddSingleton(conversationState);
services.AddSingleton(userState);
services.AddSingleton(_configuration);
}
Bot.cs:
private IStorage _storage;
private BotState _userState;
public QnaBot(UserState userState, IStorage storage)
{
_userState = userState;
_storage = storage;
}
public override async Task OnTurnAsync(ITurnContext turnContext, CancellationToken cancellationToken = new CancellationToken())
{
await base.OnTurnAsync(turnContext, cancellationToken);
if (turnContext.Activity.Type is ActivityTypes.Message)
{
string userInput = turnContext.Activity.Text;
// LoadAsync doesn't seem to set any data
await _userState.LoadAsync(turnContext, false, cancellationToken);
var userStateAccessors = _userState.CreateProperty<ClientProfile>(nameof(ClientProfile));
var client = await userStateAccessors.GetAsync(turnContext, () => new ClientProfile());
await turnContext.SendActivityAsync($"You wrote {userInput}, Session {client.Name}");
await turnContext.SendActivityAsync($"Content {content}");
}
}
protected override async Task OnMembersAddedAsync(IList<ChannelAccount> membersAdded, ITurnContext<IConversationUpdateActivity> turnContext, CancellationToken cancellationToken)
{
var userStateAccessors = _userState.CreateProperty<ClientProfile>(nameof(ClientProfile));
var client = await userStateAccessors.GetAsync(turnContext, () => new ClientProfile());
if (!client.FetchedData)
{
client.Name = "MyName";
client.FetchedData = true;
await _userState.SaveChangesAsync(turnContext, false, cancellationToken);
}
await turnContext.SendActivityAsync($"Hi my name is {client.Name}");
}
ClientProfile.cs:
public class ClientProfile
{
public string Name { get; set; }
}
有人可以告诉我我在这里做错什么吗?
答案 0 :(得分:0)
您还需要用其他方法保存状态数据。就像您提到的是在OnMembersAddedAsync
方法(await _userState.SaveChangesAsync(turnContext, false, cancellationToken);
)中完成一样,您需要在OnTurnAsync
方法中进行。
当前正在加载userState数据:
await _userState.LoadAsync(turnContext, false, cancellationToken);
但是您需要在方法末尾保存它:
await base.OnTurnAsync(turnContext, cancellationToken);
if (turnContext.Activity.Type is ActivityTypes.Message)
{
string userInput = turnContext.Activity.Text;
// LoadAsync doesn't seem to set any data
await _userState.LoadAsync(turnContext, false, cancellationToken);
var userStateAccessors = _userState.CreateProperty<ClientProfile>(nameof(ClientProfile));
var client = await userStateAccessors.GetAsync(turnContext, () => new ClientProfile());
await turnContext.SendActivityAsync($"You wrote {userInput}, Session {client.Name}");
await turnContext.SendActivityAsync($"Content {content}");
//Add this line
await _userState.SaveChangesAsync(turnContext, false, cancellationToken);
}