/// <summary>
        ///     Builds the starting and final blocks of the dataflow.
        /// </summary>
        IDataflowBuilderBuildResult <TStart, TOutput> IDataflowBuilder <TStart, TOutput> .Build()
        {
            ITargetBlock <TStart> starting_block;

            var current_block = this.CreateBlock();

            if (this.previousBuilder != null)
            {
                var previous_build_result = this.previousBuilder.Build();

                starting_block = previous_build_result.StartingBlock;
                previous_build_result.FinalBlock.LinkWithCompletionPropagation(current_block);
            }
            else
            {
                starting_block = current_block as ITargetBlock <TStart>;
                if (starting_block == null)
                {
                    throw new InvalidOperationException(string.Format("Block {0} can not be casted to the type of the starting block {1}.",
                                                                      current_block.GetType(),
                                                                      typeof(ITargetBlock <TStart>)));
                }
            }

            var result = new DataflowBuilderBuildResult <TStart, TOutput> (starting_block, current_block);

            return(result);
        }
Example #2
0
        /// <summary>
        ///     Builds the starting and final blocks of the dataflow.
        /// </summary>
        IDataflowBuilderBuildResult <TStart, TInput[]> IDataflowBuilder <TStart, TInput[]> .Build()
        {
            ITargetBlock <TStart>   starting_block;
            ISourceBlock <TInput[]> ending_block;

            var batch_block = (BatchBlock <TInput>) this.CreateBlock();

            if (this.batchWaitingTimeout == null)
            {
                starting_block = batch_block as ITargetBlock <TStart>;
                ending_block   = batch_block;
            }
            else
            {
                Timer timer   = null;
                var   timeout = (long)this.batchWaitingTimeout.Value.TotalMilliseconds;

                timer = new Timer(
                    callback: _ =>
                {
                    batch_block.TriggerBatch();
                    // ReSharper disable once AccessToModifiedClosure
                    timer?.Change(timeout, -1);
                },
                    state: null,
                    dueTime: timeout * 2,
                    period: -1);

                var after_batch_block = new TransformBlock <TInput[], TInput[]>(
                    input =>
                {
                    timer.Change(timeout, -1);
                    return(input);
                },
                    new ExecutionDataflowBlockOptions
                {
                    MaxDegreeOfParallelism = 1,
                    EnsureOrdered          = this.options.EnsureOrdered
                });

                batch_block.LinkWithCompletionPropagation(after_batch_block);

                starting_block = batch_block as ITargetBlock <TStart>;
                ending_block   = after_batch_block;
            }

            if (this.previousBuilder != null)
            {
                var previous_build_result = this.previousBuilder.Build();
                previous_build_result.FinalBlock.LinkWithCompletionPropagation((ITargetBlock <TInput>)starting_block);

                starting_block = previous_build_result.StartingBlock;
            }

            if (starting_block == null)
            {
                throw new InvalidOperationException(string.Format("Block {0} can not be casted to the type of the starting block {1}.",
                                                                  batch_block.GetType(),
                                                                  typeof(ITargetBlock <TStart>)));
            }

            var result = new DataflowBuilderBuildResult <TStart, TInput[]>(starting_block, ending_block);

            return(result);
        }