DDD Событие отправки связанных объектов - PullRequest
0 голосов
/ 31 октября 2018

Чтобы отключить профиль, связанный с пользователем, мы обычно

  • Загрузить пользователя из БД
  • Вызовите метод User.RemoveProfile(ProfileId).
  • В этом методе мы найдем указанный профиль в списке и затем вызовем метод Profile.Disable()
  • Внутри Profile.Disable() мы вызываем событие ProfileDisabled.
  • Мы совершенствуем пользователя + связанные сущности (в данном случае профили) в БД.

В настоящее время события хранятся внутри каждой сущности. Когда мы сохраняем пользователей в БД, мы проходим события под пользователем, а НЕ под всеми связанными профилями. В результате мы не отправляем события профиля, и они теряются.

Для справки: код, который мы используем для отправки события:

public abstract class Repository
{
    private readonly IMediator _mediator;

    protected Repository(IMediator mediator) => _mediator = mediator;

    // Future: Use EventStore for audit
    /* Bug: Disable profile raises an event stored at the profile level. When user gets updated only
       user events are dispatched. Profile events are lost... */
    protected async Task DispatchEventsAsync(Entity entity, CancellationToken token)
    {
        Ensure.Any.IsNotNull(entity, nameof(entity));
        await Task.WhenAll(entity.Events.Select(e => _mediator.Publish(e, token)));
        entity.SuppressEvents();
    }
}

Где Entity:

public interface IEntity { }

public abstract class Entity : IEntity
{
    private readonly List<DomainEvent> _events = new List<DomainEvent>();

    [NotMapped]
    public IReadOnlyList<DomainEvent> Events => _events.AsReadOnly();
    public bool HasEvents => _events.Any();

    protected void Emit(DomainEvent eventItem)
    {
        if (eventItem != null && !_events.Contains(eventItem))
            _events.Add(eventItem);
    }

    public void SuppressEvents() => _events.Clear();
}

Как видите, сущность НЕ знает о связанных сущностях. Это не способ получить доступ к связанным событиям.

Как бы справиться с этим делом? Означает ли это, что только Aggregate Root может вызывать события?

Thx Себ

1 Ответ

0 голосов
/ 01 ноября 2018

Я полагаю, у вас есть совокупность с двумя объектами: Пользователь и Профиль. И пользователь является AR.

События возникают, когда вы выполняете операцию с агрегатом, поэтому вы должны хранить их с AR.

В вашем случае это операция «user.removeProfile (profileId)», поэтому AR должен вызвать событие «ProfileRemovedFromUser» или что-то в этом роде.

ПРИМЕЧАНИЕ: ваш UL неоднозначен, так как вы используете слова удалить и отключить для одной и той же вещи. Вы должны использовать только одно слово.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...