gpt4 book ai didi

c# - Azure 聊天机器人中间件的依赖注入(inject)?

转载 作者:太空狗 更新时间:2023-10-29 17:58:51 25 4
gpt4 key购买 nike

我正在使用 Azure 机器人服务和 QnAMaker 开发一个新的聊天机器人。我们正在使用 BotBuilder 中间件(包括自定义中间件)来定制机器人行为。

其中一个中间件将调用 Azure 函数,我想将新的 HttpClientFactory 功能与自定义中间件一起使用 - 但这需要依赖项注入(inject)。

如何像使用常规 .NET Core 中间件一样在 BotBuilder 中间件中使用依赖注入(inject)?

当您查看 Startup.cs 中的机器人配置时,您可以看到它如何要求您新建所有机器人依赖项:

services.AddHttpClient<MyFunctionClient>(client =>
{
client.BaseAddress = new Uri(mySettings.GetValue<string>("myFunctionUrl"));
client.DefaultRequestHeaders.Add("x-functions-key", mySettings.GetValue<string>("myFunctionKey"));
});

services.AddBot<QnAMakerBot>(options =>
{
options.CredentialProvider = new ConfigurationCredentialProvider(Configuration);

options.ConnectorClientRetryPolicy = new RetryPolicy(
new BotFrameworkHttpStatusCodeErrorDetectionStrategy(),
3,
TimeSpan.FromSeconds(2),
TimeSpan.FromSeconds(20),
TimeSpan.FromSeconds(1));

var middleware = options.Middleware;
middleware.Add(new ConversationState<ChatLog>(new MemoryStorage()));
middleware.Add(new MyCustomMiddleware()); // <- I want to inject a typed HttpClient here

//... etc. ....

是否有不同的方法来配置允许依赖项注入(inject)的机器人?

如果 MyCustomMiddleware 在其构造函数中需要类型化的 HttpClient,我必须在此处创建一个新实例,因此我无法获得 DI 和我刚刚设置的配置。

最佳答案

虽然我不是服务定位器模式的粉丝,但机器人配置的当前设计并不是非常依赖注入(inject)友好。

利用 bot 中间件设置方式的性质,但必须在启动期间提供新实例,我想出了以下变通办法。

public class BotMiddlewareAdapter<TMiddleware> : IMiddleware
where TMiddleware : IMiddleware {
private readonly Lazy<TMiddleware> middleware;

public BotMiddlewareAdapter(IServiceCollection services) {
middleware = new Lazy<TMiddleware>(() =>
services.BuildServiceProvider().GetRequiredService<TMiddleware>());
}

public Task OnTurn(ITurnContext context, MiddlewareSet.NextDelegate next) {
return middleware.Value.OnTurn(context, next);
}
}

它将 IServiceCollection 作为显式依赖项,并推迟服务提供者的创建和工厂委托(delegate)中实际中间件的最终解析。

然后可以使用

middleware.Add(new BotMiddlewareAdapter<MyCustomMiddleware>(services));

当调用适配器时,它会在初始调用时延迟解析预期的中间件,然后调用它。

事实上,您可以更进一步并将其转换为扩展方法

public static class BotBuilderMiddlewareExtension {
public static void Add<TMiddleware>(this IList<IMiddleware> middleware, IServiceCollection services)
where TMiddleware : IMiddleware {
middleware.Add(new BotMiddlewareAdapter<TMiddleware>(services));
}
}

这简化了设置

middleware.Add<MyCustomMiddleware>(services);

关于c# - Azure 聊天机器人中间件的依赖注入(inject)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50440446/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com