Per effettuare il backup automatico del contenuto di alcune cartelle memorizzate sul disco fisso vi sono, com’è noto, numerose metodologie: è possibile affidarsi all’utilità di Windows, utilizzare programmi “ad hoc” sviluppati da terze parti oppure servirsi di appositi script in grado di sovrintendere l’intera procedura.
Questa volta vi proponiamo uno script VBS, realizzato dalla redazione de IlSoftware.it, che consente di creare una copia del contenuto delle directory indicate dall’utente attraverso la modifica di un file di configurazione (config.ini
). Il nostro script provvede a “leggere” il contenuto del file .INI in modo da stabilire quali cartelle debbono essere oggetto di backup nel caso del sistema in uso.
Per ciascuna macchina presente nella propria infrastruttura, si possono specificare le cartelle il cui contenuto deve essere messo in sicurezza (ad esempio, salvato in un’unità rimovibile).
Lo script VBS s’incarica di creare automaticamente una cartella col nome identico a quello assegnato alla macchina in uso. Tale denominazione corrisponde a quella che compare cliccando con il tasto destro destro sull’icona Computer, in Windows Vista così come in Windows 7, quindi sulla voce Proprietà:
In Windows XP, è il nome che può essere rilevato cliccando con il tasto destro del mouse sull’icona Risorse del computer, su Proprietà, infine sulla scheda Nome computer:
all’interno di un’unità di memorizzazione esterna (un hard disk rimovibile od una comunissima chiavetta USB).
Facendo doppio clic sul file backup.vbs
(che può essere rinominato come meglio si crede, lasciando però inalterata l’estensione .VBS), lo script inizierà col creare, nell’unità dalla quale è stato lanciato, una cartella col nome corrispondente a quello del sistema in uso. Come passo successivo, il file VBS attingerà alle informazioni contenute nel file di configurazione config.ini
ed avvierà la procedura di copia del contenuto delle cartelle in esso indicate.
A tal proposito, va evidenziato come lo script – per ciascun file – provveda a controllarne l’ultima data di modifica. Se un file presente nella directory sorgente risulta più aggiornato della versione ospitata nella cartella di backup, lo script VBS provvede ad effettuarne una copia. Viceversa, se le date di modifica sono identiche, non verrà effettuata la copia del file sull’unità di backup in modo da risparmiare tempo prezioso.
Il primo backup, infatti, a seconda delle dimensioni delle cartelle, può richiedere molto tempo per poter essere portato a completamento. Facendo successivamente doppio clic sul file VBS, questo provvederà a copiare solamente i file aggiornati riducendo nettamente le tempistiche necessarie per concludere l’operazione.
Dopo aver estratto i file backup.vbs
e config.ini
, ad esempio, in un’unità rimovibile, bisognerà cominciare con l’impostazione del file di configurazione. Il file config.ini
, di default, si presenta così come segue:
; File di configurazione ; ISTRUZIONI: ; Per richiedere il backup del contenuto di cartelle specifiche, è necessario utilizzare la seguente struttura: ; ; [NOMECOMPUTER] ; 1=C:\Documents and Settings\nomeutente\Documents\cartella ; 2=D:\Lavori\relazioni
Il file di configurazione è vuoto: come si vede contiene solo alcuni commenti (ogni riga inizia col carattere ;
).
E’ necessario, a questo, punto inserire il nome del computer correntemente in uso racchiundendolo tra due parentesi quadre. Al di sotto di tale indicazione (detta “sezione“; ved. questa pagina per maggiori informazioni sulla struttura dei file .INI), si devono indicare le cartelle oggetto di backup.
I percorsi debbono essere specificati nella forma seguente:
1=C:\Lavori
2=C:\Documents and Settings\Michele\Documents\Bozze
3=D:\Archivi\2011
Ciascun percorso, insomma, deve essere associato ad un numero progressivo (da 1 a n).
Esempio di un file di configurazione:
; File di configurazione ; ISTRUZIONI: ; Per richiedere il backup del contenuto di cartelle specifiche, è necessario utilizzare la seguente struttura: ; ; [NOMECOMPUTER] ; 1=C:\Documents and Settings\nomeutente\Documents\cartella ; 2=D:\Lavori\relazioni [HP-PC] 1=C:\Documents and Settings\Michele\Documents\Articoli IlSoftware.it 2=C:\Documents and Settings\Michele\Documents\HTML5 3=C:\Documents and Settings\Michele\Documents\Documenti personali [VAIO-PC] 1=C:\Relazioni
In questo esempio, com’è facile verificare, ogniqualvolta lo script VBS dovesse essere avviato sul sistema denominato “HP-PC” verrà automaticamente copiato il contenuto delle tre cartelle indicate mentre nel caso del sistema “VAIO-PC”, solamente la directory C:\Relazioni
.
Facendo doppio clic sul file .VBS, inizierà l’operazione di copia vera e propria che sarà estesa a tutte le eventuali sottocartelle che dovessero essere presenti all’interno delle directory riportate dall’utente nel file .INI.
Al termine della procedura, lo script mostrerà un messaggio di cortesia che riporta, tra l’altro, il numero dei file copiati:
Nel caso in cui tutti i file presenti nella directory sorgente dovessero avere la medesima data di modifica degli elementi conservati nell’unità di backup, verrebbe mostrato il messaggio seguente (0 file copiati):
Riportiamo il contenuto del file VBS che abbiamo preparato:
' BACKUP AUTOMATICO FILE E CARTELLE - versione 0.1.2 - 16.05.2011 ' File di esempio realizzato da Michele Nasi, IlSoftware.it - www.ilsoftware.it ' ----------------------------------------------------------------------------- 'recupera il nome associato alla macchina in uso Set WshNetwork = WScript.CreateObject("WScript.Network") computername = WshNetwork.ComputerName Set WshShell = WScript.CreateObject("WScript.Shell") Const FOF_CREATEPROGRESSDLG = &H4& Const FOF_NOCONFIRMATION = 16 Const FOF_NOCONFIRMDIRCREATE = 512 'recupera la cartella dalla quale è eseguito lo script VBS ParentFolder = WshShell.CurrentDirectory 'crea una cartella col nome attribuito al sistema in uso creadirectory ParentFolder,computername if right(ParentFolder,1)<>"\" then ParentFolder=ParentFolder&"\" Set fso = CreateObject("Scripting.FileSystemObject") 'imposta la cartella di destinazione (unitàcorrente:\nomecomputer\) ComputernameFolder=ParentFolder&computername&"\" c=1 f=0 do SourceFolder=ReadIni(ParentFolder&"config.ini",computername,c) if SourceFolder="" and c=1 then WScript.Echo "Il file di configurazione (config.ini) non è stato inizializzato per il sistema in uso ("& computername &")."&vbcrlf&"Aprirlo con un normale editor di testo e fare riferimento alle istruzioni." if SourceFolder=" " and c=1 then WScript.Echo "Per il sistema in uso non è stata indicata alcuna cartella sorgente."&vbcrlf&"Aprire il file config.ini con un normale editor di testo e fare riferimento alle istruzioni per modificarlo." if trim(SourceFolder)<>"" then if fso.FolderExists(SourceFolder) then creadirectory ComputernameFolder,lastfolder(SourceFolder) DestinationFolder=ComputernameFolder&lastfolder(SourceFolder) copia SourceFolder,DestinationFolder else WScript.Echo "La cartella "& SourceFolder &" non esiste."&vbcrlf&"Impossibile copiare i dati nell'unità di destinazione." end if end if c=c+1 loop until SourceFolder="" or SourceFolder=" " function copia(sorgente,destinazione) Set fileCol = fso.GetFolder(sorgente).Files Set dirCol = fso.GetFolder(sorgente).Subfolders if right(destinazione,1)<>"\" then destinazione=destinazione&"\" For Each objSubfolder in dirCol sottodirectory=objSubfolder.Name creadirectory destinazione,sottodirectory copia sorgente&"\"&sottodirectory,destinazione&sottodirectory Next ' WScript.Echo sorgente &" -- "& destinazione For Each objFile in fileCol If not fso.FileExists(destinazione & objFile.Name) Then ' Copia il file se non esiste nella cartella di destinazione objFile.Copy destinazione f=f+1 Else If objFile.DateLastModified > fso.GetFile(destinazione & objFile.Name).DateLastModified Then 'Se il file sorgente è più recente di quello di destinazione procede con la copia objFile.Copy destinazione, True f=f+1 End If End If Next Set fileCol=Nothing Set dirCol=Nothing end function function lastfolder(percorso) s=array() if instr(percorso,"\") > 0 then s=split(percorso,"\") lastfolder = s(ubound(s)) end if end function function creadirectory (nomedirectory,dirdacreare) Set objShell = CreateObject("Shell.Application") Set objFolder = objShell.NameSpace(nomedirectory) objFolder.NewFolder dirdacreare Set objFolder=Nothing Set objShell=Nothing end function Function ReadIni(myFilePath, mySection, myKey) ' This function returns a value read from an INI file ' ' Arguments: ' myFilePath [string] the (path and) file name of the INI file ' mySection [string] the section in the INI file to be searched ' myKey [string] the key whose value is to be returned ' ' Returns: ' the [string] value for the specified key in the specified section ' ' CAVEAT: Will return a space if key exists but value is blank ' ' Written by Keith Lacelle ' Modified by Denis St-Pierre and Rob van der Woude ' Riga 128 modificata da Michele Nasi Const ForReading = 1 Const ForWriting = 2 Const ForAppending = 8 Dim intEqualPos Dim objFSO, objIniFile Dim strFilePath, strKey, strLeftString, strLine, strSection Set objFSO = CreateObject("Scripting.FileSystemObject") ReadIni = "" strFilePath = Trim( myFilePath ) strSection = Trim( mySection ) strKey = Trim( myKey ) If objFSO.FileExists( strFilePath ) Then Set objIniFile = objFSO.OpenTextFile( strFilePath, ForReading, False ) Do While objIniFile.AtEndOfStream = False strLine = Trim( objIniFile.ReadLine ) ' Check if section is found in the current line If LCase( strLine ) = "[" & LCase( strSection ) & "]" Then if not objIniFile.AtEndOfStream then strLine = Trim(objIniFile.ReadLine) ' Parse lines until the next section is reached Do While Left( strLine, 1 ) <> "[" ' Find position of equal sign in the line intEqualPos = InStr( 1, strLine, "=", 1 ) If intEqualPos > 0 Then strLeftString = Trim( Left( strLine, intEqualPos - 1 ) ) ' Check if item is found in the current line If LCase( strLeftString ) = LCase( strKey ) Then ReadIni = Trim( Mid( strLine, intEqualPos + 1 ) ) ' In case the item exists but value is blank If ReadIni = "" Then ReadIni = " " End If ' Abort loop when item is found Exit Do End If End If ' Abort if the end of the INI file is reached If objIniFile.AtEndOfStream Then Exit Do ' Continue with next line strLine = Trim( objIniFile.ReadLine ) Loop Exit Do End If Loop objIniFile.Close Else WScript.Echo strFilePath & " non esiste. Crearlo e riavviare lo script." Wscript.Quit 1 End If End Function Set fso=Nothing Set WshShell=Nothing Set WshNetwork=Nothing WScript.Echo "Operazione completata."&vbcrlf&f&" file copiati." WScript.Quit
Per le operazioni di lettura del file .INI abbiamo “riciclato” il codice realizzato da K. Lacelle e modificato da Denis St-Pierre, Johan Pol e Rob van der Woude (pubblicato a questo indirizzo). Per evitare la comparsa di un errore nel caso di una scorretta configurazione del file .INI, abbiamo modificato la riga 128.
La parte principale dello script è quella compresa tra le righe 26 e 43 (ciclo do ... loop
). Per ciascuna directory oggetto di backup (letta dal file .INI attraverso l’istruzione alla riga 29), viene dapprima creata una cartella – ove necessario – nel percorso di destinazione (riga 35) quindi invocata la funzione copia
. Si tratta di un algoritmo ricorsivo (righe 45-74) che, per ciascuna eventuale sottocartella, provvede a richiamare se stesso effettuando la copia dei file, se necessario. Utilizzando il ciclo for ... next
(righe 59-71), infatti, si provvede a copiare tutti quei file che non esistono ancora nel percorso di destinazione mentre si evita la copia di quegli elementi che non appaiono aggiornati (stessa data di modifica sia nella directory sorgente che in quella di destinazione).
Qualora aveste dei dubbi sul funzionamento dello script, vi invitiamo a richiedere spiegazioni inviando un commento in calce a questo articolo.