簡體   English   中英

用最新文件填充備份驅動器

[英]Fill backup drive with newest files

我有大約12TB(並且正在增長)的庫,分布在3個HDD上,包含視頻文件,我想將它們備份到外部硬盤驅動器上。 我正在使用Windows 10專業版。

我的備份驅動器只有8TB,我想始終備份最新的8TB視頻文件。 到目前為止,我已經嘗試了大約10種同步工具,但沒有一個允許我根據創建日期復制文件。

另外,對於robocopy,我還沒有找到僅復制最新8TB文件的方法。
有什么建議么?

我有2個批處理腳本可以滿足您的要求。 它們之間的主要區別是,第一個腳本使用的是where可以找到所有將使用上次更改的時間戳的文件。 要使用另一個時間戳,例如上次訪問或創建時間,您必須使用我附帶的使用dir的第二個腳本。

1.批處理腳本where用於查找文件:

它至少需要2個參數:
用法: batch.bat <dst> <src_1> [<src_...> <src_n>]

它使用where /r <src_n> * /t命令,它將建立所有子目錄中所有文件的列表,並以以下格式標記上一次更改的時間戳:

<size>   <date>          <time>    <file name>
  5397   11.07.2017      14:32:09  C:\Users\...\foo.txt
 10860   12.07.2017      11:25:15  C:\Users\...\bar.log

如果您需要創建時間或上次訪問時間,則時間戳記是最后更改的時間,請使用下面的第二個批處理腳本,該腳本正在使用dir因為可以在不同的時間戳記之間進行選擇。

對於通過參數列表傳遞的每個源,此輸出(沒有列size )將被寫入temp dir %TEMP%下的臨時文件中(腳本后將自動刪除)。 完整的臨時文件按日期和時間排序,最新的優先。

排序后的輸出將用於將其復制到目標文件夾中。

例:

cmd當前目錄為C:\\...\\Desktop ):
batch.bat "backup_folder" "F:\\folder" "F:\\folder with space"

當前目錄在某處:
batch.bat "C:\\...\\Desktop\\backup_folder" "F:\\folder" "F:\\folder with space"

C:\\...\\Desktop\\backup_folder將包含2個文件夾folderfolder with space文件folder ,這些folder with space在腳本操作后包含這些源文件夾的所有文件。

在您的情況下,批處理腳本將僅復制8 TB的最新文件,因為驅動器將已滿,並且批處理腳本將退出,因為它可以識別復制錯誤。

批處理腳本:

@echo off
setlocal enabledelayedexpansion

rem Check if at least 2 arguments are passed
set INVARGS=0
if [%1] == [] set INVARGS=1
if [%2] == [] set INVARGS=1
if %INVARGS% == 1 (
   echo Usage: %0 ^<dst^> ^<src_1^> ^<src_...^> ^<src_n^>
   goto :EOF
)

rem Store Carriage return character in CR (used for spinner function, see below)
for /f %%a in ('copy /Z "%~dpf0" nul') do set "CR=%%a"

rem Set temp file name
set "uniqueFile=%TEMP%\%0_%RANDOM%.tmp"

rem Set destination path and shift to next argument
set "dstpath=%~1"
shift

rem Store src_1 to src_n arguments into src array
set idx=0
:again
rem If %1 is blank, we are finished
if not [%1] == [] (
   if not exist "%~1" (
      echo The following source folder doesn't exist:
      echo    "%~1"!
      echo The program will terminate!
      goto :end
   )

   pushd "%~1"
   set "src[%idx%]=!cd!"
   if [!src[%idx%]:~-1!] == [\] (
      set src[%idx%]=!src[%idx%]:~0,-1!
   )
   set /a idx=%idx%+1
   popd

   rem Shift the arguments and examine %1 again
   shift

   goto :again
)

rem Build command string:
rem where /r "src_1" * /t ^& where /r "src_..." * /t ^& where /r "src_n" * /t ^& break"
set "command="
for /F "tokens=2 delims==" %%s in ('set src[') do (
   set "command=!command!where /r "%%s" * /t ^& "
)
set "command=!command!break"

echo "Command: ^<!command!^>"

rem Clear temp file and write files to copy in it
break>"%uniqueFile%"
for /f "tokens=2,3,4,* delims= " %%F in ('!command!') do (
   call :spinner
   echo %%F %%G %%H %%I>>"%uniqueFile%"
)

rem Open the built file list
echo File list will be opened...
%uniqueFile%
rem Ask user if copying should start
echo Should this files copied into %dstpath%? (Y/N)
set INPUT=
set /P INPUT=Answer?:%=%
if not [%INPUT%] == [y] (
   if not [%INPUT%] == [Y] (
      goto :end
   )
)

set "dstpathPart="
rem Sort files newest first (last changed timestamp)
for /f "tokens=3,* delims= " %%F in ('type "%uniqueFile%" ^| sort /r') do (
   rem Build destination part from source folder names
   call :buildDestinationPath dstpathPart "%%F %%G"

   rem Prepend the destination folder
   set "dstFile=!dstpath!\!dstpathPart!"

   rem Make directories that doesn't exists
   for %%F in ("!dstFile!") do set "directory=%%~dpF"
   if not exist "!directory!" ( mkdir "!directory!" )

   rem Copy files and echo it
   echo copy /y "!file!" "!dstFile!"
   copy /y "!file!" "!dstFile!"
   echo.

   rem If copying failed exit program
   if errorlevel 1 (
      echo Copying failed... Maybe there is no more space on the disk!
      echo The program will terminate!
      goto :end
   )
)
goto :end


rem Function definitions
:buildDestinationPath
for /F "tokens=2 delims==" %%s in ('set src[') do (
   rem Go into folder e.g.: C:\src_1\ --> C:\
   pushd "%%s"
   cd ..
   rem file contains full path of the where command
   set "file=%~2"

   rem Remove trailing space
   if "!file:~-1!" == " " (
      call set "file=%%file:~0,-1%%"
   )

   rem remove src folder from file to make it relative
   rem e.g. C:\src_1\foo\bar\file1.txt --> src_1\foo\bar\file1.txt
   call set "dstpathPart_temp=%%file:!cd!=%%"

   rem Switch back to origin folder
   popd

   rem If the folder name changed the substring taken was right so take next
   if not [!dstpathPart_temp!] == [!file!] (
      set "%~1=!dstpathPart_temp!"
      goto :next
   )
)
:next
goto :EOF

:spinner
set /a "spinner=(spinner + 1) %% 4"
set "spinChars=\|/-"
<nul set /p ".=Building file list... !spinChars:~%spinner%,1!!CR!"
goto :EOF

:end
del "%uniqueFile%"
goto :EOF

2.使用dir批處理腳本以找到文件:

它需要一個以上的參數,因此您至少需要3個參數:
用法: batch.bat <timeordering> <dst> <src_1> [<src_...> <src_n>]

它將使用dir命令生成與上述相同的列表。 dir命令采用以下參數,該參數是腳本的<timeordering>參數:

/tc Creation
/ta Last access
/tw Last written

批處理腳本:

@echo off
setlocal enabledelayedexpansion

rem Check if at least 2 arguments are passed
set INVARGS=0
if [%1] == [] set INVARGS=1
if [%2] == [] set INVARGS=1
if [%3] == [] set INVARGS=1
if %INVARGS% == 1 (
   echo Usage: %0 ^<timeordering^> ^<dst^> ^<src_1^> ^<src_...^> ^<src_n^>
   goto :EOF
)

rem Store Carriage return character in CR (used for spinner function, see below)
for /f %%a in ('copy /Z "%~dpf0" nul') do set "CR=%%a"

rem Set temp file name
set "uniqueFile=%TEMP%\%0_%RANDOM%.tmp"

rem Set timeordering and destination path and shift to next argument
set "timeordering=%~1"
shift
set "dstpath=%~1"
shift

rem Store src_1 to src_n arguments into src array
set idx=0
:again
rem If %1 is blank, we are finished
if not [%1] == [] (
   if not exist "%~1" (
      echo The following source folder doesn't exist:
      echo    "%~1"!
      echo The program will terminate!
      goto :end
   )

   pushd "%~1"
   set "src[%idx%]=!cd!"
   if [!src[%idx%]:~-1!] == [\] (
      set src[%idx%]=!src[%idx%]:~0,-1!
   )
   set /a idx=%idx%+1
   popd

   rem Shift the arguments and examine %1 again
   shift

   goto :again
)


rem Clear temp file and write files to copy in it
break>"%uniqueFile%"
rem call commands with all sources:
rem call :getFileInformation /TC "src_1\*"
rem                          /TW
rem                          /TA
for /F "tokens=2 delims==" %%s in ('set src[') do (
   call :getFileInformation %timeordering% "%%s\*" "%uniqueFile%""
)

rem Open the built file list
echo Unsorted file list will be opened...
%uniqueFile%
rem Ask user if copying should start
echo Should this files copied into %dstpath%? (Y/N)
set INPUT=
set /P INPUT=Answer?:%=%
if not [%INPUT%] == [y] (
   if not [%INPUT%] == [Y] (
      goto :end
   )
)

set "dstpathPart="
rem Sort files newest first (last changed timestamp)
for /f "tokens=3,* delims= " %%F in ('type "%uniqueFile%" ^| sort /r') do (
   rem Build destination part from source folder names
   call :buildDestinationPath dstpathPart "%%F %%G"

   rem Prepend the destination folder
   set "dstFile=!dstpath!\!dstpathPart!"

   rem Make directories that doesn't exists
   for %%F in ("!dstFile!") do set "directory=%%~dpF"
   if not exist "!directory!" ( mkdir "!directory!" )

   rem Copy files and echo it
   echo copy /y "!file!" "!dstFile!"
   copy /y "!file!" "!dstFile!"
   echo.

   rem If copying failed exit program
   if errorlevel 1 (
      echo Copying failed... Maybe there is no more space on the disk!
      echo The program will terminate!
      goto :end
   )
)
goto :end


rem Function definitions
:buildDestinationPath
for /F "tokens=2 delims==" %%s in ('set src[') do (
   rem Go into folder e.g.: C:\src_1\ --> C:\
   pushd "%%s"
   cd ..
   rem file contains full path of the where command
   set "file=%~2"

   rem Remove trailing space
   if "!file:~-1!" == " " (
      call set "file=%%file:~0,-1%%"
   )

   rem remove src folder from file to make it relative
   rem e.g. C:\src_1\foo\bar\file1.txt --> src_1\foo\bar\file1.txt
   call set "dstpathPart_temp=%%file:!cd!=%%"

   rem Switch back to origin folder
   popd

   rem If the folder name changed the substring taken was right so take next
   if not [!dstpathPart_temp!] == [!file!] (
      set "%~1=!dstpathPart_temp!"
      goto :next
   )
)
:next
goto :EOF

:getFileInformation
for /f "delims=" %%a in ('dir /s /b /a-d %~1 "%~2"') do (
   for /f "tokens=1,2 delims= " %%b in ('dir %~1 "%%a" ^| findstr /l /c:"%%~nxa"') do (
      echo %%b %%c %%a>>"%~3"
      call :spinner
   )
)
goto :EOF

:spinner
set /a "spinner=(spinner + 1) %% 4"
set "spinChars=\|/-"
<nul set /p ".=Building file list... !spinChars:~%spinner%,1!!CR!"
goto :EOF

:end
del "%uniqueFile%"
goto :EOF

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM