Ejemplo n.º 1
0
            /// <summary>
            /// Initializes a new instance of the <see cref="ConnectedCommand" /> class.
            /// </summary>
            /// <param name="connectionGuid">The connection unique identifier.</param>
            /// <param name="service">The service.</param>
            /// <param name="connection">The connection.</param>
            /// <param name="request">The request.</param>
            /// <param name="token">The cancellation token.</param>
            public ConnectedCommand(
                Guid connectionGuid,
                [NotNull] BaseService service,
                [NotNull] NamedPipeConnection connection,
                [NotNull] CommandRequest request,
                CancellationToken token = default(CancellationToken))
            {
                ConnectionGuid = connectionGuid;
                _connection = connection;
                _request = request;
                _cancellationTokenSource = token.ToCancelable();
                ID = _request.ID;

                token = _cancellationTokenSource.Token;

                Task.Run(
                    async () =>
                    {
                        try
                        {
                            do
                            {
                                // ReSharper disable once PossibleNullReferenceException
                                await Task.Delay(250, token).ConfigureAwait(false);
                                if (token.IsCancellationRequested) return;
                                await Flush(0, token).ConfigureAwait(false);
                            } while (true);
                        }
                        catch (TaskCanceledException)
                        {
                        }
                    },
                    token);
                // Kick of task to run command.
                Task.Run(
                    async () =>
                    {
                        Exception exception = null;
                        bool cancelled = false;
                        try
                        {
                            await
                                service.ExecuteAsync(ConnectionGuid, _request.CommandLine, this, token)
                                    .ConfigureAwait(false);
                            if (!token.IsCancellationRequested)
                                await Flush(-1, token).ConfigureAwait(false);
                            else
                                cancelled = true;
                        }
                        catch (OperationCanceledException)
                        {
                            cancelled = true;
                        }
                        catch (Exception e)
                        {
                            exception = e;
                        }

                        if (cancelled)
                            using (await _flushLock.LockAsync(token).ConfigureAwait(false))
                            {
                                try
                                {
                                    using (CancellationTokenSource cts = Constants.FireAndForgetTokenSource)
                                        await connection.Send(
                                            new CommandCancelResponse(
                                                _cancelRequest != null ? _cancelRequest.ID : Guid.Empty,
                                                ID),
                                            cts.Token)
                                            .ConfigureAwait(false);
                                }
                                catch (OperationCanceledException)
                                {
                                }
                                return;
                            }

                        if (exception != null)
                            try
                            {
                                await Flush(0, token).ConfigureAwait(false);
                                _builder.Append(exception.Message);
                                await Flush(-2, token).ConfigureAwait(false);
                            }
                                // ReSharper disable once EmptyGeneralCatchClause
                            catch
                            {
                            }

                        Dispose(true);
                    },
                    token);
            }