예제 #1
0
        void ExecuteStep(IChannelHandlerContext context, TestScenarioStep currentStep)
        {
            if (!context.Channel.Open)
            {
                // todo: dispose scheduled work in case of channel closure instead?
                return;
            }

            Task   lastTask    = null;
            object lastMessage = null;

            foreach (object message in currentStep.Messages)
            {
                lastMessage = message;
                var    writeTimeoutCts   = new CancellationTokenSource();
                Task   task              = context.WriteAsync(message);
                object timeoutExcMessage = message;
                context.Channel.EventLoop.Schedule(
                    () => this.completion.TrySetException(new TimeoutException(string.Format("Sending of message did not complete in time: {0}", timeoutExcMessage))),
                    this.sendTimeout,
                    writeTimeoutCts.Token);
                task.ContinueWith(
                    t => writeTimeoutCts.Cancel(),
                    TaskContinuationOptions.OnlyOnRanToCompletion | TaskContinuationOptions.ExecuteSynchronously);
                task.OnFault(t => this.completion.TrySetException(t.Exception));

                lastTask = task;
            }

            if (currentStep.WaitForFeedback)
            {
                if (this.responseTimeout > TimeSpan.Zero)
                {
                    this.responseTimeoutCts = new CancellationTokenSource();
                    if (lastTask == null)
                    {
                        this.ScheduleReadTimeoutCheck(context, null);
                    }
                    else
                    {
                        lastTask.ContinueWith(
                            t => this.ScheduleReadTimeoutCheck(context, lastMessage),
                            TaskContinuationOptions.OnlyOnRanToCompletion | TaskContinuationOptions.ExecuteSynchronously);
                    }
                }
            }

            context.Flush();

            if (!currentStep.WaitForFeedback)
            {
                context.Channel.EventLoop.Execute(
                    ctx => this.ContinueScenarioExecution((IChannelHandlerContext)ctx),
                    context);
            }
        }
        void ExecuteStep(IChannelHandlerContext context, TestScenarioStep currentStep)
        {
            if (!context.Channel.Open)
            {
                // todo: dispose scheduled work in case of channel closure instead?
                return;
            }

            Task lastTask = null;
            object lastMessage = null;
            foreach (object message in currentStep.Messages)
            {
                lastMessage = message;
                var writeTimeoutCts = new CancellationTokenSource();
                Task task = context.WriteAsync(message);
                object timeoutExcMessage = message;
                context.Channel.EventLoop.ScheduleAsync(
                    () => this.completion.TrySetException(new TimeoutException(string.Format("Sending of message did not complete in time: {0}", timeoutExcMessage))),
                    this.sendTimeout,
                    writeTimeoutCts.Token);
                task.ContinueWith(
                    t => writeTimeoutCts.Cancel(),
                    TaskContinuationOptions.OnlyOnRanToCompletion | TaskContinuationOptions.ExecuteSynchronously);
                task.OnFault(t => this.completion.TrySetException(t.Exception));

                lastTask = task;
            }

            if (currentStep.WaitForFeedback)
            {
                if (this.responseTimeout > TimeSpan.Zero)
                {
                    this.responseTimeoutCts = new CancellationTokenSource();
                    if (lastTask == null)
                    {
                        this.ScheduleReadTimeoutCheck(context, null);
                    }
                    else
                    {
                        lastTask.ContinueWith(
                            t => this.ScheduleReadTimeoutCheck(context, lastMessage),
                            TaskContinuationOptions.OnlyOnRanToCompletion | TaskContinuationOptions.ExecuteSynchronously);
                    }
                }
            }

            context.Flush();

            if (!currentStep.WaitForFeedback)
            {
                context.Channel.EventLoop.Execute(
                    ctx => this.ContinueScenarioExecution((IChannelHandlerContext)ctx),
                    context);
            }
        }
예제 #3
0
        void ContinueScenarioExecution(IChannelHandlerContext context)
        {
            if (!this.testScenario.MoveNext())
            {
                context.CloseAsync()
                .ContinueWith(
                    t => this.completion.TrySetException(t.Exception),
                    TaskContinuationOptions.OnlyOnFaulted | TaskContinuationOptions.ExecuteSynchronously);
                this.completion.TryComplete();
                return;
            }

            TestScenarioStep currentStep = this.testScenario.Current;

            if (currentStep.Delay > TimeSpan.Zero)
            {
                context.Channel.EventLoop.Schedule((ctx, state) => this.ExecuteStep((IChannelHandlerContext)ctx, (TestScenarioStep)state), context, currentStep, currentStep.Delay);
            }
            else
            {
                this.ExecuteStep(context, currentStep);
            }
        }