Thomas Kramer

IT-COW | August 2011

Nur eine Instanz von robocopy laufen lassen

By Administrator at August 09, 2011 23:40
Filed Under: Administration, VBScript

Bei mir gibt es zwei Server, wobei der erste (Linux) TV-Aufnahmen stromsparend erstellt und der zweite (Windows-Server, Datenlager) die Dateien von diesem herunterlädt und selbst lediglich 12 Stunden am Tag (zeitgesteuert) im Betrieb ist. Diese Aufgabenteilung impliziert natürlich das auf ersterem ebenfalls ein (temporärer) File-Server läuft.

 

Nun hatte ich auf dem Windows-Server immer zeitgesteuert eine Batch-Datei aufgerufen, die robocopy startet und die Dateien rüberkopieren lässt. Das stellte sich jedoch als ungünstig heraus, denn wenn mehrere robocopy-Prozesse gleichzeitig laufen und um dieselbe Datei rangeln kann es passieren das nach dem Ende einer Dateienübertragung dieselbe Datei nochmal von vorne übertragen wird (wenn das Intervall zu kurz ist).

 

Alternativ zu der zeitgesteuerten Übertragung gibt es auch noch die Möglichkeit die Batch-Datei über den Gruppenrichtlinien-Editor (beim WHS/Windows Server 2003) bei jedem Start von Windows aufzurufen (zusammen mit der Monitoring-Funktion von robocopy), aber auch das verhindert nicht direkt doppelte Instanzen, weswegen ich mich entschied die Batch-Datei selbst anzupassen.

 

Aus einer Batch-Datei wurde somit ein VB-Script, welches zuerst prüft ob robocopy läuft und es dann erst gegebenenfalls startet. Das Script funktioniert übrigens über die Windows Management Instrumentation.

 

Übrigens gibt es gewissermaßen auch bereits einen Nachfolger zum Windows Scripting Host, die Windows Powershell. Irgendwann will ich mich in diese auch noch einarbeiten.

 

' Startet robocopy, wenn es nicht eh schon läuft

option explicit
on error resume next
Dim WShell, strComputer, objWMIService, colitems, objItem
Dim PID, ra


Set WShell = CreateObject("WScript.Shell")

strComputer = "."

Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")
Set colItems = objWMIService.ExecQuery("Select * from Win32_process where name =" & "'robocopy.exe'")
PID = 0
For Each objItem in colItems
   ra = objItem.Caption
   
   if Instr(0, ra, "robocopy.exe") then
     PID = objItem.ProcessId
   End If
Next

if PID = 0 then
  'WScript.Echo "Programm läuft noch nicht"
  Set oRobocopy = WShell.Exec("robocopy.exe \\$Server-IP$\$Freigabe$\ $Lfwk$:\$Zielverzeichnis$\ /S /XF *.directory /IF *.end1 *.end2 /W:10 /TBD /Z /MOT:5 ")
end if

wscript.quit

 

Weitere Links:


  • Source-Center: Link
  • MSDN: Link
  • CIM-Classes and Namespaces: Link
  • Robocopy-Parameter: Link

 

Monats-Liste