Batch to archive files

Discussion forum for all Windows batch related topics.

Moderator: DosItHelp

Message
Author
tiagocampos
Posts: 38
Joined: 21 Feb 2013 12:41

Batch to archive files

#1 Post by tiagocampos » 21 Feb 2013 12:44

I am making a script that can allow me to archive all files of a given directory whom last modified date is superior to 30 days. The files should be moved to a new folder and this folder must be zipped afterwards.

Aditionaly - and this is a bit crutial - in the archiving process, the files should be grouped by month. The name of the zipped folder should indicate the month and year of the contained files.

Example: 2012_12.zip (contains all files from December 2012) ; 2013_01.zip (contains all files from January 2013)

This is what I have so far:

Code: Select all

ECHO OFF

ECHO.
SET /p folder=Which folder you want to archive?
ECHO.
ECHO %folder%

CHDIR %folder%
MKDIR Archive

ROBOCOPY "%folder%" "%folder%\Arquivo" /E /V /ETA /MOVE /XD "%folder%\Archive"
:: Exclude files newer than 30 days

FORFILES /P "%folder%\Archive" /D -31/12/2012 /D +1/12/2012 /C GOTO :ZIP




CALL:ZIP
SET filetozip="%folder%\Archive"
set tempdir=C:\Users\tiago.campos\Documents\OMS\FilesArchiver\tempdir
mkdir %tempdir%
copy %filetozip% %tempdir%
mkdir "%filetozip%\Archive"
rmdir %tempdir%
realdate

echo Set objArgs = WScript.Arguments > _zipIt.vbs
echo InputFolder = objArgs(0) >> _zipIt.vbs
echo ZipFile = objArgs(1) >> _zipIt.vbs
echo CreateObject("Scripting.FileSystemObject").CreateTextFile(ZipFile, True).Write "PK" ^& Chr(5) ^& Chr(6) ^& String(18, vbNullChar) >> _zipIt.vbs
echo Set objShell = CreateObject("Shell.Application") >> _zipIt.vbs
echo Set source = objShell.NameSpace(InputFolder).Items >> _zipIt.vbs
echo objShell.NameSpace(ZipFile).CopyHere(source) >> _zipIt.vbs
echo wScript.Sleep 2000 >> _zipIt.vbs


CScript  _zipIt.vbs  %tempdir%  "%filetozip%\Archive\2013.01.zip"

del "_zipIt.vbs"

pause


As a bonus feature, it would be very useful if instead of giving the directory as an input, the script would read from a csv file with more than one directory.

I'm a bit lost in the momement. I thank in advance for every reply!

foxidrive
Expert
Posts: 6031
Joined: 10 Feb 2012 02:20

Re: Batch to archive files

#2 Post by foxidrive » 21 Feb 2013 18:33

More information is needed to give you a versatile batch file.

What range of dates are involved here.

Is each source folder a single folder, without subfolders?

Please show a sample of the filenames.

Can you use 7Zip to zip them up?

Ocalabob
Posts: 79
Joined: 24 Dec 2010 12:16
Location: Micanopy Florida

Re: Batch to archive files

#3 Post by Ocalabob » 22 Feb 2013 01:49

Greetings tiagocampos,

Wow, you've got a "train wreck" in your script before you even get to the Robocopy line.
Did you just copy/paste some scripts together?

Use foxidrive's reply as a guide and I'll try to help with the Robocopy portion of the file.

Best wishes!

tiagocampos
Posts: 38
Joined: 21 Feb 2013 12:41

Re: Batch to archive files

#4 Post by tiagocampos » 22 Feb 2013 04:23

foxidrive wrote:More information is needed to give you a versatile batch file.

What range of dates are involved here.

Is each source folder a single folder, without subfolders?

Please show a sample of the filenames.

Can you use 7Zip to zip them up?


Hello foxidrive,

The data range can go up to early 2012.

Regarding the filenames, I'll show some prints, there are several types:

Image
In this type, there is already a folder named Archive resulting from an older script that copied files older than X days to a new folder named Archive. The files in it aren't zipped.

Image

Image
In this case, the folders are already compressed.

Image
Inside which folder, there are files that should be archive following the 30 days older rule.

If 7zip gets the job done, fine by me!

Hope this help, and I really appreciate your help, many thanks!

foxidrive
Expert
Posts: 6031
Joined: 10 Feb 2012 02:20

Re: Batch to archive files

#5 Post by foxidrive » 22 Feb 2013 05:33

This isn't quite what you asked for - what it does is this:

It processes a folder full of directories. Launch it in the folder that contains all the directories that you need to process.
It creates directories in each of the above folders in the format "tempzip-2012_01" and "tempzip-2012_02" to "tempzip-2012_12"
For all the filetypes and folders you mentioned, it moves them into "tempzip-2012_01" etc and then creates a "2012_01.zip" file of them all.

Copy some folders into a temp folder and try this batch file on those test files.

What you need to do before using it in future is to change the year and months variables to match your requirements.
If you want to automate this part you have to detect the current month - 30 days - 1 month and build the list of months, and year, but changing this part is trivial compared to the time you save in the processing part.

It expects you to install "c:\Program Files\7-Zip\7z.exe" which is a free archiver called 7-zip.



Code: Select all

@echo off
set "year=2012"
set months=01 02 03 04 05 06 07 08 09 10 11 12


set yr=%year:~-2%
for /f "delims=" %%a in ('dir /a:d /b') do (
pushd "%%a"
for %%b in (%months%) do (
 echo processing year %year% and month %%b
 if exist "*_??.%%b.%yr%.dat" md "tempzip-%year%_%%b" 2>nul & move "*_??.%%b.%yr%.dat" "tempzip-%year%_%%b"
 if exist "*_%year%%%b??.csv" md "tempzip-%year%_%%b" 2>nul & move "*_%year%%%b??.csv" "tempzip-%year%_%%b"
  if exist "wb*.%year%%%b??-??????" md "tempzip-%year%_%%b" 2>nul & (
   for /f "delims=" %%c in ('dir /ad /b "wb*.%year%%%b??-??????"') do move "%%c" "tempzip-%year%_%%b"
   )
if exist "tempzip-%year%_%%b\" (
   pushd "tempzip-%year%_%%b"
   echo Making ZIP file
   "c:\Program Files\7-Zip\7z.exe" a -r -tzip "%year%_%%b.zip" *
   move "%year%_%%b.zip" ..
   popd
   )
)
popd
)
pause

tiagocampos
Posts: 38
Joined: 21 Feb 2013 12:41

Re: Batch to archive files

#6 Post by tiagocampos » 22 Feb 2013 09:07

Hi again foxidrive,

I created a test scenario, like this:
Image

Content of the folders:
ImageImage

Then I run the script as Administrator and see it processing all months, but no folders are created.
I don't think he's entering the if condition for the date.

Current code (I added the .js and .txt condition):

Code: Select all

@echo off
set year=2012
set months=01 02 03 04 05 06 07 08 09 10 11 12


set yr=%year:~-2%
for /f "delims=" %%a in ('dir /a:d /b') do (
pushd "%%a"
for %%b in (%months%) do (
 echo processing year %year% and month %%b
 if exist "*_??.%%b.%yr%.dat" md "tempzip-%year%_%%b" 2>nul & move "*_??.%%b.%yr%.dat" "tempzip-%year%_%%b"
 if exist "*_%year%%%b??.csv" md "tempzip-%year%_%%b" 2>nul & move "*_%year%%%b??.csv" "tempzip-%year%_%%b"
 if exist "*_%year%%%b??.js" md "tempzip-%year%_%%b" 2>nul & move "*_%year%%%b??.js" "tempzip-%year%_%%b"
 if exist "*_%year%%%b??.txt" md "tempzip-%year%_%%b" 2>nul & move "*_%year%%%b??.txt" "tempzip-%year%_%%b"
  if exist "wb*.%year%%%b??-??????" md "tempzip-%year%_%%b" 2>nul & (
   for /f "delims=" %%c in ('dir /ad /b "wb*.%year%%%b??-??????"') do move "%%c" "tempzip-%year%_%%b"
   )
if exist "tempzip-%year%_%%b\" (
   pushd "tempzip-%year%_%%b"
   echo Making ZIP file
   "C:\Program Files\7-Zip\7z.exe" a -r -tzip "%year%_%%b.zip" *
   move "%year%_%%b.zip" ..
   popd
   )
)
popd
)
pause


Again thank you very much for your assistance!

foxidrive
Expert
Posts: 6031
Joined: 10 Feb 2012 02:20

Re: Batch to archive files

#7 Post by foxidrive » 22 Feb 2013 09:18

Your files are in different formats and will need a different method than I used...

Are you able to use XXcopy for this task? It is free for personal use.

tiagocampos
Posts: 38
Joined: 21 Feb 2013 12:41

Re: Batch to archive files

#8 Post by tiagocampos » 22 Feb 2013 09:21

Yes I can.

foxidrive
Expert
Posts: 6031
Joined: 10 Feb 2012 02:20

Re: Batch to archive files

#9 Post by foxidrive » 22 Feb 2013 10:34

This seems to work here. Test it on some copies of your folders.

It does the same thing the last one does, but it actually checks the last modified date and operates on files older than 30 days.
It uses VBS to get the date 30 days ago, and forfiles.exe to process the files, and 7-Zip to create the ZIP files.


Code: Select all

@echo off
call :getdate today -30

for /f "delims=" %%a in ('dir /a:d /b') do (
pushd "%%a"
 for /f "delims=" %%b in ('dir /b') do (
  for /f "tokens=1,2,3 delims=/" %%c in ('forfiles /M "%%b" /c "cmd /c echo @fdate"') do (
   echo checking "%%b"
   forfiles /m "%%b" /d -%day% /c "cmd /c MD 0x22%%e_%%d0x22 2>nul & move @file 0x22%%e_%%d0x22 >nul"
  )
 )
popd
)

for /f "delims=" %%a in ('dir /a:d /b') do (
pushd "%%a"
for /f "delims=" %%b in ('dir "????_??" /ad /b') do (
   pushd "%%b"
   echo Making ZIP file from "%%b" folder
   "c:\Program Files\7-Zip\7z.exe" a -r -tzip "%%b.zip" *
   move "%%b.zip" .. >nul
   popd
   )
popd
)

pause
goto :EOF


:getdate
:: Date foward & backward
@echo off
:: from code by Phil Robyn
setlocal
if [%1]==[] (
  echo to get todays date use
  echo call "%~n0" today 0
  echo.
  echo to get yesterdays date use
  echo call "%~n0" today -1
  echo.
  echo to get the date 25 days ago:
  echo call "%~n0" today -25
  echo.
  echo to get the date 1250 days in the future
  echo call "%~n0" today +1250
  goto :EOF)

set date1=%1
set qty=%2
if /i "%date1%" EQU "TODAY" (
 set date1=now
) else (
 set date1="%date1%"
)
echo >"%temp%\%~n0.vbs" s=DateAdd("d",%qty%,%date1%)
echo>>"%temp%\%~n0.vbs" WScript.Echo year(s)^&_
echo>>"%temp%\%~n0.vbs"         right(100+month(s),2)^&_
echo>>"%temp%\%~n0.vbs"         right(100+day(s),2)
for /f %%a in (
  'cscript //nologo "%temp%\%~n0.vbs"') do set result=%%a
del "%temp%\%~n0.vbs"
endlocal& set "day=%result:~6,2%/%result:~4,2%/%result:~0,4%"
:: echo %%day%% is set to "%day%" (without the quotes)

tiagocampos
Posts: 38
Joined: 21 Feb 2013 12:41

Re: Batch to archive files

#10 Post by tiagocampos » 22 Feb 2013 11:05

I executed the last version in one of my test folders and was surprised by the prompt output, check here: http://prntscr.com/tq79x

I tracked the files and ended up in the C:\Windows directory.

Do you have any idea what is causing this behaviour?

foxidrive
Expert
Posts: 6031
Joined: 10 Feb 2012 02:20

Re: Batch to archive files

#11 Post by foxidrive » 22 Feb 2013 11:22

Ending in c:\windows might be because you ran the code in a remote path, not a local drive.

The error in date format could be a forfiles issue - can you type this and check the /D switch to see what date format it lists?

forfiles /?

Copy and paste the help here.

tiagocampos
Posts: 38
Joined: 21 Feb 2013 12:41

Re: Batch to archive files

#12 Post by tiagocampos » 22 Feb 2013 11:25


foxidrive
Expert
Posts: 6031
Joined: 10 Feb 2012 02:20

Re: Batch to archive files

#13 Post by foxidrive » 22 Feb 2013 11:30

If you didn't run it on a remote UNC path earlier then it could have side effects that will destroy windows (by moving system files).

If it was a UNC path then map a drive letter to the server first, and try this - it just changes the date format to suit yours. Forfiles has regional differences I now realise.


Code: Select all

@echo off
call :getdate today -30

for /f "delims=" %%a in ('dir /a:d /b') do (
pushd "%%a"
 for /f "delims=" %%b in ('dir /b') do (
  for /f "tokens=1,2,3 delims=/-" %%c in ('forfiles /M "%%b" /c "cmd /c echo @fdate"') do (
   echo checking "%%b"
   forfiles /m "%%b" /d -%day% /c "cmd /c MD 0x22%%e_%%d0x22 2>nul & move @file 0x22%%e_%%d0x22 >nul"
  )
 )
popd
)

for /f "delims=" %%a in ('dir /a:d /b') do (
pushd "%%a"
for /f "delims=" %%b in ('dir "????_??" /ad /b') do (
   pushd "%%b"
   echo Making ZIP file from "%%b" folder
   "c:\Program Files\7-Zip\7z.exe" a -r -tzip "%%b.zip" *
   move "%%b.zip" .. >nul
   popd
   )
popd
)

pause
goto :EOF


:getdate
:: Date foward & backward
@echo off
:: from code by Phil Robyn
setlocal
if [%1]==[] (
  echo to get todays date use
  echo call "%~n0" today 0
  echo.
  echo to get yesterdays date use
  echo call "%~n0" today -1
  echo.
  echo to get the date 25 days ago:
  echo call "%~n0" today -25
  echo.
  echo to get the date 1250 days in the future
  echo call "%~n0" today +1250
  goto :EOF)

set date1=%1
set qty=%2
if /i "%date1%" EQU "TODAY" (
 set date1=now
) else (
 set date1="%date1%"
)
echo >"%temp%\%~n0.vbs" s=DateAdd("d",%qty%,%date1%)
echo>>"%temp%\%~n0.vbs" WScript.Echo year(s)^&_
echo>>"%temp%\%~n0.vbs"         right(100+month(s),2)^&_
echo>>"%temp%\%~n0.vbs"         right(100+day(s),2)
for /f %%a in (
  'cscript //nologo "%temp%\%~n0.vbs"') do set result=%%a
del "%temp%\%~n0.vbs"
endlocal& set "day=%result:~6,2%-%result:~4,2%-%result:~0,4%"
:: echo %%day%% is set to "%day%" (without the quotes)

tiagocampos
Posts: 38
Joined: 21 Feb 2013 12:41

Re: Batch to archive files

#14 Post by tiagocampos » 22 Feb 2013 11:56

The forfile issue was fixed but it still goes to the C:\Windows

It's really odd, this is where i run the script:

Image

foxidrive
Expert
Posts: 6031
Joined: 10 Feb 2012 02:20

Re: Batch to archive files

#15 Post by foxidrive » 22 Feb 2013 21:03

Do you have a batch file etc called forfiles?

There isn't a command in my batch file to change the directory to the windows folders.

Post Reply