¿Hay alguna forma de usar Winmerge dentro de git para hacer Diffs?
¿Hay alguna forma de usar Winmerge dentro de git para hacer Diffs?
Respuestas:
Actualización de junio de 2015, 6 años después:
Como se detalla en " git mergetool winmerge ", un simple git config diff.tool winmerge
será suficiente.
¡Git 2.5+ (Q2, 2015) ahora conoce Winmerge como una herramienta de diferenciación o fusión!
Respuesta original (2009-2012)
(msysgit, 1.6.5, sesión de DOS)
La primera parte (usando winmerge) se describe en " ¿Cómo veo la salida 'git diff' con el programa visual diff? "
C:\myGitRepo>git config --replace --global diff.tool winmerge
C:\myGitRepo>git config --replace --global difftool.winmerge.cmd "winmerge.sh \"$LOCAL\" \"$REMOTE\""
C:\myGitRepo>git config --replace --global difftool.prompt false
Con winmerge.sh
almacenado en un directorio parte de su PATH
:
#!/bin/sh
echo Launching WinMergeU.exe: $1 $2
"$PROGRAMFILES/WinMerge/WinMergeU.exe" -e -u -dl "Local" -dr "Remote" "$1" "$2"
(ver Opciones de la línea de comandos de WinMerge )
git difftool
ahora lanzará WinMerge.
Si desea git diff
iniciar WinMerge, simplemente configure:
set GIT_EXTERNAL_DIFF=winmerge.sh
Pero el valor agregado real proviene de la capacidad de usar esa misma herramienta de diferencias para presentar todas las diferencias en un lote en lugar de presentarlas secuencialmente, lo que te obliga a cerrar las ventanas de la herramienta de diferencias de un archivo a la vez.
Actualización de junio de 2012 (2 años y medio después):
La comparación de directorios en lugar de archivo por archivo estará disponible pronto:
Vea [ANUNCIO] Git 1.7.11.rc1 :
"
git difftool
" aprendió la--dir-diff
opción " " para generar herramientas de diferencias externas que pueden comparar dos jerarquías de directorios a la vez después de completar dos directorios temporales, en lugar de ejecutar una instancia de la herramienta externa una vez por par de archivos .
Consulte " Parche difftool
: enseñar difftool
a manejar diferencias de directorio " y la respuesta " Comparación de directorios de ramas de Git " para obtener más detalles.
Diftool original por el script de directorios (diciembre de 2009)
Como menciona Seba Illingworth en su respuesta , un script git-diffall.sh (también incluido en la ruta) puede hacer precisamente eso:
#!/bin/sh
git diff --name-only "$@" | while read filename; do
git difftool "$@" --no-prompt "$filename" &
done
Pero eso solo funciona abriendo n ventanas para n archivos (si intenta usar la -s
opción de WinMerge, no funcionará debido a que la herramienta difftool elimina los archivos temporales demasiado pronto)
Es por eso que me gusta el enfoque de GitDiff.bat - power-diffing con GI , que le permite revisar la lista de archivos con una diferencia, antes de seleccionar uno para examinar sus diferencias internas.
Lo modifiqué para usar solo comandos de DOS
@echo off
setlocal
if "%1" == "-?" (
echo GitDiff - enables diffing of file lists, instead of having to serially
echo diff files without being able to go back to a previous file.
echo Command-line options are passed through to git diff.
echo If GIT_FOLDER_DIFF is set, it is used to diff the file lists. Default is windff.
goto END
)
if "%GIT_DIFF_COPY_FILES%"=="" (
rd /s /q %TEMP%\GitDiff
mkdir %TEMP%\GitDiff
mkdir %TEMP%\GitDiff\old
mkdir %TEMP%\GitDiff\new
REM This batch file will be called by git diff. This env var indicates whether it is
REM being called directly, or inside git diff
set GIT_DIFF_COPY_FILES=1
set GIT_DIFF_OLD_FILES=%TEMP%\GitDiff\old
set GIT_DIFF_NEW_FILES=%TEMP%\GitDiff\new
set GIT_EXTERNAL_DIFF=%~dp0\GitDiff.bat
echo Please wait and press q when you see "(END)" printed in reverse color...
call git diff %*
if defined GIT_FOLDER_DIFF (
REM This command using GIT_FOLDER_DIFF just does not work for some reason.
%GIT_FOLDER_DIFF% %TEMP%\GitDiff\old %TEMP%\GitDiff\new
goto END
)
if exist "%ProgramFiles%\Beyond Compare 2\BC2.exe" (
set GIT_FOLDER_DIFF="%ProgramFiles%\Beyond Compare 2\BC2.exe"
"%ProgramFiles%\Beyond Compare 2\BC2.exe" %TEMP%\GitDiff\old %TEMP%\GitDiff\new
goto END
)
"%ProgramFiles(x86)%\WinMerge\WinMergeU.exe" -r -e -dl "Local" -dr "Remote" %TEMP%\GitDiff\old %TEMP%\GitDiff\new
goto END
)
REM diff is called by git with 7 parameters:
REM path old-file old-hex old-mode new-file new-hex new-mode
copy %TEMP%\%~nx2 %GIT_DIFF_OLD_FILES%\%1
copy %5 %GIT_DIFF_NEW_FILES%
:END
No es lo suficientemente robusto para manejar archivos con los mismos nombres en diferentes directorios, pero le da una idea general de lo que es posible:
Aquí solo se abrirá un WinMerge, con la lista de archivos con diferencias internas. Puede hacer clic en los que desea examinar, luego un simple ESCcerrará todas las WinMerge-diff
sesiones.
git diff
?
-ub
, consulte las preguntas frecuentes de WinMerge : es lo mismo que -u
: le dice a WinMerge que no agregue los archivos a la MRU.
c:\Temp\GitDiff\old
y c:\Temp\GitDiff\new
, no ' /tmp
'. ¿Está seguro de que está ejecutando este programa de DOS desde una sesión de DOS (y no desde una sesión de bash)?
""
en mi caso (ejecutando el git config
comando desde una CMD de Windows. Pero tiene razón: se evaluaría ""
si se ejecutara desde un shell bash.)
Tuve problemas para usar la primera parte en 2 lugares y la arreglé de la siguiente manera
El segundo comando para configurar winmerge.cmd requería una barra oblicua adicional en cmdline (antes de $ LOCAL y $ REMOTE), de lo contrario, cygwin estaba sustituyendo la variable en cmdline
C:\myGitRepo>git config --replace --global difftool.winmerge.cmd "winmerge.sh \"\$LOCAL\" \"\$REMOTE\""
cambió el archivo winmerge.sh a (sin esto, estaba obteniendo un error de ruta derecha inválida)
#!/bin/sh
echo Launching WinMergeU.exe: "$(cygpath -aw "$1")" "$(cygpath -aw "$2")"
"$PROGRAMFILES/WinMerge/WinMergeU.exe" -e -ub -dl "Base" -dr "Mine" "$(cygpath -aw "$1")" "$(cygpath -aw "$2")"
Dado que el hilo se está volviendo confuso y bifurcado, aquí hay instrucciones consolidadas para el método WinMerge "--dir-diff" de Listado de directorios para msysgit Git Windows.
Paso 1 : cree un archivo llamado winmerge.sh en una ubicación accesible a su ruta (como /home/bin/winmerge.sh) con el siguiente contenido.
#!/bin/sh
echo Launching WinMergeU.exe: $1 $2
"$PROGRAMFILES/WinMerge/WinMergeU.exe" -r -ub -dl "Remote" -dr "Local" "$1" "$2"
Paso 2 : escribe los siguientes comandos en Git Bash para indicarle a git que use winmerge.sh como difftool (estas opciones se almacenan en /home/.gitconfig):
git config --replace --global diff.tool winmerge
git config --replace --global difftool.winmerge.cmd "winmerge.sh \"$LOCAL\" \"$REMOTE\""
git config --replace --global difftool.prompt false
Paso 3 : ahora puede probar escribiendo el siguiente comando en Git Bash para iniciar su diferencia de WinMerge:
git difftool --dir-diff
Paso 4 : para un acceso más rápido, cree un alias para este comando agregando esta línea a .bashrc en su carpeta de inicio (o cree un archivo .bashrc con esta línea si el archivo aún no existe):
alias diffdir='git difftool --dir-diff'
Paso 5 : ahora puede ver rápidamente una diferencia en WinMerge simplemente escribiendo el siguiente comando en Git Bash
diffdir
$LOCAL
y $REMOTE
.
Tengo un script que configurará las herramientas Diff y Merge en la configuración de Git con los parámetros adecuados que no requieren un archivo .sh separado para existir. Parece que me está funcionando bien.
git config --global diff.tool winmerge
git config --global difftool.prompt false
git config --global difftool.winmerge.cmd "\"\$PROGRAMFILES\"/WinMerge/WinMergeU.exe -r -u -e -dl \"Local\" -dr \"Remote\" \"\$LOCAL\" \"\$REMOTE\""
git config --global merge.tool winmerge
git config --global mergetool.prompt false
git config --global mergetool.winmerge.trustExitCode true
git config --global mergetool.winmerge.cmd "\"\$PROGRAMFILES\"/WinMerge/WinMergeU.exe -r -u -e -dl \"Local\" -dr \"Remote\" \"\$LOCAL\" \"\$REMOTE\" \"\$BASE\" \"\$MERGED\""
Nota : se cita toda la parte .cmd para que los parámetros se enumeren en el .gitconfig correctamente
git config --global difftool.winmerge.cmd "\"\$PROGRAMFILES\"/WinMerge/WinMergeU.exe -r -u -e -dl \"Local\" -dr \"Remote\" \"\$LOCAL\" \"\$REMOTE\""
Nota: este comando debe ejecutarse desde un símbolo del sistema y no desde powershell. Agregar manualmente lo siguiente a mi [difftool "winmerge"]
sección .gitconfig funcionó para mí: cmd = 'C:/Program Files (x86)/WinMerge/WinMergeU.exe' -r -u -e -dl \"Local\" -dr \"Remote\" \"$LOCAL\" \"$REMOTE\"
git config --global mergetool.winmerge.cmd "\"C:\Program Files (x86)\WinMerge\WinMergeU.exe\" -r -u -e -dl \"Local\" -dr \"Remote\" \"$LOCAL\" \"$REMOTE\" \"$BASE\" \"$MERGED\""
. Hubo algunas cadenas de escape incorrectas (tenga en cuenta algunas barras diagonales inversas no deseadas adicionales justo antes del $
, supongo $
que no es necesario escapar). Además, le faltaba un final "
después WinMergeU?.exe
. Corre git config --get mergetool.winmerge.cmd
para ver qué se ha configurado realmente. De todos modos, gracias por la no .sh
versión: +1!
En Windows puedes hacerlo de esta manera:
1) Abra el archivo .gitconfig. Se encuentra en su directorio de inicio: c: \ users \ username.gitconfig
2) Agregue las líneas siguientes. Preste atención a las comillas simples que envuelven el camino a winmerge:
[diff]
tool = winmerge
[difftool "winmerge"]
cmd = "'C:/Program Files (x86)/WinMerge/WinMergeU.exe'" -e "$LOCAL" "$REMOTE"
[difftool]
prompt = false
[merge]
tool = winmerge
[mergetool "winmerge"]
cmd = "'C:/Program Files (x86)/WinMerge/WinMergeU.exe'" \"$MERGED\" \"$REMOTE\"
[mergetool]
keepBackup = false
trustExitCode = false
Sin configuración:
git difftool --tool winmerge
Asumiendo:
Estaba confundido acerca de por qué la solución se presentaba como un archivo por lotes de DOS, ya que mi instalación de Git venía con un shell bash. Tampoco pude ejecutar un contexto de DOS desde bash, así que intenté adaptar lo que se compartió anteriormente en un contexto de bash.
Ya que git diff
parece ejecutar el comando especificado una vez para cada archivo, dividí mi solución en dos scripts bash:
Primero, configure gitprepdiff.sh
para ser el difftool como se mencionó anteriormente
#!/bin/sh
#echo ...gitprepdiff.sh
cp -v $1 "$TMP/GitDiff/old/$2"
cp -v $2 "$TMP/GitDiff/new"
También noté que los resultados de los git configure
comandos se pueden encontrar y editar directamente enC:\Users\<username>\.gitconfigure
gitdiff.sh
luego se ejecuta en la línea de comandos donde normalmente llamaría git diff
#!/bin/sh
#echo Running gitdiff.sh...
DIFFTEMP=$TMP/GitDiff
echo Deleting and re-creating $DIFFTEMP...
rm -rf $DIFFTEMP;
mkdir $DIFFTEMP;
echo Creating $DIFFTEMP/old...
mkdir $DIFFTEMP/old;
echo Creating $DIFFTEMP/new...
mkdir $DIFFTEMP/new;
git diff --name-only "$@" | while read filename; do
git difftool "$@" --no-prompt "$filename";
done
"$PROGRAMFILES\WinMerge\WinMergeU.exe" -r -e -dl "Repository" -dr "Working" $LOCALAPPDATA\\Temp\\1\\GitDiff\\old $LOCALAPPDATA\\Temp\\1\\GitDiff\\new
También vale la pena señalar que, en mi instalación, /tmp
(en bash) asignado a %LOCALAPPDATA%\Temp\1\
(en Windows), por eso estoy usando este último en mi llamada a WinMerge.
gitprepdiff.sh
por #!/bin/sh #echo ...gitprepdiff.sh mkdir -vp "$TMP/GitDiff/old/$(dirname $2)" cp -v $1 "$TMP/GitDiff/old/$2" cp -v --parents $2 "$TMP/GitDiff/new"
Gracias!
git config --global diff.tool winmerge
git config --global difftool.winmerge.cmd "\"$PROGRAMFILES\\WinMerge\\WinMergeU.exe\" -u -dl \"Local\" -dr \"Remote\" \"\$LOCAL\" \"\$REMOTE\""
git config --global difftool.prompt false
Según el manual de la línea de comandos de WinMerge : "Los parámetros tienen como prefijo una barra inclinada (/) o un guión (-)"