2009-02-09 5 views
45

Je veux communiquer entre un processus parent et enfant écrit en C#. Il devrait être asynchrone, axé sur les événements. Je ne veux pas courir un fil dans tous les processus qui traitent la communication très rare.Quelle est la méthode la plus simple de communication inter-processus entre 2 processus C#?

Quelle est la meilleure solution pour cela?

+1

Je l'ai fait un article sur mon blog d'un exemple très simple de communication inter-processus en utilisant des canaux nommés dans WCF. [https://dopeydev.com/wcf-interprocess-communication/](https://dopeydev.com/wcf-interprocess-communication/) –

Répondre

9

Je suggère d'utiliser Windows Communication Foundation:

http://en.wikipedia.org/wiki/Windows_Communication_Foundation

Vous pouvez passer des objets en arrière, utiliser une variété de différents protocoles. Je suggère d'utiliser le protocole tcp binaire.

+57

... alors quelle est la manière compliquée alors? – dfasdljkhfaskldjhfasklhf

+4

@BPAndrew: Réécrire votre propre version de WCF? ;) – technophile

+50

Si la méthode WCF est la "méthode la plus simple", j'ai vraiment envie de pleurer: P – kizzx2

13

Si vos processus en même ordinateur, vous pouvez simplement utiliser stdio.

Ceci est mon utilisation, une page web screenshooter:

 var jobProcess = new Process(); 

     jobProcess.StartInfo.FileName = Assembly.GetExecutingAssembly().Location; 
     jobProcess.StartInfo.Arguments = "job"; 

     jobProcess.StartInfo.CreateNoWindow = false; 
     jobProcess.StartInfo.UseShellExecute = false; 

     jobProcess.StartInfo.RedirectStandardInput = true; 
     jobProcess.StartInfo.RedirectStandardOutput = true; 
     jobProcess.StartInfo.RedirectStandardError = true; 

     // Just Console.WriteLine it. 
     jobProcess.ErrorDataReceived += jp_ErrorDataReceived; 

     jobProcess.Start(); 

     jobProcess.BeginErrorReadLine(); 

     try 
     { 
      jobProcess.StandardInput.WriteLine(url); 
      var buf = new byte[int.Parse(jobProcess.StandardOutput.ReadLine())]; 
      jobProcess.StandardOutput.BaseStream.Read(buf, 0, buf.Length); 
      return Deserz<Bitmap>(buf); 
     } 
     finally 
     { 
      if (jobProcess.HasExited == false) 
       jobProcess.Kill(); 
     } 

Detect args sur Main

static void Main(string[] args) 
{ 
    if (args.Length == 1 && args[0]=="job") 
    { 
     //because stdout has been used by send back, our logs should put to stderr 
     Log.SetLogOutput(Console.Error); 

     try 
     { 
      var url = Console.ReadLine(); 
      var bmp = new WebPageShooterCr().Shoot(url); 
      var buf = Serz(bmp); 
      Console.WriteLine(buf.Length); 
      System.Threading.Thread.Sleep(100); 
      using (var o = Console.OpenStandardOutput()) 
       o.Write(buf, 0, buf.Length); 
     } 
     catch (Exception ex) 
     { 
      Log.E("Err:" + ex.Message); 
     } 
    } 
    //... 
} 
+3

Ne fonctionnera cependant pas si le processus cible doit avoir une interface graphique, c'est-à-dire si 'ProcessStartInfo.UseShellExecute' est' true'. Dans ce cas, vous ne pouvez pas rediriger la sortie et l'erreur standard. –

+0

@GuidoDomenici Vous pouvez réellement l'utiliser quand il a une interface graphique .... –

+0

@JayCroghan Je ne pense pas que vous pouvez l'utiliser quand il a une interface graphique. Au moins lorsque le processus client est lancé à partir d'une application Web. – Balanikas

0

Il y a aussi COM.

Il y a des détails techniques, mais je dirais que l'avantage est que vous pourrez appeler des méthodes que vous pouvez définir. MSDN propose des didacticiels d'interopérabilité C# COM. S'il vous plaît chercher parce que ces liens changent.

Pour commencer rightaway aller here ...

Questions connexes