[英]Factory Pattern in ASP.Net Core
I'm working on Worker Service in .Net Core
and Added DDD to it.我正在Worker Service in .Net Core
并为其添加了 DDD。 In the Application Layer, I have created a Factory Pattern to Pick a specific Message Handler to handle different Kafka Topics.在应用层,我创建了一个工厂模式来选择一个特定的消息处理程序来处理不同的 Kafka 主题。 This approach is working fine.这种方法运行良好。 But, wanted to know is it the right way of implementing it?但是,想知道这是实现它的正确方法吗? I am a bit confused about injecting constructor parameters in MessageFactory
我对在MessageFactory
中注入构造函数参数有点困惑
public interface IMessageFactory
{
IMessageHandler CreateMessage(string topicName);
}
Implementation of Factory Method工厂方法的实现
public class MessageFactory: IMessageFactory
{
private readonly ILogger<MessageFactory> _logger;
private readonly IOneRepository _oneRepository;
private readonly ITwoRepository _twoRepositoty;
public MessageFactory(ILogger<MessageFactory> logger,
IOneRepository oneRepository,
ITwoRepository twoRepositoty)
{
_logger = logger;
_oneRepository = oneRepository;
_twoRepositoty = twoRepositoty;
}
public IMessageHandler CreateMessage(string topicName)
{
switch (topicName.ToUpper())
{
case KafkaConstants.OneMaster:
return new OneMessageHandler(_logger, _oneRepository );
case KafkaConstants.TwoMaster:
return new TwoMessageHandler(_logger, _twoRepositoty );
default:
return null;
}
}
}
}
Individual Handlers个人处理程序
public class OneMessageHandler : IMessageHandler
{
private readonly ILogger<MessageFactory> _logger;
private readonly IOneRepository _oneRepository;
public OneMessageHandler (ILogger<MessageFactory> logger,
IOneRepository _oneRepository)
{
_logger = logger;
_oneRepository = oneRepository;
}
public async Task<bool> ProcessMessage(string message)
{
..........
}
}
public class TwoMessageHandler : IMessageHandler
{
private readonly ILogger<MessageFactory> _logger;
private readonly ITwoRepository _twoRepository;
public TwoMessageHandler(ILogger<MessageFactory> logger,
ITwoRepository twoRepository)
{
_logger = logger;
_twoRepository = twoRepository;
}
public async Task<bool> ProcessMessage(string message)
{
..........
}
}
Worker Service工人服务
public class Worker: BackgroundService
{
private readonly IMessageFactory _messageFactory;
public Worker(IMessageFactory messageFactory)
{
_messageFactory = messageFactory;
}
IMessageHandler messageHandler = _messageFactory.CreateMessage("OneMaster");
messageHandler.ProcessMessage(message_from_kafka_response));
}
Dependency Injection依赖注入
services.AddTransient<IMessageFactory, MessageFactory>();
Well, I would make everything injectable, so I can register it like this (all classes self explanatory) without using factory and just using container:好吧,我会让所有东西都可注入,所以我可以像这样注册它(所有类都自我解释),而不使用工厂,只使用容器:
container.RegisterSingleton<IHostedService>(x =>
new RepeatBackgroundWorker(
repeatInterval,
new MessageHandler<TKey, TPayload>( //this can also be just something like void IWorker.RunAsync(cancellationToken)
new KafkaMessageProducer<TKey, TPayload>(/*settings like name, consumer group and connection settings*/),
x.GetByKey<IMessageProcessor<TKey, TPayload>>(/*processor name*/))));
//RepeatBackgroundWorker - it will generally repeat some background worker
//MessageHandler - it will consume message, process it, set new offset and until message producer enumerable reaches the end (end of queue)
//KafkaMessageProducer - it will just return something like IAsyncEnumerable<Message<TKey, TPayload>>
//IMessageProcessor - it will be your processor
as you see you have mutiple benefits:如您所见,您有多种好处:
PS I didnt implement all classes, because it depends on business requirements PS我没有实现所有类,因为它取决于业务需求
PS2 This is basically what I use in production to squeeze kafka performance, get all logs into kibana and all metrics (message timestamp is particullary useful when you have spikes and want to rebalance up/down) to prometheus+grafana from all sources out of the box. PS2这基本上是我在生产中使用来挤压 kafka 性能,将所有日志放入 kibana 和所有指标(当您遇到峰值并想要重新平衡向上/向下时,消息时间戳特别有用)从所有来源到 prometheus+grafana盒子。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.