Skip to content

Instantly share code, notes, and snippets.

@end2endzone
Last active October 18, 2018 11:44
Show Gist options
  • Save end2endzone/019c6feab89cdb1255d858feb31375b9 to your computer and use it in GitHub Desktop.
Save end2endzone/019c6feab89cdb1255d858feb31375b9 to your computer and use it in GitHub Desktop.
Apply and create unified-diff patches in windows command line with this batch file (depends on subversion).
@echo off
REM Description:
REM The following script allows one to create patches in unified-diff format by comparing an old file (base file) with a new version of the file.
REM The script works by creating a temporary subversion repository. It commits the old file into the repository and update the local file with the new version. Using svn.exe, it creates a patch file for the changes.
REM The same steps are also executed for applying a patch. A temporary repository is created. The old file is committed into the repository and the patch is applied locally with svn.exe. The updated file is copied back to the user-desired destination and the temporary repository is deleted.
REM Note that the script is written for windows and have a dependency to subversion (svn.exe).
REM References:
REM https://docs.microsoft.com/en-us/previous-versions/windows/it-pro/windows-xp/bb490909(v=technet.10)
REM https://tortoisesvn.net/docs/nightly/TortoiseSVN_en/tsvn-cli-main.html
set BASE_DIR=%TEMP%\%RANDOM%
set REPO_DIR=%BASE_DIR%\repository
set TRUNK_DIR=%BASE_DIR%\trunk
set TEMP_FILENAME=base.txt
set CURRENT_DIR=%cd%
::Validate command line arguments
if "%1"=="CREATE" goto :create
if "%1"=="APPLY" goto :apply
::Error. Invalid arguments
set BASE_DIR=
set REPO_DIR=
set TRUNK_DIR=
set TEMP_FILENAME=
set CURRENT_DIR=
goto :usage
:usage
echo Usage:
echo %~nx0 CREATE [oldfile] [newfile] [patchfile]
echo %~nx0 APPLY [oldfile] [patchfile]
goto :eof
:create
set BASE_FILE=%~2
set NEW_FILE=%~3
set PATCH_FILE=%~4
echo Creating patch file '%PATCH_FILE%'
echo from '%BASE_FILE%'
echo to '%NEW_FILE%'
pause
::Create base repository with %BASE_FILE% already committed
call :prepare
::Override base file with new file...
echo Creating patch...
copy /v "%NEW_FILE%" "%TRUNK_DIR%\%TEMP_FILENAME%" >NUL
if %errorlevel% neq 0 exit /b %errorlevel%
cd /d "%TRUNK_DIR%"
svn diff > "%TRUNK_DIR%\diff.patch"
cd /d "%CURRENT_DIR%"
copy /v /y "%TRUNK_DIR%\diff.patch" "%PATCH_FILE%" >NUL
if %errorlevel% neq 0 exit /b %errorlevel%
call :cleanup
goto :eof
:apply
set BASE_FILE=%~2
set NEW_FILE=
set PATCH_FILE=%~3
echo Apply patch file '%PATCH_FILE%'
echo to '%BASE_FILE%'
pause
::Create base repository with %BASE_FILE% already committed
call :prepare
::Patching
echo Patching '%BASE_FILE%' file...
svn patch "%PATCH_FILE%" "%TRUNK_DIR%" >NUL
if %errorlevel% neq 0 exit /b %errorlevel%
::Copy patched file to over base file
copy /v /y "%TRUNK_DIR%\%TEMP_FILENAME%" "%BASE_FILE%" >NUL
call :cleanup
goto :eof
:prepare
::Create repository
echo Creating temporary respository in %BASE_DIR%
IF EXIST %BASE_DIR% (
rmdir /S /Q %BASE_DIR%
)
mkdir %BASE_DIR%
if %errorlevel% neq 0 exit /b %errorlevel%
svnadmin create --fs-type fsfs %REPO_DIR%
if %errorlevel% neq 0 exit /b %errorlevel%
::Creating trunk directory
svn checkout "file:///%REPO_DIR%" %TRUNK_DIR% >NUL
if %errorlevel% neq 0 exit /b %errorlevel%
::Commit base file
echo Commiting '%BASE_FILE%' file...
copy /v "%BASE_FILE%" "%TRUNK_DIR%\%TEMP_FILENAME%" >NUL
if %errorlevel% neq 0 exit /b %errorlevel%
svn add "%TRUNK_DIR%\%TEMP_FILENAME%" >NUL
if %errorlevel% neq 0 exit /b %errorlevel%
svn commit -m "Base file" "%TRUNK_DIR%" >NUL
if %errorlevel% neq 0 exit /b %errorlevel%
goto :eof
:cleanup
echo Cleanup...
rmdir /S /Q %BASE_DIR%
if %errorlevel% neq 0 exit /b %errorlevel%
set BASE_DIR=
set REPO_DIR=
set TRUNK_DIR=
set TEMP_FILENAME=
set CURRENT_DIR=
set BASE_FILE=
set NEW_FILE=
set PATCH_FILE=
goto :eof
@end2endzone
Copy link
Author

The following script allows one to create patches in unified-diff format by comparing an old file (base file) with a new version of the file.

The script works by creating a temporary subversion repository. It commits the old file into the repository and update the local file with the new version. Using svn.exe, it creates a patch file for the changes. The same is also executed for applying a patch. A temporary repository is created. The old file is committed into the repo and the patch is applied locally. The updated file is copied back to the user-desired destination and the temporary repo is deleted.

Note that the script is written for windows and have a dependency to subversion (svn.exe).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment