public void Close_CanBeCalledWithoutConnectAsync()
 {
     using (var receiver = new StandardOutputReceiver(Mock.Of <IPluginProcess>()))
     {
         receiver.Close();
     }
 }
        public void MessageReceived_RaisedForSingleMessage()
        {
            var json      = "{\"RequestId\":\"a\",\"Type\":\"Response\",\"Method\":\"None\"}";
            var requestId = "a";
            var type      = MessageType.Response;
            var method    = MessageMethod.None;
            var process   = new Mock <IPluginProcess>();

            process.Setup(x => x.BeginReadLine())
            .Callback(() => process.Raise(x => x.LineRead += null, new LineReadEventArgs(json)));

            using (var receivedEvent = new ManualResetEventSlim(initialState: false))
                using (var receiver = new StandardOutputReceiver(process.Object))
                {
                    MessageEventArgs args = null;

                    receiver.MessageReceived += (object sender, MessageEventArgs e) =>
                    {
                        args = e;

                        receivedEvent.Set();
                    };

                    receiver.Connect();

                    receivedEvent.Wait();

                    Assert.NotNull(args);
                    Assert.NotNull(args.Message);
                    Assert.Equal(requestId, args.Message.RequestId);
                    Assert.Equal(type, args.Message.Type);
                    Assert.Equal(method, args.Message.Method);
                    Assert.Null(args.Message.Payload);
                }
        }
        public void Faulted_RaisedForInvalidMessage(string json)
        {
            var process = new Mock <IPluginProcess>();

            process.Setup(x => x.BeginReadLine())
            .Callback(() => process.Raise(x => x.LineRead += null, new LineReadEventArgs(json)));

            using (var faultedEvent = new ManualResetEventSlim(initialState: false))
                using (var receiver = new StandardOutputReceiver(process.Object))
                {
                    ProtocolErrorEventArgs args = null;

                    receiver.Faulted += (object sender, ProtocolErrorEventArgs e) =>
                    {
                        args = e;

                        faultedEvent.Set();
                    };

                    receiver.Connect();

                    faultedEvent.Wait();

                    Assert.NotNull(args);
                    Assert.IsType <ProtocolException>(args.Exception);
                }
        }
        public void Faulted_RaisedForDeserializationError()
        {
            var json = "{\"RequestId\":\"a\",\"Type\":\"Response\",\"Method\":\"None\",\"Payload\":\"{\\\"d\\\":\\\"e\\\"}\"}\r\n";

            var process = new Mock <IPluginProcess>();

            process.Setup(x => x.BeginReadLine())
            .Callback(() => process.Raise(x => x.LineRead += null, new LineReadEventArgs(json)));

            using (var faultedEvent = new ManualResetEventSlim(initialState: false))
                using (var receiver = new StandardOutputReceiver(process.Object))
                {
                    ProtocolErrorEventArgs args = null;

                    receiver.Faulted += (object sender, ProtocolErrorEventArgs e) =>
                    {
                        args = e;

                        faultedEvent.Set();
                    };

                    receiver.Connect();

                    faultedEvent.Wait();

                    Assert.NotNull(args);
                    Assert.NotNull(args.Exception);
                    Assert.IsType <ProtocolException>(args.Exception);
                    Assert.Null(args.Message);
                }
        }
 public void Dispose_IsIdempotent()
 {
     using (var receiver = new StandardOutputReceiver(Mock.Of <IPluginProcess>()))
     {
         receiver.Dispose();
         receiver.Dispose();
     }
 }
        public void Connect_ThrowsIfAlreadyConnected()
        {
            using (var receiver = new StandardOutputReceiver(Mock.Of <IPluginProcess>()))
            {
                receiver.Connect();

                Assert.Throws <InvalidOperationException>(() => receiver.Connect());
            }
        }
        public void Connect_ThrowsIfDisposed()
        {
            var receiver = new StandardOutputReceiver(Mock.Of <IPluginProcess>());

            receiver.Dispose();

            var exception = Assert.Throws <ObjectDisposedException>(() => receiver.Connect());

            Assert.Equal(nameof(StandardOutputReceiver), exception.ObjectName);
        }
        public void Dispose_CancelsReading()
        {
            var process = new Mock <IPluginProcess>(MockBehavior.Strict);

            process.Setup(x => x.CancelRead());

            using (var receiver = new StandardOutputReceiver(process.Object))
            {
            }

            process.Verify(x => x.CancelRead(), Times.Once);
        }
        public void MessageReceived_HandlesNullAndEmptyString()
        {
            var json      = "{\"RequestId\":\"a\",\"Type\":\"Response\",\"Method\":\"None\"}";
            var requestId = "a";
            var type      = MessageType.Response;
            var method    = MessageMethod.None;
            var process   = new Mock <IPluginProcess>();

            process.Setup(x => x.BeginReadLine())
            .Callback(() =>
            {
                // We can't directly verify handling of null and empty string except by
                // passing a valid line after them and ensuring it gets processed correctly.
                process.Raise(x => x.LineRead += null, new LineReadEventArgs(null));
                process.Raise(x => x.LineRead += null, new LineReadEventArgs(""));
                process.Raise(x => x.LineRead += null, new LineReadEventArgs(json));
            });

            using (var receivedEvent = new ManualResetEventSlim(initialState: false))
                using (var receiver = new StandardOutputReceiver(process.Object))
                {
                    MessageEventArgs args = null;

                    receiver.MessageReceived += (object sender, MessageEventArgs e) =>
                    {
                        args = e;

                        receivedEvent.Set();
                    };

                    receiver.Connect();

                    receivedEvent.Wait();

                    Assert.NotNull(args);
                    Assert.NotNull(args.Message);
                    Assert.Equal(requestId, args.Message.RequestId);
                    Assert.Equal(type, args.Message.Type);
                    Assert.Equal(method, args.Message.Method);
                    Assert.Null(args.Message.Payload);
                }
        }