/// <summary>
        /// Handles the shard map publishing request and processes it against the shard set driver.
        /// </summary>
        /// <param name="request">The shard map publishing request.</param>
        /// <param name="queue">The queue.</param>
        public static void HandleShardMapPublishingRequest(ShardMapPublishingRequest request,
                                                           IShardSetActionQueue queue)
        {
            var shardSetConfig = GetCurrentShardSetConfig(request.ShardSetName);

            Action <ShardMapPublishingRequest> process =
                x =>
            {
                ProcessShardMapPublishingRequest(x, shardSetConfig);

                if (!request.ShouldUpdateShardMap)
                {
                    return;
                }

                PublishRangeMap(shardSetConfig.ShardSetName, request.CurrentShardMapID, request.NewShardMapID);
            };

            Action <ShardMapPublishingRequest> complete =
                x =>
            {
                CompleteShardMapPublishingRequest(shardSetConfig, x);
                queue.SendQueueProcessingEvent(GetCompletionMessage("ShardMapPublishingRequest", x));
            };

            Action <ShardMapPublishingRequest> error =
                x => queue.SendQueueProcessingEvent(GetErrorMessage("ShardMapPublishingRequest", x));

            request.Process(process, complete, error);
        }
        /// <summary>
        /// Handles the shard deletion request and processes it against the shard set driver.
        /// </summary>
        /// <param name="request">The shard deletion request.</param>
        /// <param name="queue">The queue.</param>
        public static void HandleShardDeletionRequest(ShardDeletionRequest request,
                                                      IShardSetActionQueue queue)
        {
            var config = GetCurrentShardSetConfig(request.ShardSetName);
            var driver = GetShardSetDriver(config);

            Action <ShardDeletionRequest> process = (x =>
            {
                var shard = new RangeShard
                {
                    Catalog = request.Catalog,
                    ServerInstanceName = request.ServerInstanceName,
                };
                //Do not delete the database if it is populated for now, as the move shardlet code could error leaving shardlets behind
                //TODO: Allow this to delete populated databases, by orchestrating that a failed shardlet move stops this step for that database.
                driver.DeleteShard(shard, config);
            });

            Action <ShardDeletionRequest> complete =
                (x => queue.SendQueueProcessingEvent(GetCompletionMessage("ShardDeletionRequest", x)));
            Action <ShardDeletionRequest> error =
                (x => queue.SendQueueProcessingEvent(GetErrorMessage("ShardDeletionRequest", x)));

            request.Process(process, complete, error);
        }
        /// <summary>
        /// Handles the shardlet move request from tje request queue.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <param name="queue">The queue.</param>
        /// <param name="uniqueProcessID">A unique process identifier that can be set to maintain state between moves.</param>
        public static void HandleShardletMoveRequest(ShardletMoveRequest request, IShardSetActionQueue queue,
                                                     Guid uniqueProcessID)
        {
            Action <ShardletMoveRequest> process =
                x =>
            {
                var shardlet         = Load(x.ShardSetName, x.ShardingKey);
                var destinationShard =
                    new RangeShard
                {
                    Catalog            = x.DestinationCatalog,
                    ServerInstanceName = x.DestinationServerInstanceName
                };

                shardlet.MoveToShard(destinationShard, x.Pin, x.DeleteOnMove, uniqueProcessID);
            };

            Action <ShardletMoveRequest> complete =
                x =>
            {
                var message = GetCompletionMessage("ShardletMoveRequest", x);
                queue.SendQueueProcessingEvent(message);
            };

            Action <ShardletMoveRequest> error =
                x =>
            {
                var message = GetErrorMessage("ShardletMoveRequest", x);
                queue.SendQueueProcessingEvent(message);
            };

            request.Process(process, complete, error);
        }
        /// <summary>
        /// Handles the shard creation request and processes it against the shard set driver.
        /// </summary>
        /// <param name="request">The shard creation request.</param>
        /// <param name="queue">The queue.</param>
        public static void HandleShardCreationRequest(ShardCreationRequest request,
                                                      IShardSetActionQueue queue)
        {
            var config = GetCurrentShardSetConfig(request.ShardSetName);
            var driver = GetShardSetDriver(config);

            Action <ShardCreationRequest> process = (x =>
            {
                var shard = new RangeShard
                {
                    Catalog = request.Catalog,
                    ServerInstanceName = request.ServerInstanceName,
                };

                driver.CreateShard(shard, config);
            });

            Action <ShardCreationRequest> complete =
                (x => queue.SendQueueProcessingEvent(GetCompletionMessage("ShardCreationRequest", x)));
            Action <ShardCreationRequest> error =
                (x => queue.SendQueueProcessingEvent(GetErrorMessage("ShardCreationRequest", x)));

            request.Process(process, complete, error);
        }
 public ScaleOutQueueManager(IShardSetActionQueue shardSetActionQueue)
 {
     _shardSetActionQueue = shardSetActionQueue;
 }