Et simpelt eksempel på brug af NamedPipeServerStream

Hvis man vil lave en server og en klient som snakker sammen via pipes, har jeg her sammensat et lille eksempel, som viser hvad man skal bruge, for at komme igang.

Server

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Main
{
    class Program
    {
        static System.Threading.ManualResetEvent _quitEvent = new System.Threading.ManualResetEvent(false);
        static object state = new object();
        static void Main(string[] args)
        {
            Console.CancelKeyPress += (sender, eArgs) => {
                _quitEvent.Set();
                eArgs.Cancel = true;
            };
            var server = new System.IO.Pipes.NamedPipeServerStream("server", System.IO.Pipes.PipeDirection.InOut, 
                1,
                System.IO.Pipes.PipeTransmissionMode.Message,
                System.IO.Pipes.PipeOptions.Asynchronous);


           var result=  server.BeginWaitForConnection((asyncResult) => 
            {
                server.EndWaitForConnection(asyncResult);
                var reader = new System.IO.StreamReader(server);
                Console.WriteLine(reader.ReadLine());

            }, state);
			
            _quitEvent.WaitOne();
            server.Close();
        }
    }
}

Det man skal huske på serversiden, hvis man laver wait kaldet asynkront via server.BeginWaitForConnection er at man skal huske at kalde EndWaitForConnection så hurtigt man kan efter man modtager noget data. Vil man lave det synkront kan man nøjes med at kalde WaitForConnection. Dette kald er et blocking kald, som frigiver tråden, og venter på at der kommer en connection, før tråden bliver vækket til live igen.

Pga. at NamedPipeServerStream er en wrapper omkring en system pipe, skal man huske på at man ikke bare kan lave en while(true), og modtage flere connections over samme begin, som her

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Main
{
    class Program
    {
        static System.Threading.ManualResetEvent _quitEvent = new System.Threading.ManualResetEvent(false);
        static object state = new object();
        static void Main(string[] args)
        {
            Console.CancelKeyPress += (sender, eArgs) => {
                _quitEvent.Set();
                eArgs.Cancel = true;
            };

            var server = new System.IO.Pipes.NamedPipeServerStream("server", System.IO.Pipes.PipeDirection.InOut, 
                1,
                System.IO.Pipes.PipeTransmissionMode.Message,
                System.IO.Pipes.PipeOptions.Asynchronous);

			while(true)
			{
				var result=  server.WaitForConnection();
				
				server.EndWaitForConnection(asyncResult);
				var reader = new System.IO.StreamReader(server);
				Console.WriteLine(reader.ReadLine());
			}
            _quitEvent.WaitOne();

            server.Close();
        }
    }
}

Dette vil give en fejl! Man skal have var server = new ... med ind i løkken.

Klient

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Client
{
    class Program
    {
        static void Main(string[] args)
        {
            var client = new System.IO.Pipes.NamedPipeClientStream("server");
            client.Connect();
            string message = "hello world";
            client.Write(Encoding.UTF8.GetBytes(message), 0, message.Length);
            client.Close();
        }
    }
}

Klienten er lige ud af landevejen. Husk at kalde Connect() før man laver et Write!!

Opdateret.