/// <summary>
        /// Schedules the specified command.
        /// </summary>
        /// <param name="scheduledCommand">The scheduled command.</param>
        /// <returns>
        /// A task that is complete when the command has been successfully scheduled.
        /// </returns>
        /// <exception cref="System.NotSupportedException">Non-immediate scheduling is not supported.</exception>
        public virtual async Task Schedule(IScheduledCommand <TAggregate> scheduledCommand)
        {
            if (scheduledCommand.Result is CommandDeduplicated)
            {
                return;
            }

            if (scheduledCommand.Command.CanBeDeliveredDuringScheduling() && scheduledCommand.IsDue())
            {
                if (!await PreconditionHasBeenMet(scheduledCommand))
                {
                    CommandScheduler.DeliverIfPreconditionIsMetSoon(
                        scheduledCommand,
                        Configuration.Current);
                }
                else
                {
                    // resolve the command scheduler so that delivery goes through the whole pipeline
                    await Configuration.Current.CommandScheduler <TAggregate>().Deliver(scheduledCommand);

                    return;
                }
            }

            if (scheduledCommand.Result == null)
            {
                throw new NotSupportedException("Deferred scheduling is not supported by the current command scheduler pipeline configuration.");
            }
        }
Example #2
0
        /// <summary>
        /// Schedules a command for asynchronous and, optionally, deferred delivery.
        /// </summary>
        /// <typeparam name="TCommand">The type of the command.</typeparam>
        /// <param name="command">The command.</param>
        /// <param name="due">The time when the command should be delivered. If this is null, the scheduler will deliver it as soon as possible.</param>
        /// <exception cref="System.ArgumentNullException">command</exception>
        protected void ScheduleCommand <TCommand>(TCommand command,
                                                  DateTimeOffset?due = null)
            where TCommand : class, ICommand <T>
        {
            if (command == null)
            {
                throw new ArgumentNullException("command");
            }

            var scheduled = CommandScheduler.CreateScheduledCommand <TCommand, T>(
                Id,
                command,
                due) as CommandScheduled <T>;

            RecordEvent(scheduled);
        }
        // TODO: (CommandSchedulerExtensions) combine with CommandScheduler class
        public static async Task <IScheduledCommand <TAggregate> > Schedule <TCommand, TAggregate>(
            this ICommandScheduler <TAggregate> scheduler,
            Guid aggregateId,
            TCommand command,
            DateTimeOffset?dueTime   = null,
            IEvent deliveryDependsOn = null)
            where TCommand : ICommand <TAggregate>
            where TAggregate : IEventSourced
        {
            if (aggregateId == Guid.Empty)
            {
                throw new ArgumentException("Parameter aggregateId cannot be an empty Guid.");
            }

            var scheduledCommand = CommandScheduler.CreateScheduledCommand <TCommand, TAggregate>(
                aggregateId,
                command,
                dueTime,
                deliveryDependsOn);

            await scheduler.Schedule(scheduledCommand);

            return(scheduledCommand);
        }