Script Para Borrar Ficheros Viejos
Posted by urpiano en viernes 9 \09\+01:00 febrero \09\+01:00 2007
Este script permite borrar los ficheros contenidos en uina carpeta cuya fecha de última modificación sea anterior a la fecha que se le pasa como parámetro.
'Este script recibe como parámetros una ruta de carpeta y una fecha en
'formato DD/MM/YYYY y borra todos aquellos ficheros ubicados en la ruta
'que indica la carpeta que tengan como fecha de última modificación
'una igual o anterior a la recibida como parámetro. Si se añade el
'modificador /R el borrado se hará en todo el árbol cuya raíz es el
'parámetro de ruta recibido. Ejemplo:
'cscript borrar-ficheros-hasta-fecha.vbs /R c:Carpeta 23/11/2003
'© Noviembre de 2006 - Fernando Reyes
'Febrero de 2007:
'Se añade el parámetro /R por el cual se realizará un borrado de forma
'recursiva, esto es, de la carpeta recibida y de todo el subárbol que
'contiene
Option Explicit
Dim str_Fecha
Dim bol_Recursivo
Dim str_Ruta
Dim dth_Fecha
WScript.Echo "1.- " & WScript.Arguments(0)
WScript.Echo "2.- " & WScript.Arguments(1)
'Comprobamos que hemos recibido el número correcto de parámetros
'recibidos
If WScript.Arguments.Unnamed.Count <> 2 Then
WScript.Echo "Error 1: Número de parámetros incorrecto. " & _
"Se deben pasar 2:" & _
vbCrLf & vbCrLf & _
" 1.- Ruta de la carpeta donde borrar los ficheros." & _
vbCrLf & _
" 2.- Fecha de última modificación a partir de la cual" & _
vbCrLf & _
" se borrarán los ficheros anteriores y de la misma fecha " & _
"(DD/MM/YYYY)." & vbCrLf & vbCrLf & _
"Se puede agregar el modificador /R para que haga " & _
"el borrado de forma recursiva" & vbCrLf & _
vbCrLf & _
"Ejemplo:" & vbCrLf & vbCrLf & _
"cscript borrar-ficheros-hasta-fecha.vbs /R " & _
"c:Carpeta 23/11/2003"
WScript.Quit 1
End If
If WScript.Arguments.Named.Exists("R") Then bol_Recursivo = True
str_Ruta = WScript.Arguments.Unnamed(0)
dth_Fecha = WScript.Arguments.Unnamed(1)
Call s_BorrarFicheros(str_Ruta, dth_Fecha, bol_Recursivo)
Sub s_BorrarFicheros(str_Ruta, dth_Fecha, bol_Recursivo)
Dim obj_FSO
Dim obj_Carpeta
Dim obj_Fichero
'Creamos el objeto FileSystemObject
Set obj_FSO = CreateObject("Scripting.FileSystemObject")
'Comprobamos que la ruta recibida sea válida
If not obj_FSO.FolderExists(str_Ruta) Then
WScript.Echo "Error 2: La carpeta " & str_Ruta & _
" recibida como parámetro no existe."
Set obj_FSO = Nothing
WScript.Quit 2
End If
'Comprobamos que la fecha recibida sea válida
If not IsDate(dth_Fecha) Then
WScript.Echo "Error 3: La fecha " & dth_Fecha & _
" recibida como parámetro no es una fecha válida."
Set obj_FSO = Nothing
WScript.Quit 3
End If
'Creamos el objeto carpeta
Set obj_Carpeta = obj_FSO.GetFolder(str_Ruta)
'Recorremos los ficheros contenidos en la carpeta
For Each obj_Fichero In obj_Carpeta.Files
'Comprobamos que la fecha de última modificación del fichero
'sea anterior o igual a la recibida como parámetro
If DateValue(obj_Fichero.DateLastModified) <= _
DateValue(dth_Fecha) Then
'En caso afirmativo, mostramos el nombre y fecha del fichero
'y lo borramos
WScript.Echo "Borrando " & obj_Fichero.Name & _
": Modificado el " & _
obj_Fichero.DateLastModified
'Borramos el fichero incluso en el caso de ser de sistema, si
'quisiéramos que no se borren los de sistema, tan sólo
'debemos eliminar el True o sustituirlo por False
obj_Fichero.Delete True
End If
Next
'Si queremos que se recorra todo el subárbol de carpetas...
If bol_Recursivo Then
'Definimos un objeto para las subcarpetas
Dim obj_Subcarpeta
'Recorremos las subcarpetas en este bucle
For Each obj_Subcarpeta In obj_Carpeta.Subfolders
'Llamada recursiva para borrar los ficheros de la
'subcarpeta
Call s_BorrarFicheros(obj_Subcarpeta.Path,dth_Fecha, _
bol_Recursivo)
Next
Set obj_Subcarpeta = Nothing
End If
'Nos limpiamos el culito antes de terminar :-))
Set obj_Fichero = Nothing
Set obj_Carpeta = Nothing
Set obj_FSO = Nothing
End Sub
thefame said
Hola.
Antes de nada felicitarte por el script.
La verdad es que le encuentro un pequeño problema. Como he de hacerlo para que sea recursivo la busqueda de ficheros en la carpeta que le dices??
Muchas gracias.
Atentamente,
thefame
thefame said
Hola de nuevo.
He estado indagando en el tema y he conseguido hacer que sea recursivo solo en un solo nivel, aunque creo que para hacerlo recursivo mas de 1 vez tendremos que repetir el codigo que pongo tantas veces como queramos podras llegar a hacerlo recursivo.
Dim sf
Dim f1
Set sf = obj_Carpeta.SubFolders
For Each f1 in sf
For Each obj_Fichero In f1.Files
'Comprobamos que la fecha de última modificación del fichero sea anterior
'o igual a la recibida como parámetro
If DateValue(obj_Fichero.DateLastModified)
thefame said
Codigo completo:
Dim sf
Dim f1
Set sf = obj_Carpeta.SubFolders
For Each f1 in sf
For Each obj_Fichero In f1.Files
‘Comprobamos que la fecha de última modificación del fichero sea anterior
‘o igual a la recibida como parámetro
If DateValue(obj_Fichero.DateLastModified)
thefame said
Hola de nuevo.
No se que pasa que no me deja poner el codigo entero.
Pido al administrador que borre el post anterior.
Gracias
urpiano said
Acabo de subir esta nueva versión del script que hace lo que quieres. Cuando desees que el borrado sea recursivo, debes añadir el modificador «/R»
Silverio said
Hola buenas,
Gracias por la ayuda que supone a la gente que no dominamos los script.
Estoy intentando que me funcione pero me da varios errores. Al borrar de manera recursiva, con el /R, supone un tercer argumento, por lo que argument(0) no sería la ruta si no el /R. Luego a la hora de buscar en las subcarpetas le pasas la ruta, pero me parece que se produce un bucle en: Set obj_Carpeta = obj_FSO.GetFolder(WScript.Arguments(0)), porque vuelve a coger el valor de la ruta pasada desde la línea de comandos.
Si puedes echarme una mano, gracias de antemano y un saludo.
urpiano said
¡Esto me pasa por sobrado y por no haber probado el script antes de publicarlo! :-) Hay un gazapo en la línea:
Set obj_Carpeta = obj_FSO.GetFolder(WScript.Arguments(0))
Debería ser:
Set obj_Carpeta = obj_FSO.GetFolder(str_Ruta)
Este gazapo provoca el bucle que dices, pues hace que siempre se procese la misma carpeta.
Hay otro gazapo en la línea:
If DateValue(obj_Fichero.DateLastModified) <= _
DateValue(WScript.Arguments(1)) Then
Debería ser:
If DateValue(obj_Fichero.DateLastModified) <= _
DateValue(dth_Fecha) Then
Este gazapo no provoca ningún error si se sitúa el modificador /R como último parámetro; en el momento que que sea el primero o el segundo el error se produce.
Estas líneas eran correctas cuando el script no era recursivo, le añadí la recursividad y se me escaparon. Como no estaba el modificador /R, se podía uno referir a los parámetros como WScript.Arguments(0) o WScript.Arguments(1); una vez añadido el modificador /R, es necesario hacerlo como WScript.Arguments.Unnamed(0) y WScript.Arguments.Unnamed(1), de esa manera no se falsea si pones /R delante, o en medio, de los otros parámetros.
Gracias por avisarme, lo he retocado, espero que te funcione ahora sin problemas.
kike said
Está genial.
Tengo una duda, a ver si me podeis ayudar. Utilizo un metodo similar para visualizar las imágenes de una carpeta del servidor.
dim fs2,fo2,x2
set fs2=Server.CreateObject(«Scripting.FileSystemObject»)
Path = session(«eldirectoriofisico»)
set fo2=fs2.GetFolder(path)
for each x2 in fo2.files
‘visualizo la imagen de x2
next
Todo perfecto pero el tema es que lo visualiza ordenado por nombre del fichero y a mi me interesa que lo visualice ordenado por fecha de modificación. Sabeis como puedo hacerlo?
Gracias
urpiano said
Para eso necesitas cargar los nombres de los ficheros y su tamaño en un array de dos dimensiones, ordenar el array y luego recorrelo. Mira si te ayuda este enlace:
ASPFAQS (118): FileSystemObject – How to Sort Files
enec said
Buenas,
He probado el script de forma no recursiva y funciona correctamente, el problema viene cuando intento hacerlo recursivo con /R, por mucho que cambie el modificador de posicion tengo siempre el mismo problema, aqui lo muestro:
C:\prueba>cscript scritp.vbs yo 06/06/2007 /R
Microsoft (R) Windows Script Host versión 5.6
Copyright (C) Microsoft Corporation 1996-2001. Reservados todos los derechos.
1.- yo
2.- 06/06/2007
Error 1: Número de parámetros incorrecto. Se deben pasar 2:
1.- Ruta de la carpeta donde borrar los ficheros.
2.- Fecha de última modificación a partir de la cual
se borrarán los ficheros anteriores y de la misma fecha (DD/MM/YYYY).
Se puede agregar el modificador /R para que haga el borrado de forma recursiva
Ejemplo:
cscript borrar-ficheros-hasta-fecha.vbs /R c:\Carpeta 23/11/2003
C:\prueba>
¿que hago mal? ¿alguna solucion?
urpiano said
No es culpa tuya, si no mía por no haberlo testeado. El problema estaba en la línea:
If WScript.Arguments.Count <> 2 Then
Que debería haber sido:
If WScript.Arguments.Unnamed.Count <> 2 Then
Lo he modificado, prueba ahora
enec said
Gracias, :-)
ya funciona correctamente, solo que hay que cambiar
Call s_BorrarFicheros(obj_Subcarpeta.Path,dthFecha, _
bol_Recursivo)
por
Call s_BorrarFicheros(obj_Subcarpeta.Path,dth_Fecha, _
bol_Recursivo)
urpiano said
Lo dicho, que me pasa por no testearlo. El script lo desarrollé sin recursividad, por petición de un oyente le hice la recursividad con prisas, no tenía demasiado tiempo para andar testeando en condiciones, lo que ha provocado este tipo de errores. Cada vez que le he metido mano desde entonces me ha pillado a contrapié y lo he depurado sin probar. Muchas gracias por buscarme ese gazapo. Paso a corregirlo.
Martin said
Muy buen trabajo, ante todo. Lo que te queria consultar, ante la imposibilidad de hacerlo yo dado que no programo en este lenguaje, es si existe posibilidad de que haga exactamente lo que hace, pero solo en cierto tipo de archivos. Es decir, poder pasarle que borre solo archivos de audio .mp3 o de video .wmv, por decir algo.
Gracias desde ya por tan buen trabajo, nos vemos.
Martin said
Hola a todos,
Pude solucionar el tema de elegir un tipo de archivos especifico, si bien seguramente no es de la mejor manera. Simplemente se modifico la linea:
If DateValue(obj_Fichero.DateLastModified) <= _
DateValue(dth_Fecha) Then
Por esta otra:
If DateValue(obj_Fichero.DateLastModified) <= _
DateValue(dth_Fecha) and (obj_FSO.GetExtensionName(obj_Fichero.Path)=»wmv» or obj_FSO.GetExtensionName(obj_Fichero.Path)=»WMV») Then
Saludos!
urpiano said
Martín:
Es correcta tu solución, pero sería más simple si usases UCase o LCase:
If DateValue(obj_Fichero.DateLastModified) <= DateValue(dth_Fecha) _
And LCase(obj_FSO.GetExtensionName(obj_Fichero.Path))=”wmv” Then
No obstante, a ver si tengo un rato y retoco el script para que permita poner patrones además de fechas.
Script VBScript Para Borrar Ficheros Viejos (2) « El Blog de Gualtrysoft said
[…] por urpiano on 11/10/07 Basado en un script mío anterior, este script sirve para borrar ficheros cuya fecha de última modificación sea igual o anterior a […]
IT said
Buenas días,
Tengo un script hecho que me elimina los archivos con más de dos meses de antigüedad en una carpeta llamada Prueba (adjunto código):
—————————————————————————————–
Option Explicit
Const DIAS = 60
Const DIRECTORIO = «c:\Prueba\Log»
Dim OBJETO, PROPIEDAD, GRUPODEARCHIVOS, ARCHIVO
Set OBJETO = WScript.CreateObject(«Scripting.FileSystemObject»)
Set PROPIEDAD = OBJETO.GetFolder (DIRECTORIO)
Set GRUPODEARCHIVOS = PROPIEDAD.Files
For Each ARCHIVO in GRUPODEARCHIVOS
If DateDiff («d», ARCHIVO.DateCreated, Now) > DIAS Then
ARCHIVO.Delete
End If
Next
———————————————————————————————-
El problema viene porque la carpeta Prueba tiene subcarpetas y dicho script no funciona para éstas. ¿Alguien podría indicarme cómo hacer recursivo mi script?
Gracias de antemano.
Saludos
urpiano said
Para que te procese las subcarpetas, tienes que hacer el script recursivo, poniendo el cuerpo dentro de un procedimiento que se llame a sí mismo con las subcarpetas que contenga la carpeta que se recibe como parámetro:
—————————————————————-
Option Explicit
Const DIAS = 60
Const DIRECTORIO = "c:\Prueba\Log"
Call s_BorrarFicheros(DIRECTORIO)
Sub s_BorrarFicheros(str_Ruta)
Dim OBJETO, PROPIEDAD, GRUPODEARCHIVOS, ARCHIVO,CARPETA
Set OBJETO = WScript.CreateObject("Scripting.FileSystemObject")
Set PROPIEDAD = OBJETO.GetFolder (DIRECTORIO)
Set GRUPODEARCHIVOS = PROPIEDAD.Files
For Each ARCHIVO in GRUPODEARCHIVOS
If DateDiff ("d", ARCHIVO.DateCreated, Now) > DIAS Then
ARCHIVO.Delete
End If
Next
For Each CARPETA In PROPIEDAD.SubFolders
Call s_BorrarFicheros(CARPETA.Path)
Next
End Sub
—————————————————————-
Si te fijas, esto mismo es lo que hace mi script, con lo que con una ligera modificación, puede servirte. Tú buscas la fecha en la propiedad Fecha de creación (DateCreated), mientras que mi script lo hace en la propiedad Fecha de última modificación (DateLastModified). Para que mi script lo haga con esta fecha, basta con modificar la línea:
If DateValue(obj_Fichero.DateLastModified) <= _
DateValue(dth_Fecha) Then
Por:
If DateValue(obj_Fichero.DateCreated) <= _
DateValue(dth_Fecha) Then
IT said
Hola Urpiano,
Antes de nada agradecerte tu pronta respuesta, he modificado mi script tal y como me indicaste y me ha saltado un mensaje de error de Windows Script Host, es el siguiente:
Error: Memoria insuficiente: ‘WSCript.CreateObject’
Código: 800A0007
El fichero que tenía en la carpeta raíz me lo ha borrado, pero el de la subcarpeta no.
¿Alguna idea de por qué me salta el error?
Gracias de antemano.
Saludos
urpiano said
Yo creo que porque hay demasiados objetos y porque no se destruyen. Mira si así se arregla:
Option Explicit
Const DIAS = 60
Const DIRECTORIO = "c:\Prueba\Log"
Call s_BorrarFicheros(DIRECTORIO)
Sub s_BorrarFicheros(str_Ruta)
Dim OBJETO, PROPIEDAD, ARCHIVO, CARPETA
Set OBJETO = WScript.CreateObject("Scripting.FileSystemObject")
Set PROPIEDAD = OBJETO.GetFolder (DIRECTORIO)
For Each ARCHIVO in PROPIEDAD.Files
If DateDiff ("d", ARCHIVO.DateCreated, Now) > DIAS Then
ARCHIVO.Delete
End If
Next
For Each CARPETA In PROPIEDAD.SubFolders
Call s_BorrarFicheros(CARPETA.Path)
Next
Set CARPETA = Nothing
Set ARCHIVO = Nothing
Set PROPIEDAD = Nothing
Set OBJETO = Nothing
End Sub
IT said
Hola Urpiano,
El error se sigue produciendo y ya no sé que hacer. ¿Alguna sugerencia?
Gracias de antemano.
Saludos
urpiano said
:XXXXXXXXXXXXXXXXXXXXXXXXXXXXXD
¡¡Menuda Tontería!!
El problema es que he llamado al parámetro que recibe el procedimiento «str_Ruta», sin embargo en el procedimiento no obtengo la carpeta str_Ruta, si no la carpeta «DIRECTORIO»; esto hace que una vez ha procesado DIRECTORIO, liste sus subcarpetas y en la llamada recursiva, siempre se obtenga la carpeta DIRECTORIO, así una y otra vez, en un bucle infinito. Basta con sustituir la línea:
Set PROPIEDAD = OBJETO.GetFolder(DIRECTORIO)
Por esta otra:
Set PROPIEDAD = OBJETO.GetFolder(str_Ruta)
No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo. No volveré a escribir código y no probarlo.
IT said
Muchísimas gracias Urpiano, ahora ya me funciona perfectamente.
Eres un crack.
Saludos
Frantesi said
Buenos días,
empezaré diciendo que no tengo ni idea de scripts y agradeceré cualquier ayuda prestada.
El caso es que necesito hacer una buena limpieza de archivos, pero no puedo basarme en la fecha de modificación. ya que algunos son solo de consulta. Necesitaría poder borrar los archivos cuya «fecha de acceso» sea más antigua que una fecha dada.
Es posible??
Muchas gracias de antemano por vuestra ayuda.
Saludos cordiales
urpiano said
Frantesi,
Lo que pides es muy fácil de hacer, simplemente debes sustituir la línea:
If DateValue(obj_Fichero.DateLastModified) <= _
DateValue(dth_Fecha) Then
Por esta otra
If DateValue(obj_Fichero.DateLastAccessed) <= _
DateValue(dth_Fecha) Then
tulop said
El problema que he encontrado es que cuando el archivo en está en uso el script casca, habría de hacer para que no cascara e eliminara de forma recursiva todo el árbol de directorios seleccionado hasta terminar y saltándose los ficheros abiertos o aquellas rutas que superen los 256 caracteres.
Muchas gracias
urpiano said
Eso es sencillo:
Script para borrado de archivos « Mikel Arizkuren Botello said
[…] encontrado en https://urpiano.wordpress.com/2007/02/09/script-para-borrar-ficheros-viejos/ un script para el borrado de archivos en función de fecha. Funciona realmente […]
Richard said
Buenas tardes estimado, Saludos!
Disculpe la molestia, tengo un script sencillo que uso desde hace tiempo, sin embargo algunos procesos han cambiado y se han creados subcarpetas, pero mi script no las elimina.
Quería saber si me falta actualizar algún comando en mi script para realizar el borrado completo incluyendo las subcarpetas.
Este es mi script: DeleteFilesOld.vbs
sFolder = «G:\BackupArchive»
iMaxAge = 30
Set oFSO = CreateObject(«Scripting.FileSystemObject»)
If oFSO.FolderExists(sFolder) Then
for each oFile in oFSO.GetFolder(sFolder).Files
If DateDiff(«d», oFile.DateLastModified, Now) > iMaxAge Then
‘wscript.echo «Deleting oFile.Name»
oFile.Delete
End If
next
End If
Agradezco de antemano la ayuda que me pueda brindar,
Saludos,
Richard
Jael said
Hola a todos.
Disculpen que los moleste pero quiero hacer mi script recursivo, para que borre los archivos de todas las subcarpetas del directorio principal pero no lo logro, alguien puede ayudarme?
Dim oFSO, oFolder, sDirectoryPath
Dim oFileCollection, oFile, sDir
Dim iDaysOld
sDirectoryPath = «D:\Todo»
iDaysOld = 20
Set oFSO = CreateObject(«Scripting.FileSystemObject»)
Set oFolder = oFSO.GetFolder(sDirectoryPath)
Set oFileCollection = oFolder.Files
For each oFile in oFileCollection
If LCase(Right(Cstr(oFile.Name), 3)) = «txt» Then
If oFile.DateLastModified < (Date() – iDaysOld) Then
oFile.Delete(True)
End If
End If
Next
Set oFSO = Nothing
Set oFolder = Nothing
Set oFileCollection = Nothing
Set oFile = Nothing
Muchas graicas por la ayuda…