예제 #1
0
        internal static void Perform <TCommand>(this IAggregateRoot aggregate, TCommand command)
        {
            var subscription = AggregateInvokersCache.GetWhenMethod(aggregate.GetType(), command.GetType());

            if (subscription == null)
            {
                throw new InvalidOperationException("Aggregate can't perform command.");
            }

            if (aggregate.Status == RootStatus.New && !subscription.IsConstructor)
            {
                throw new InvalidOperationException("Attempting to apply a command to non existed aggregate.");
            }

            if (aggregate.Status != RootStatus.New && subscription.IsConstructor)
            {
                throw new InvalidOperationException("Attempting to create existed aggregate.");
            }

            if (aggregate.Status == RootStatus.Archived)
            {
                throw new InvalidOperationException("Aggregate is archived.");
            }

            subscription.Invoker(aggregate, command);

            if (aggregate.Changes.Count < 1)
            {
                throw new InvalidOperationException($"Command '{command.GetType().AssemblyQualifiedName}' produced no events");
            }

            aggregate.Status = RootStatus.Alive;
            aggregate.Reel(aggregate.Changes);

            if (subscription.IsDestructor)
            {
                aggregate.Status = RootStatus.Archived;
            }
        }
예제 #2
0
        private static void ApplyOnState(this IAggregateRoot root, object evnt)
        {
            StateOnMethod subscription = AggregateInvokersCache.GetStateOnMethod(root.State.GetType(), evnt.GetType());

            subscription?.Invoker(root.State, evnt);
        }