Ordner Löschen mit VBS

ThLey

Grünschnabel
Hallo,
bin ohne Erfahrung in VBS. Habe mir eine Backuplösung aus verschiedenen Quellen zusammen gestellt, nun habe folgendes VBS Problem:

Ich erstelle auf einem Externen Laufwerk mittels VBS ein Backup. Hierzu wird immer
ein neuer Ordner "jjjj-mm-dd" erzeugt in dem die gesicherten Datein liegen.

Mit der Zeit wird die Platte jedoch zu voll. Ich möchte daher nur die letzten 10 Ordner behalten, die anderen sollen gelöscht werden. Leider kann ich das nicht über die Datumsabfrage lösen da nicht jeden Tag ein Backup erstellt wird.

Hatte so angefangen:
Code:
'    ' alte Sicherungsdatei löschen -------------------------- 

' Einlesen des Backup Verzeichnisses
Set ReadKonfiguration = objFSO.OpenTextFile(Konfiguration, 1, true)
    'Einlesen des Verzeichnisses
    B = ReadKonfiguration.Readline
    ReadKonfiguration.close

MsgBox "Verzeichnis: " & (B)

Set fsoLoeschen = CreateObject("Scripting.FileSystemObject")
Set ordner = fsoLoeschen.GetFolder (B)
MsgBox "Gefunden: " & (ordner)

Ich lese aus einem Textfile den Laufwerksbuchstaben aus und speichere den in der Variable B. Danach komme ich nicht weiter. Erstelle ein Object "fsoLoeschen".

Das Script soll nun alle Ordner sortieren und dann die ersten 10 behalten und den Rest löschen. Irgendwie muss ich die mit ein er FOR Each...NEXT Schleife zählen soviel habe ich bei "Schwichtenberg" gelesen.

Einfacher: Wie sortiere, durchlaufe und lösche ich Ordner in einem Verzeichniss so, dass ich nur die letzten 10 erstelten übrigbleiben?

Hat da jemand eine Idee?
 

Hawkings

Erfahrenes Mitglied
Hi du,

also ich habe meine Backup - Lösung von Servern folgendermaßen realisiert.
Code:
Set WshShell = WScript.CreateObject("WScript.Shell")


' get number of the curretn day of the week
lDayAsNumber = Weekday(Now)

' create path where to store the backups
lPath =  "c:\backup\" & lDayAsNumber 
'Chr(34) && chr(34)

Dim x
Dim i
Dim user
Dim pwd
Dim datei
Dim Text
Dim Pos1
Dim e
Dim fso
Dim lCommand,lCommand1
'Dim arrLog(3)
'  arrLog(0)= lPath&"\logfilevbsA.txt"
'  arrLog(1)= lPath&"\logfilevbsB.txt"
'  arrLog(2)= lPath&"\logfilevbsC.txt"
'  arrLog(3)= lPath&"\logfilevbsD.txt"
Dim paradb(3)
  paradb(0)= "mcashvins"
  paradb(1)= "m3iarchive"
  paradb(2)= "mcworkflow"
  paradb(3)= "mclog"
 
Dim Err
    Dim objArgs, strMsgBody, iMsg, iConf, Flds
    
    Set iMsg  = CreateObject("CDO.Message")
    Set iConf = CreateObject("CDO.Configuration")

' Validating index and keys
Function ValidDb(fDBName,fPath)
	Set WshShell = WScript.CreateObject("wscript.shell")
        lautoris = "uid=dba;pwd=dba"
	lCommand = "dbbackup -c " & Chr(34) & "dsn="& fDBName &";"&lautoris&"" & chr(34) & " -x -y " & fPath 
	lResult = WshShell.Run(lCommand , 0, True)



	lCommand = "dbeng9 -ga -n ValidDb "& fPath & "\" & fDBName &".db"
	wshshell.run lCommand,0,false 'dbeng9 wird gestartet
	lLogFileName=fPath & "\logfilevbs.txt"
	
	Set fso = WScript.CreateObject("Scripting.FileSystemObject")
	If (fso.FileExists(lLogFileName)) Then
	  fso.deleteFile (lLogFileName)
	Else
	End if	
	
	' wait here, to give dbeng the chance to start
	WScript.Sleep 5000
	
	wshshell.run "dbvalid -c "& lautoris &";eng=ValidDb;dbn="& fDBName &" -f -o "& lLogFileName,0,True
	
	objShell.LogEvent 1, _
    	"MC BackupValid ist abgeschlossen worden."
	
	Err=0
	Set datei = fso.OpenTextFile(lLogFileName)
	Text = datei.ReadAll 
	datei.Close()
	Pos1 = InStr( 1,Text,"No errors reported",1)
	If Pos1 > 0 Then
	  If InStr(1,Text, "No errors reported",1) > 0 Then  
	  Else
	      Err=1
	  End If
	 Else
	    Err=1
	End If 
	If Err =1 Then
		 ValidDb = False 
	Else 
		ValidDb = True
	End If
	
End Function

Sub BackupValidCheck(fDatadb,fPath)
	If ValidDb(fDatadb,fPath)=False Then
		If ValidDb(fDatadb,fPath) = False Then
			Call SendMail(fDatadb)
		End If
	Else
	End If
End Sub

Function SendMail (fDatabaseName)

Set objShell = Wscript.CreateObject("Wscript.Shell")
objShell.LogEvent 1, _
    "MC DBValid error in database " & fDatabaseName
        
    'Parameter 1 = Typ der Meldung und zugleich Ereigniskennung
	'0 = Information
	'2 = Warnung
	'1 = Fehler 
	'Parameter 2 = Meldung
	'Diese Meldung wird in der Beschreibung angezeigt 
	'Parameter 3 = Ziel
	'Hier kann ein entfernter Computer angegeben werden, z.B.: "\\Servername" 
  
Set objMessage = CreateObject("CDO.Message")
objMessage.Subject = "BackupValidierungsCheck"
objMessage.Sender = "alert@.....com"
objMessage.To = "achristiansen@....com"
objMessage.TextBody = "Alert-Mail: An Failure was detected by repeatet Validating Database-Backup , please check it" & lLogFileName

objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/sendusing") = ..
objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpserver") = "smtp.medicalcommunications.com"
objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpserverport") = .ö.
objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpauthenticate") = ...
objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/sendusername") = ...
objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/sendpassword") = ...
objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpconnectiontimeout") = ...
objMessage.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpusessl") = ...
objMessage.Configuration.Fields.Update

objMessage.Send


End Function

''''''''''''''''''''''''''''''''''''''''''''
' main routine
Const EVENT_SUCCESS = 0

Set objShell = Wscript.CreateObject("Wscript.Shell")

objShell.LogEvent EVENT_SUCCESS, _
    "MC DBValid gestartet"

 Call BackUpValidCheck(paradb(li),lPath)

objShell.LogEvent EVENT_SUCCESS, _
    "MC DBValid beendet"

Bei mir wird auf Server zugegriffen und die Datenbanken gebackupt und anschließend validiert, also überprüft, ob die Backuperstellung fehlerlos vonstatten ging, ist dies der Fall ist alles toll, wenn nicht, wird der Admin, in dem Falle habe ich mich azubi mal angegeben ^^ benachtrichtigt.

Um dein Problemn anzusprechen:

Code:
' get number of the curretn day of the week
lDayAsNumber = Weekday(Now)

' create path where to store the backups
lPath =  "c:\backup\" & lDayAsNumber 
'Chr(34) && chr(34)

Wenn du jetzt hier anstelle der heweiligen Wochentag, also 1,2,3,4,5,6 oder 7 einfach die Anzahl der Backups alös Nummer nimmst, also immer wenn eins erstellt wird
NumberBackup = NumberBackup + 1
Wahrscheinlich musst du dafür dann abprüfen, welche Datei die letzte ist, von der Nummer auch her und diese dann entsprechend verarbeiten, sprich die Nummer des letzten backups auslesen.

Wenn du die hast kannst du die einfach um eins hochzählen und als Nummer für dein nächstes Backup verwenden.

Ich probioers mal aus, sobald es klappt, melde ich mich..

Gruß, Hawkin
 

Hawkings

Erfahrenes Mitglied
So, das dürfte gehen, denke ich :)

Code:
Set WshShell = WScript.CreateObject("WScript.Shell")


Dim i,num
Set ObjFSO = CreateObject("Scripting.FileSystemObject")
'____________Datum an dem das Verzeichnis erstellt wurde

For i = 200 To 1 step -1						
StrDatei = "C:\Backup\"&i
WScript.Echo StrDatei

If ObjFSO.Folderexists(StrDatei) Then
WScript.Echo "File "& StrDatei&" existiert" 
'get number for actual backup
num = i
'create PAth where to store the backups
lPath = "C:\backup\" & num + 1			' ! ! ! Der Pfad, der für das ablegen des Backups bestimmt ist
i = 1
Else
WScript.Echo "File existiert nicht"
End if

Next


WScript.Echo "ende"

Erklärung:
Dieser Programmabschnitt besteht aus einer For-Schleife und einer If-Abfrage.
Innerhalb der For - Schleife wird von 200 runter auf 1 gezählt und dabei jeweils
überprüft, ob das hier vordefinierte File "C:\Backup\&"num existiert.

Gibt es bspw. bisher 15 Backups, so ist das letzte Backup nach dem Beispiel
unter C:\Backup\15 abgelegt, das zweitletzte In 14 usw..

Die For schleife zählt solange runter, bis die integrierte IfSchleife diese letzte
Datei gefunden hat und legt dann ein neues Verzeichnis an, also bei 15 wird die 16 ngelegt
und dort das Backup reingelegt...


Das setzt jedoch voraus, dass du einen festen Ort hast, an dem du deine Backups speicherst, ich habe hier als Beispiel einfach "C:\Backup\..." angegeben.
Das Verzeichnis kannst du ja einfach ändern im Code.
Der Code hier gibt dir dann anschließend denn neuen Pfad (lPath) für dein neues Backup, dass du dann einfach nur noch in dein Skript einfügen musst.

Hoffe, das hilft dir weiter, Hawkin
 

ThLey

Grünschnabel
Schon mal Danke für die Hilfe. jedoch ist nicht das erstellen der Sicherungsordner ist das Problem, hier erzeuge ich Ordner des Formats yyyy-dmm-dd


Code:
 'Anpassen des Datumformats
    If Month(Now) <10 Then 
    	FMonth="0"&Month(Now)
    Else
    	FMonth=Month(Now)
    End If
    
    If Day(Now) <10 Then 
    	FDay="0"&Day(Now)
    Else
    	FDay=Day(Now)
    End If
    
    ' Variable (erst hier ist "Target" definiert) ---------
    UserFolder  = Target & "\" & objNetwork.UserName  
    BackupFolder= Target & "\" & objNetwork.UserName & "\" & Year(Now)&"-"&FMonth&"-"&FDay

sondern viel mehr ist es das löschen der überzähligen Ordner auf dem Sicherungslaufwerk.

Ich möchte die zu letzt erstelten 10 Ordner behalten, die anderen sollen gelöscht werden.
So lese ich die erstellten Ordner im Moment ein:

Code:
Set fsoLoeschen = Createobject("Scripting.filesystemobject")
		i = 0
		
		set ordnerstamm = fsoLoeschen.getfolder(B& "\" & objNetwork.UserName)
		for each ordner in ordnerstamm.subfolders
		i = i + 1 
		 Set f1 = fsoLoeschen.GetFolder(ordner.path)
		 zeit = f1.DateCreated

Wie sortiere ich diese so, dass ich alle überschüssigen erkennen kann?
 

Alex F.

Erfahrenes Mitglied
Du hast mit dem FSO leider keine Möglichkeit zu sortieren. Demnach müsstest du vielleicht alle Sicherungsordner löschen die nach deinem Muster kleiner sind. Heisst du extrahierst das Datum aus dem Ordnernamen
Prüfst mit datediff ob das Datum >10 Tage ist und wenn ja dann löschen. Das setzt natürlich vorraus, das du dies täglich durchführst.

Grüsse bb
 

Hawkings

Erfahrenes Mitglied
Stimmt, nicht das erstellen der ORdner ist das Problem, sondern das herausfinden, welche geläöscht werden sollen und welche nicht...

In meiner Lösung geht es folgendermaßen:
Du sagtest, dass du nicht regelmäßig Backups erstellsdt, also sagen wir mal täglich, also nummeriere ich die Ordner einfach und alle bis auf die letzten 10 erstellten Ordner werden gelöscht, dafür brauch man eigentlich kein Datum, außer es muß für dich ganz genau 10 Tage sein, erstellt du jedoch jeden Tag ein Backup, dann funkt mein Skript auch, musst halt nur noch das löschen der Ordner in die Abfrage mit einbinden...

Gruß, Hawkin
 

Hawkings

Erfahrenes Mitglied
Wacken?!

Also, nochmal zu meinem Verständnis:

Du möchtest ein Skript, dass dir Backups anlegt und diese in ORdnern in ein Verzeichnis anlegt, bspw. C:\Backup\...
Dabei sollen nur jeweils die 10 neuesten Ordner mit den enthaltenen Backups jeweils in diesem Verzeichnis liegen.

Dann stellt sich mir die Frage, bestehst du auf das Datum als Name des ORdners?!
ODer reicht dir eine einfache Durchnummerierung, an dr du schnell und einfach ablesen kannst, welches das neueste Backup ist?!
Brauchst du nicht unbedingt das Datum al ORdnernamen, dann frage ich mich, wo das PRob ist, wenn ihr die Ordner einfach durchnummeriert, der neueste ORdner hat +1 als letzter Ordner, alsso sieht ein Verzeichnis folgendermaßen aus...

C:\Backup\

4
5
6
7
8
9
10
11
12
13

Die letzten 10 Backups in den Ordnern sind noch da, die älteren wurden gelöscht, das finde ich einfacher als umständlich das Datum auszufiltern aus den Namen, da das mit BubbleSort oder ählichen nichtz so easy ist...

Oder ist dir das mit Datum lieber?!

:confused: :confused: :confused: :confused:

Gruß, Hawkin
 

Sven Mintel

Mitglied
Falls du nicht auf VBS bestehst, mit JScript ginge es analog, nur wäre dort das Sortieren ungleich bequemer zu bewerkstelligen:
Code:
  fso = new ActiveXObject("Scripting.FileSystemObject");
  f = fso.GetFolder("c:\\Backup");
  n=10;
  a=[];
  fc = new Enumerator(f.SubFolders);
  
  for (;!fc.atEnd(); fc.moveNext())
    {
      s=fso.getFolder(fc.item());
      a.push([new Date(s.DateCreated).getTime(),fc.item()]);
    }
    a.sort();
    while(a.length>n)
      {
        fso.DeleteFolder(a[0][1]);
        a.shift();
      }
 

Praecox

Grünschnabel
Falls du nicht auf VBS bestehst, mit JScript ginge es analog, ...
Dank an Sven!
Ich hole das Thema nach vielen Jahren wieder hoch, weil ich das gleiche Problem / die gleiche Aufgabenstellung habe (hatte), wie der Themen-Ersteller. ThLey hat sich ja nicht mehr gemeldet. Wie er, bin ich absoluter Scripting-Anfänger.
Ich habe lange nach einer Möglichkeit gesucht, die x neuesten Ordner zu behalten - und den Rest zu löschen.
Jetzt habe ich diese Möglichkeit gefunden :)
(Falls ein Admin dies liest, das Thema kann als erfolgreich beantwortet gekennzeichnet werden).
Gruß, Praecox
 

Neue Beiträge