Ardalis.SharedKernel icon indicating copy to clipboard operation
Ardalis.SharedKernel copied to clipboard

Support for HasDomainEventsBase in the DomainEventDispatcher

Open Patrick2607 opened this issue 10 months ago • 1 comments

I'm employing strongly typed Ids in my entities. Consequently, I'm unable to utilize DispatchAndClearEvents(). Instead, I can resort to DispatchAndClearEvents<TId>(). However, this requires manual definition of each entity which will become cumbersome for larger projects, for example:

public async Task SaveChangesAsync(CancellationToken cancellationToken = default)
{
    UpdateAuditableEntities();
    await dbContext.SaveChangesAsync(cancellationToken);
    await HandleDomainEvents<CustomerId>();
    await HandleDomainEvents<OrderId>();
    await HandleDomainEvents<OrderLineId>();
    await HandleDomainEvents<ProductId>();
    // etc.
}

private Task HandleDomainEvents<TId>() where TId : struct, IEquatable<TId>
{
    if (dispatcher is null)
        return Task.CompletedTask;

    EntityBase<TId>[] entitiesWithEvents = dbContext.ChangeTracker
        .Entries<EntityBase<TId>>()
        .Select(e => e.Entity)
        .Where(e => e.DomainEvents.Any())
        .ToArray();

    return dispatcher.DispatchAndClearEvents(entitiesWithEvents);
}

I was wondering why the current code is written with EntityBase in mind and not the underlying HasDomainEventBase? You would be able to define the following and omit the other two methods:

public async Task DispatchAndClearEvents(IEnumerable<HasDomainEventsBase> entitiesWithEvents)
{
    foreach (HasDomainEventsBase entity in entitiesWithEvents)
    {
        DomainEventBase[] events = entity.DomainEvents.ToArray();
        entity.ClearDomainEvents();
        foreach (DomainEventBase domainEvent in events)
        {
            await mediator.Publish(domainEvent).ConfigureAwait(false);
        }
    }
}

Correct? Or is the Id of the EntityBase necessary for the DbContext.ChangeTracker? If so, what would be a good approach here?

Patrick2607 avatar May 02 '24 15:05 Patrick2607