Domain driven design 事件处理程序是否应该被激活并遗忘

Domain driven design 事件处理程序是否应该被激活并遗忘,domain-driven-design,cqrs,Domain Driven Design,Cqrs,在处理程序处理命令操作后,我引发域事件。在某些情况下,事件处理程序失败是可以容忍的。我可以说,大多数事件处理程序都是这样,我希望所有事件处理程序都是可以容忍失败的 如果事件处理程序失败,我的操作是否应该失败,或者事件处理程序是否应该触发并忽略 例如,假设这是我引发事件的地方,正如您所看到的,来自eventHandler.Execute的潜在异常不会被处理 public void Publish<TEvent>(TEvent @event) where TEvent : IDomain

在处理程序处理命令操作后,我引发域事件。在某些情况下,事件处理程序失败是可以容忍的。我可以说,大多数事件处理程序都是这样,我希望所有事件处理程序都是可以容忍失败的

如果事件处理程序失败,我的操作是否应该失败,或者事件处理程序是否应该触发并忽略

例如,假设这是我引发事件的地方,正如您所看到的,来自
eventHandler.Execute
的潜在异常不会被处理

public void Publish<TEvent>(TEvent @event) where TEvent : IDomainEvent
{
    IEnumerable<IEventHandler<TEvent>> handlers = _lifetimeScope.GetService<IEnumerable<IEventHandler<TEvent>>>();
    var eventHandlers = handlers as IEventHandler<TEvent>[] ?? handlers.ToArray();
    if (eventHandlers.Any())
    {
        foreach (IEventHandler<TEvent> eventHandler in eventHandlers)
        {
            eventHandler.Execute(@event);
        }
    }
    else
    {
        throw new InvalidOperationException("No handler registered");
    }
}
public void Publish(TEvent@event),其中TEvent:IDomainEvent
{
IEnumerable handlers=_lifetimeScope.GetService();
var eventHandlers=作为IEventHandler[]??handlers.ToArray()的处理程序;
if(eventHandlers.Any())
{
foreach(事件处理程序中的IEventHandler事件处理程序)
{
eventHandler.Execute(@event);
}
}
其他的
{
抛出新的InvalidOperationException(“未注册处理程序”);
}
}
然而,我的愿望是拥有如下内容:

public void Publish<TEvent>(TEvent @event) where TEvent : IDomainEvent
{
    IEnumerable<IEventHandler<TEvent>> handlers = _lifetimeScope.GetService<IEnumerable<IEventHandler<TEvent>>>();
    var eventHandlers = handlers as IEventHandler<TEvent>[] ?? handlers.ToArray();
    if (eventHandlers.Any())
    {
        foreach (IEventHandler<TEvent> eventHandler in eventHandlers)
        {
            try
            {
                eventHandler.Execute(@event);
            }
            catch (Exception ex)
            {
                // log the expection
                // swallow it
            }
        }
    }
    else
    {
        throw new InvalidOperationException("No handler registered");
    }
}
public void Publish(TEvent@event),其中TEvent:IDomainEvent
{
IEnumerable handlers=_lifetimeScope.GetService();
var eventHandlers=作为IEventHandler[]??handlers.ToArray()的处理程序;
if(eventHandlers.Any())
{
foreach(事件处理程序中的IEventHandler事件处理程序)
{
尝试
{
eventHandler.Execute(@event);
}
捕获(例外情况除外)
{
//记录期望值
//吞下去
}
}
}
其他的
{
抛出新的InvalidOperationException(“未注册处理程序”);
}
}

我通常将事件放在持久化的发布/订阅系统上,然后从命令处理程序返回


通过这种方式,单个事件处理程序可以在不影响主系统或彼此的情况下失败。

我通常将事件放在持久化的发布/子系统上,然后从命令处理程序返回


这样,单个事件处理程序就可以在不影响主系统或彼此的情况下失败。

好的一点!我实际上倾向于这条路,因为另一条路似乎更脆弱,但如果是这样,还有另一种可能性:当任何事件发布操作失败时,操作是否失败?Goog发布/订阅系统应该是高可用的,但仍然有可能。如果事件失败,命令处理程序不会失败。事件是已经发生的事件,因此订阅者失败不会影响命令处理程序。这一点很好!我实际上倾向于这条路,因为另一条路似乎更脆弱,但如果是这样,还有另一种可能性:当任何事件发布操作失败时,操作是否失败?Goog发布/订阅系统应该是高可用的,但仍然有可能。如果事件失败,命令处理程序不会失败。事件是已经发生的事件,因此它不应该影响订阅服务器失败的命令处理程序。