So some background information of what I'm trying to accomplish. I have a log file in a location that I am copying to another location and renaming with a timestamp in the name, but leaving the attributes of the file the same. I also have it to where depending on a variable, it may make this file hidden. This all works as intended, and is triggered through a vbscript. The thing I am now trying to accomplish is before copying this file, I want to look at it's last modified date. I then want to compare that to each of the files in this other storage location, and if this matches then the file in the storage folder will be moved to a subfolder to store duplicate files.
#echo off
::////CONFIGURATION////
:: Set source folder and target folder in quotations
Set source="C:\Users\cafogle\Desktop\TEST\Source"
Set target="C:\Users\cafogle\Desktop\TEST\Destination"
:: Set folder name of where to keep copied files with duplicate last modified dates, without quotations
Set dumpfolder=filedump
:: The file name (including extension) without quotations
Set file=Log.txt
:: The file extension without quotations
Set filetype=.txt
:: If you want the file copied to be hidden, set this variable to '+h' If not, change it to '-h'
Set hidden=+h
::////SCRIPT////
:: Move duplicate files based on last modified date
Set reffilename=%file:~0,1%*%filetype%
for /f "delims=" %%i in ('"forfiles /P %source%\ /M %file% /C "cmd /c echo #ftime" "') do set reffiletime=%%i
for /f "delims=" %%k in ('"forfiles /P %target%\ /M %reffilename% /C "cmd /c echo #ftime" "') do (
(set reftimetemp=%%k)
for /f "delims=" %%j in ('"forfiles /P %target%\ /M %reffilename% /C "cmd /c echo #file" "') do (
(set reffiletemp=%%j)
if (%reftimetemp%==%reffiletime%) (robocopy %target% %target\%dumpfolder% %reffiletemp% /mov /a+:r)
)
)
pause
:: Running robocopy
Robocopy %source% %target% %file% /a+:r
taskkill /F /IM robocopy.exe
:: Retrieve local date and time from PC and save it to MyDate variable
for /f "skip=1" %%x in ('wmic os get localdatetime') do if not defined MyDate set MyDate=%%x
set timestamp=%MyDate:~0,4%-%MyDate:~4,2%-%MyDate:~6,2%_%MyDate:~8,2%_%MyDate:~10,2%_%MyDate:~12,2%
:: Set variable for new file name
Set newfilename=%file%_%timestamp%%filetype%
:: Directing the rename function to destination folder and file name, this will then rename the file with current date and time.
ren %target%\%file% "%newfilename%"
:: Determine if file should be made hidden and hide if necessary
attrib %target%\%newfilename% %hidden%
This is the entire batch file, but the only part that I am having issues with is:
:: Move duplicate files based on last modified date
Set reffilename=%file:~0,1%*%filetype%
for /f "delims=" %%i in ('"forfiles /P %source%\ /M %file% /C "cmd /c echo #ftime" "') do set reffiletime=%%i
for /f "delims=" %%k in ('"forfiles /P %target%\ /M %reffilename% /C "cmd /c echo #ftime" "') do (
(set reftimetemp=%%k)
for /f "delims=" %%j in ('"forfiles /P %target%\ /M %reffilename% /C "cmd /c echo #file" "') do (
(set reffiletemp=%%j)
if (%reftimetemp%==%reffiletime%) (robocopy %target% %target\%dumpfolder% %reffiletemp% /mov /a+:r)
)
)
I've tried just about everything I can find, but the main issue is finding a way to take the date from the source file, and then comparing it to each individual file and moving them individually based on the outcome.
Any assistance would be greatly appreciated, as I have exhausted every option I can find.
Thanks!
I'm using a batch file now to delete all files ending in .snp that are older than 180 days. The code below works to delete all files ending in .snp under the root folder
C:\Program Files\Snapshots
But I recently discovered that within the Snapshots folder there are folders organized by date
"1-10-2014, 12-20-2014, 10-15-2014 etc.."
and that the below line of code doesn't work to recursively search through each directory and is therefore not deleting.
What changes should I make to this code to have it recursively search through folders within a root folder and delete files that are greater than 180 days?
forfiles /M *.snp /P "C:\Program Files\Snapshots" /S /D -180 /C "cmd /c del /F /Q #path"
Without the /D (Date) it workes for sub-folders
forfiles /M *.txt /P "C:\hlpme" /S /C "cmd /c del /f /q #path
but you obviously want the date to be there
then in CMD
forfiles /D -180 /M *.txt /P "C:\hlpme" /S /C "cmd /c del /f /q #path
The /D before the Pathname selects all files that have been changed more than 180 days ago
The best option for highest reliability is to combine the strengths of the For command with the FORFILES commands to allow each one to do what they do best.
Set str_Ext=*.snp
Set int_Age=-180
For /R "%~dp0" %%D IN (.) DO (
For /F "usebackq tokens=*" %%F IN (`FORFILES /P "%%~D" /m %str_Ext% /D %int_Age% 2^>nul`) DO (
Call :s_Del_File "%%~D" "%%~F"
)
)
Goto :EOF
:s_Del_File
Set "str_DIR=%~1"
Set "str_FIL=%~2"
Set "str_DIR=%str_DIR:~0,-1%"
DEL /F/Q/A "%str_DIR%%str_FIL%"
Goto :EOF
Within the second FOR command, the backquote (~ key) contains the FORFILES command and uses the console output to call a batch subroutine to delete the specified file.
Spaces in folder and file names will not slow this beast down, and the double quotes ["] around the Set commands will allow the process to work with folders and files that have parentheses in them or other exotic, but allowable characters.
Description:
I want to use a syntax like COMP I:\folder1 Z:\folder2 to compare all files in my I drive with the content of my z drive. I only need to compare their names to see if one exsists in the other. I need to recurse into the subdirectories because there are many located in both drives, I understand I need to use a batch script using a FOR loop and the PUSHD and POPD command.
QUESTION:
How do I do this?
From the output from FOR /?
FOR /R [[drive:]path] %variable IN (set) DO command [command-parameters]
Walks the directory tree rooted at [drive:]path, executing the FOR
statement in each directory of the tree. If no directory
specification is specified after /R then the current directory is
assumed. If set is just a single period (.) character then it
will just enumerate the directory tree.
So you'd do something like
#echo off
setlocal enabledelayedexpansion ENABLEEXTENSIONS
for /R P:\ %%F in (*.*) DO (
set fileFull=%%~fF
set filePath=%%~pF
set fileDrive=%%~dF
set fileName=%%~nF
set fileExtension=%%~xF
call :checker "!filePath!" "!fileName!" "!fileExtension!"
)
goto :eof
:checker
set fileTarget="c:%~1%~2%~3"
if not exist %fileTarget% echo %fileTarget% not found
goto :eof
In this case, the script is getting all the filenames in P:\ and its subdirectories and telling me if the file doesn't exist on the same path in C:
List folder differences over a tree:
This uses robocopy to create the list - don't remove /L as this switch makes robocopy only list the information.
robocopy "d:\source\folder one" "c:\target\folder two" /L /fp /njs /njh /ndl /ns /np /mir
If you really need to avoid third party utilities:
#ECHO OFF
SET FOLDER1=I:\Folder1\
SET FOLDER2=Z:\Folder2\
ECHO SET FNAME=%%1 ^& #ECHO %%FNAME:%FOLDER1%=%%^>^>FILES1.TXT>FILES1.BAT
ECHO SET FNAME=%%1 ^& #ECHO %%FNAME:%FOLDER2%=%%^>^>FILES2.TXT>FILES2.BAT
IF EXIST FILES1.TXT DEL FILES1.TXT
IF EXIST FILES2.TXT DEL FILES2.TXT
FOR /F "tokens=*" %%* IN ('DIR /S /B /ON "%FOLDER1%"') DO CALL FILES1.BAT "%%*"
FOR /F "tokens=*" %%* IN ('DIR /S /B /ON "%FOLDER2%"') DO CALL FILES2.BAT "%%*"
ECHO Files from "%FOLDER1%" which are not found in "%FOLDER2%"
FOR /F "tokens=*" %%* IN (FILES1.TXT) DO (FIND %%* FILES2.TXT >NUL || ECHO %%*)
ECHO Files from "%FOLDER2%" which are not found in "%FOLDER1%"
FOR /F "tokens=*" %%* IN (FILES2.TXT) DO (FIND %%* FILES1.TXT >NUL || ECHO %%*)
I have this script which is created to backup a cube within an application. It runs every saturday and it created a sub folder within the application folder. Due to space requirements I've had to delete the oldest folder every week. I need to create a script to do that.
Here's the backup code:
:: Create folder for App Db if it does not exist
IF NOT EXIST %BACKUPDIR%%1"\"%2 GOTO MAKEDIR
GOTO CONT
:MAKEDIR
mkdir %BACKUPDIR%%1"\"%2
GOTO :CONT
:CONT
cd %BACKUPDIR%%1"\"%2
:: Get todays date
for /f "tokens=2,3,4 delims=/ " %%i in ('date /t') do (
set my_day=%%j
set my_month=%%i
set my_year=%%k )
set datestamp=%my_month%%my_day%%my_year%
::echo %datestamp%
:: Create date folder for app db
IF NOT EXIST %BACKUPDIR%%1"\"%2"\"%datestamp% GOTO MAKEDIRTIMEDATE
:MAKEDIRTIMEDATE
G:
cd %BACKUPDIR%%1"\"%2"\
mkdir %BACKUPDIR%%1"\"%2"\%datestamp%
:: Copy otl, csc, rul, rep files from App to Backup fodler
XCOPY %APPFOLDER%"\app\"%1"\"%2"\*.csc" %BACKUPDIR%%1"\"%2"\"%datestamp% /Y
XCOPY %APPFOLDER%"\app\"%1"\"%2"\*.rul" %BACKUPDIR%%1"\"%2"\"%datestamp% /Y
XCOPY %APPFOLDER%"\app\"%1"\"%2"\*.otl" %BACKUPDIR%%1"\"%2"\"%datestamp% /Y
XCOPY %APPFOLDER%"\app\"%1"\"%2"\*.rep" %BACKUPDIR%%1"\"%2"\"%datestamp% /Y
XCOPY %APPFOLDER%"\app\"%1"\"%2"\*.ind" %BACKUPDIR%%1"\"%2"\"%datestamp% /Y
cd %SCRIPTDIR%
:: Move data file from script dir to backupdir if data file exist If not exit out of code
IF NOT EXIST %SCRIPTDIR%%1"_"%2"_AllData.txt" GOTO EXIT
:END
MOVE %SCRIPTDIR%%1"_"%2"_AllData*.txt" %BACKUPDIR%%1"\"%2"\"%datestamp%
GOTO EXIT
:EXIT
exit /b
As you can see ever week a new folder is created with the creation data as its title (i.e. 102913). That folder is a subfolder of an application. I need a script to deleted the oldest folder.
So far I've tried (using test folders):
FORFILES -p "C:\Oracle\test\New folder\new folder" -s -m *.rul /D -<7> /C "cmd IF #isdir == TRUE" /c del #path
and
forfiles -p "C:\Oracle\test\New folder\new folder" -s -m *.rul /D -<7> /C "cmd /c del #path"
Any suggestion would be useful.
set "backupDir=C:\Oracle\test\New folder\new folder"
for /F "tokens=*" %%f in ('dir /ad /tc /o-d /b "%backupDir%"') do set "oldest=%backupDir%\%%f"
echo "%oldest%"
Get directory list ordered by creation date descending, only incuding directories, in brief format. Last line in list will be stored in variable %oldest% with the working directory prefixed.
I want to have a batch file that will delete all the folders and files in my cache folder for my wireless toolkit.
Currently I have the following:
cd "C:\Users\tbrollo\j2mewtk\2.5.2\appdb\RMS"
del *.db
This will delete all .db files in my RMS directory, however I want to delete every single thing from this directory. How can I do this?
Use:
Create a batch file
Copy the below text into the batch file
set folder="C:\test"
cd /d %folder%
for /F "delims=" %%i in ('dir /b') do (rmdir "%%i" /s/q || del "%%i" /s/q)
It will delete all files and folders.
del *.* instead of del *.db. That will remove everything.
IF EXIST "C:\Users\tbrollo\j2mewtk\2.5.2\appdb\RMS" (
rmdir "C:\Users\tbrollo\j2mewtk\2.5.2\appdb\RMS" /s /q
)
This will delete everything from the folder (and the folder itself).
I just put this together from what morty346 posted:
set folder="C:\test"
IF EXIST "%folder%" (
cd /d %folder%
for /F "delims=" %%i in ('dir /b') do (rmdir "%%i" /s/q || del "%%i" /s/q)
)
It adds a quick check that the folder defined in the variable exists first, changes directory to the folder, and deletes the contents.
del *.* will only delete files, but not subdirectories. To nuke the contents of a directory, you can use this script:
#echo off
setlocal enableextensions
if {%1}=={} goto :HELP
if {%1}=={/?} goto :HELP
goto :START
:HELP
echo Usage: %~n0 directory-name
echo.
echo Empties the contents of the specified directory,
echo WITHOUT CONFIRMATION. USE EXTREME CAUTION!
goto :DONE
:START
pushd %1 || goto :DONE
rd /q /s . 2> NUL
popd
:DONE
endlocal
The pushd changes into the directory of which you want to delete the children. Then when rd asks to delete the current directory and all sub directories, the deletion of the sub directories succeed, but the deletion of the current directory fails - because we are in it. This produces an error which 2> NUL swallows. (2 being the error stream).
You can do this using del and the /S flag (to tell it to recurse all files from all subdirectories):
del /S C:\Path\to\directory\*
The RD command can also be used. Recursively delete quietly without a prompt:
#RD /S /Q %VAR_PATH%
Rmdir (rd)
set "DIR_TO_DELETE=your_path_to_the_folder"
IF EXIST %DIR_TO_DELETE% (
FOR /D %%p IN ("%DIR_TO_DELETE%\*.*") DO rmdir "%%p" /S /Q
del %DIR_TO_DELETE%\*.* /F /Q
)
Use
set dir="Your Folder Path Here"
rmdir /s %dir%
mkdir %dir%
This version deletes without asking:
set dir="Your Folder Here"
rmdir /s /q %dir%
mkdir %dir%
Example:
set dir="C:\foo1\foo\foo\foo3"
rmdir /s /q %dir%
mkdir %dir%
This will clear C:\foo1\foo\foo\foo3.
(I would like to mention Abdullah Sabouin's answer. There was a mix up about me copying him. I did not notice his post. I would like to thank you melpomene for pointing out errors!)
Try the following; it works for me.
I have an application which dumps data in my "C:\tmp" folder, and the following works the best for me. It doesn't even ask Yes or No to delete the data. I have made a schedule for it to run after every 5 minutes
cd "C:\tmp"
del *.* /Q
Better yet, let's say I want to remove everything under the C:\windows\temp folder.
#echo off
rd C:\windows\temp /s /q
You could use robocopy to mirror an empty folder to the folder you are clearing.
robocopy "C:\temp\empty" "C:\temp\target" /E /MIR
It also works if you can't remove or recreate the actual folder.
It does require an existing empty directory.
I would like to suggest using simple tool like cleardir. So, in batch file you can write:
cleardir path/to/dir
And you'll get empty directory dir. A bit slow, but still resolves the "problem".
I'm an author of the tool =)
The easiest way is:
Create *.txt file
Write:
rmdir /q /s . dir
Save file as *.bat in folder which you want to clear (you can call the file NUKE.bat)
Turn it on
WARNING!
THIS DELETES EVERYTHING IN THE FOLDER WHERE IT IS WITHOUT ASKING FOR CONFIRMATION!!!
SO CHOOSE WISELY PLACE FOR SAVING IT.
Easy simple answer :
C:
del /S /Q C:\folderName\otherFolderName\*
C: Important in case you have to switch from D: to C: or C: to D: (or anything else)
/S Recursive, all subfolders are deleted along
/Q If you don't activate quiet mode, prompt will ask you to type y for every subfolders... you don't want that
Be carful, it's drastic.
You cannot delete everything with either rmdir or del alone:
rmdir /s /q does not accept wildcard params. So rmdir /s /q * will error.
del /s /f /q will delete all files, but empty subdirectories will remain.
My preferred solution (as I have used in many other batch files) is:
rmdir /s /q . 2>NUL
Just a modified version of GregM's answer:
set folder="C:\test"
cd /D %folder%
if NOT %errorlevel% == 0 (exit /b 1)
echo Entire content of %cd% will be deleted. Press Ctrl-C to abort
pause
REM First the directories /ad option of dir
for /F "delims=" %%i in ('dir /b /ad') do (echo rmdir "%%i" /s/q)
REM Now the files /a-d option of dir
for /F "delims=" %%i in ('dir /b /a-d') do (echo del "%%i" /q)
REM To deactivate simulation mode remove the word 'echo' before 'rmdir' and 'del'.
#echo off
#color 0A
echo Deleting logs
rmdir /S/Q c:\log\
ping 1.1.1.1 -n 5 -w 1000 > nul
echo Adding log folder back
md c:\log\
You was on the right track. Just add code to add the folder which is deleted back again.