2009-12-04 1 views
8

Ich habe eine Konsolenanwendung, die serverbasiert ist. Ich möchte nur 1 Instanz davon gleichzeitig für einen bestimmten Server ausgeführt werden (dies ist unabhängig von dem Benutzer, der es möglicherweise ausführt).Die beste Methode zum Implementieren von Singleton in einer Konsolenanwendung C#?

Ich muss eine Überprüfung hinzufügen, um sicherzustellen, dass nur 1 Instanz davon ausgeführt wird, kann ich dies bereits tun, indem Sie die laufenden Prozesse auf dem Server überprüfen, aber ist diese Best Practice?

Da ich ständig auf der Suche nach Möglichkeiten bin, die Codierungsstile zu verbessern und auf dem neuesten Stand zu bleiben, gibt es einen besseren Weg, dies in letzter Zeit zu tun? Wenn du denkst - "Wenn es nicht kaputt ist, repariere es nicht", Vielleicht hast du recht, aber ich möchte mehr von der eingebauten Funktionalität des Frameworks profitieren.

Ich verwende .net v3.5, und dies ist eine Konsolenanwendung.

Vielen Dank im Voraus

Antwort

14

Sie Mutex-Klasse verwenden sollte, wie hier erklärt: C# .NET Single Instance Application

+0

+1 und akzeptierte Antwort, nicht sicher, ob Sie eine bessere Antwort als das bekommen können. Tyvm! –

+0

+1 Ich stimme JL –

+0

Nun, das dauerte eine ganze 2 Minuten zu implementieren :) –

1

ein Nahm Viele Teile und Codes von überall, aber ich fand schließlich die magische Soße, die konzeptionell eine Singleton-Konsolen-App erstellt, die auch weiterhin Befehle empfangen kann Zeilenargumente. Wenn das also zum ersten Mal ausgeführt wird, verarbeitet es seine Befehlszeilenparameter und wartet dann. Wenn Sie versuchen, das erneut auszuführen, wenn das erste noch ausgeführt wird, werden diese Befehlszeilenargumente an den ersten Prozess zur Behandlung übergeben und der zweite Prozess stirbt.

using System; 
using System.IO; 
using System.IO.Pipes; 
using System.Threading; 
using System.Threading.Tasks; 

namespace SingletonConsoleApp 
{ 
    class Program 
    { 
     const string InterprocessID = "{D2D6725E-79C3-4988-8475-4446549B6E6D}"; // can be anything that's unique 
     static Mutex appSingletonMaker = new Mutex(true, InterprocessID); 

     static void Main(string[] args) 
     { 
      if (appSingletonMaker.WaitOne(TimeSpan.Zero, true)) 
      { 
       var argHandler = new Action<string[]>((arguments => 
       { 
        Console.WriteLine(String.Join(" ", arguments)); 
       })); 
       Task.Run(() => 
       { 
        using (var server = new NamedPipeServerStream(InterprocessID)) 
        { 
         using (var reader = new StreamReader(server)) 
         { 
          using (var writer = new StreamWriter(server)) 
          { 
           while (true) 
           { 
            server.WaitForConnection(); 
            var incomingArgs = reader.ReadLine().Split('\t'); 
            writer.WriteLine("done"); 
            writer.Flush(); 
            server.Disconnect(); 
            argHandler(incomingArgs); 
           } 
          } 
         } 
        } 
       }); 
       argHandler(args); 
       Console.ReadKey(); 
       appSingletonMaker.ReleaseMutex(); 
      } 
      else 
      { 
       if (args.Length > 0) 
       { 
        using (var client = new NamedPipeClientStream(InterprocessID)) 
        { 
         client.Connect(); 
         var writer = new StreamWriter(client); 
         using (var reader = new StreamReader(client)) 
         { 
          writer.WriteLine(String.Join("\t", args)); 
          writer.Flush(); 
          reader.ReadLine(); 
         } 
        } 
       } 
      } 
     } 
    } 
} 
Verwandte Themen