Posted at

ファイルの世代管理が辛いときに使うやつ

More than 3 years have passed since last update.

ファイルの世代管理が辛いときに使うやつ

@echo off

:: file_path を backup_dir にコピーする。
:: コピーする際にファイル名に日付を付与する(C:\backup_dir\fileName_yyyymmdd.ext)。
:: 既に同名のファイルが存在する場合は、更に連番を付ける(C:\backup_dir\fileName_yyyymmdd_n.ext)。

:: ユーザ定義変数
set file_path=hogehoge.ext
set backup_dir=C:\example\fugafuga

:: ユーザ定義変数のエラーチェック
if not exist %file_path% (
call :GET_FULLPATH %file_path%
set file_path=%RETURN%
echo バックアップ対象のファイルが存在しません。 %file_path%
echo 処理を終了します。
echo;
pause
exit /b
)

if not exist %backup_dir% (
call :GET_FULLPATH %backup_dir%
set backup_dir=%RETURN%
echo バックアップ先が存在しません。新しく作成します。
echo mkdir %backup_dir%
mkdir %backup_dir%
echo;
)
if %errorlevel% neq 0 (
echo バックアップ先の作成に失敗しました。
echo 処理を終了します。
echo;
pause
exit /b
)

:: 変数の初期化
call :GET_YYYYMMDD
set yyyymmdd=%RETURN%

call :GET_BASENAME %file_path%
set baseName=%RETURN%

call :GET_EXTENSION %file_path%
set extension=%RETURN%

call :BUILD_PATH %backup_dir% %baseName%_%yyyymmdd%.%extension%
set backup_path=%RETURN%

set /a suffix=0
:LOOP
if not exist %backup_path% goto :BREAK
set /a suffix=suffix+1
call :BUILD_PATH %backup_dir% %baseName%_%yyyymmdd%_%suffix%.%extension%
set backup_path=%RETURN%
goto :LOOP
:BREAK

:: バックアップの実行
copy %file_path% %backup_path% > nul

:: 実行結果の確認
if %errorlevel% neq 0 (
echo ファイルコピーに失敗しました。
echo 処理を終了します。
echo;
pause
exit /b
)

:: 実行結果の出力
call :GET_FULLPATH %file_path%
set file_path=%RETURN%

call :GET_FULLPATH %backup_path%
set backup_path=%RETURN%

echo ファイルをコピーしました。
echo From: %file_path%
echo To : %backup_path%
echo;
pause
exit /b

:: サブルーチンの定義

:: システムの日付を YYYYMMDD 形式で取得する
:GET_YYYYMMDD
set RETURN=%date:/=%
exit /b

:: パスのフルパスを取得する。
:: 第一引数としてファイルパスを受け取る。
:GET_FULLPATH
set RETURN=%~dpnx1
exit /b

:: ファイルパスからファイル名と拡張子を取り出す。
:: 第一引数としてファイルパスを受け取る。
:GET_FILENAME
set RETURN=%~nx1
exit /b

:: ファイルパスから拡張子を取り出す。
:: 第一引数としてファイルパスを受け取る。
:GET_EXTENSION
set RETURN=%~x1%
set RETURN=%RETURN:~1%
exit /b

:: ファイルパスからファイル名(拡張子除く)を取り出す。
:: 第一引数としてファイルパスを受け取る。
:GET_BASENAME
set RETURN=%~n1
exit /b

:: ファイルパスから親ディレクトリのパスを返す。末尾の \ は付いたまま。
:: 第一引数としてファイルパスを受け取る。
:GET_PARENT_DIR
set RETURN=%~dp1
exit /b

:: 末尾の \ の有無に関わらず文字列を連結してWindowsパスを作る。
:: 第一引数としてディレクトリパスを受け取る。
:: 第二引数としてファイル名を受け取る。
:BUILD_PATH
setlocal
set parent=%1
set child=%2
set tail=%parent:~-1,1%

if %tail% EQU \ (
set RETURN=%parent%%child%
) else (
set RETURN=%parent%\%child%
)
endlocal && set RETURN=%RETURN%
exit /b