2009-11-02 2 views
7

Ich habe ein Projekt, wo ich eine Reihe von benutzerdefinierten Windows-Leistungsindikatoren auf mehreren Servern treffen und sie in einer Datenbank zusammenfassen. Wenn ein Server ausgefallen ist, möchte ich ihn überspringen und einfach mit meinem Tag fortfahren.Schnelle Möglichkeit zu überprüfen, ob ein Server über das Netzwerk in C# verfügbar ist

Momentan überprüfe ich, ob ein Server live ist, indem ich eine DirectoryInfo auf einer Freigabe mache, die ich später im Prozess sowieso ansehen muss, und dann die .Exists Eigenschaft überprüfen. Dies ist mein aktueller Codeausschnitt für Testen:

DirectoryInfo di = new DirectoryInfo(machine.Share_Path); 
if (!di.Exists) 
{ 
    log.Warn("Could not access " + machine.Name + "! Maybe its down?"); 
    continue; // Skips to the next server in my loop where this snippet exists. 
} 

Das funktioniert, aber es ist ziemlich langsam. Es dauert durchschnittlich 68 Sekunden, bis das Bit "ex.Exists" seine Arbeit beendet hat, und ich muss idealerweise innerhalb einer Sekunde wissen, ob ein Server erreichbar ist oder nicht. Das Pingen ist auch keine Option, da ein Server zwar pingbar sein kann, aber in unserer Umgebung nicht "live" ist.

Ich bin immer noch ein bisschen frisch in der .NET-Welt, also bin ich offen für jede Beratung, die Leute anbieten können.

Vielen Dank im Voraus.

-Weegee

+0

dauert es 68 Sekunden, wenn der Server da ist, wenn der Server nicht da ist, oder beides? –

+0

Wenn der Server nicht da ist. Wenn der Server da ist, dauert es weniger als eine Sekunde. – Weegee

+0

Wie wäre es, den Check in einem separaten Worker-Thread auszuführen und ihn einfach so lange dauern zu lassen? – Dolphin

Antwort

8

Ping Erste, dann Fragen stellen

Warum nicht ping zuerst, und dann tun die di.Exists wenn Sie eine Antwort erhalten?

Das würde es Ihnen ermöglichen, früh in dem Fall zu scheitern, der nicht erreichbar ist, und keine Zeit für Maschinen zu verschwenden, die hart sind.

Ich habe tatsächlich diese Methode erfolgreich zuvor verwendet.


Paralellize

Eine weitere Option, die Sie haben, ist die Überprüfung und Aktion auf den Servern paralellize als sie zur Verfügung stehen, sind bekannt.

Sie können die Paralell.ForEach()-Methode verwenden und eine Thread-sichere Warteschlange zusammen mit einem einfachen Consumer-Thread verwenden, um die erforderliche Aktion auszuführen. Kombiniert mit der obigen Prüfmethode könnte dies den gesamten Engpass bei der Aufwärts-/Abwärtsprüfung verringern.


Klopfen an der Tür

Noch ein anderes Verfahren zur ckeck wäre, wenn der erforderliche Remote-Dienst ausgeführt wird (entweder durch seinen Hafen direkt treffen oder indem sie sie mit WMI Abfrage).

Da WMI fast immer ausgeführt wird, wenn eine Maschine aktiv ist, sollte Ihre Verbindung sehr schnell erfolgreich sein oder fehlschlagen.

+0

Das ist ein ausgezeichneter Vorschlag, und ich denke, ich werde es umsetzen. Allerdings haben wir häufig Server, die nicht hart sind; aus Wartungsgründen, dass ich schnell überspringen muss. – Weegee

+1

Hrm ... Gibt es einen Fernservice, den Sie an der Maschine überprüfen könnten? Oder verwenden Sie Remote-WMI? –

+0

Remote WMI ist eine großartige Idee. Ich versuche bereits, einige Leistungsindikatoren zu treffen, also werde ich einfach versuchen, eine Dummy zu erstellen, von der ich weiß, dass sie auf jedem Server existiert (% Prozessorzeit \ _Total) und wenn sie fehlschlägt, werde ich diesen Server überspringen.Ich weiß nicht, warum ich nicht früher daran gedacht habe. Danke noch einmal! – Weegee

2

Der einzige "schnelle" Weg, um zu sehen, ob es ohne Ping ist, wäre einen Socket zu erstellen und zu sehen, ob Sie tatsächlich eine Verbindung zu dem Port des Dienstes herstellen können, den Sie erreichen möchten.

Dies wäre das Äquivalent von telnet Servername 135 zu sehen, ob es oben ist.

Insbesondere ...

  1. ein NET TCP Socket-Client erstellen (System.Net.Sockets.TcpClient)
  2. Anruf Beginconnect() als asynchroner Betrieb, an den Server betreffende auf einem des RPC-Ports zu verbinden, Ihr Verzeichnis würde Code sowieso verwenden (TCP 135, 139 oder 445).
  3. Wenn Sie innerhalb von X Millisekunden nichts hören, rufen Sie Close() auf, um die Verbindung abzubrechen.

Haftungsausschluss: Ich habe keine Ahnung, welche Auswirkungen dies auf jede Bedrohung/Firewall-Schutz haben würde, die diese Art von Connect/Disconnect als Bedrohung ohne Daten gesendet Aktivität sehen.

0
  • Die "Full-Blown" Option, um ein Monitoring-Tool wie SCOM (System Center Operations Manager) zu installieren, wäre dies hat eine SDK Sie SCOM verwenden können für die Abfrage (Performance) und Wartungsinformationen avout Maschinen zu sein überwacht. Könnte eine Brücke zu weit sein, aber ....

  • Telnet ist eine andere Option. Versuchen Sie, eine Telnet-Verbindung zum Zielcomputer herzustellen, um festzustellen, ob dieser antwortet.

  • Erstellen Sie ein kleines Windows-Dienst, die Sie auf Ihrem Zielrechner installieren, müssen der Admin es stoppen sys, wenn sie Wartungsarbeiten an der Zielmaschine auszuführen (verwenden Batch-Datei nur net stop/net starten den Dienst)

1

Öffnen Socket zu einem bestimmten Port in der Regel den Trick. Wenn Sie wirklich schnell sein möchten, stellen Sie sicher, dass die NoDelay-Eigenschaft auf dem neuen Socket (Nagle-Algorithmus) festgelegt ist, so dass keine Pufferung stattfindet.

Fast hängt weitgehend von der Latenz ab, aber dies ist wahrscheinlich der schnellste Weg, den ich kenne, um eine Verbindung zu einem Endpunkt herzustellen. Es ist ziemlich einfach, mit den Async-Methoden zu parallelisieren. Wie schnell Sie überprüfen können, hängt weitgehend von Ihrer Netzwerktopologie ab, aber in Tests für 1000 Server (Latenz zwischen 0 und 75 ms) konnte ich den Verbindungsstatus in ~ 30 Sekunden abrufen. Keine wissenschaftlichen Daten, aber sollten Sie auf die Idee kommen.

Auch nicht durch UNC-Dateifreigaben, denn wenn der Server nicht mehr existiert, haben Sie eine Reihe von dangling Verbindungen, die für immer zu Timeout dauern. Wenn Sie also viele Server mit ungültigen DNS-Einträgen haben und versuchen, diese abzufragen, werden Sie Windows im Laufe der Zeit komplett herunterfahren. Dinge wie File.Exists und jeder Dateizugriff verursachen dies.

Verwandte Themen