Quando digito "git diff", gostaria de ver um diff lado a lado, como com "diff -y", ou gostaria de exibir o diff em uma ferramenta de diff interativa como "kdiff3". Como isso pode ser feito?
Quando digito "git diff", gostaria de ver um diff lado a lado, como com "diff -y", ou gostaria de exibir o diff em uma ferramenta de diff interativa como "kdiff3". Como isso pode ser feito?
Respostas:
Embora o Git tenha uma implementação interna do diff, você pode configurar uma ferramenta externa.
Existem duas maneiras diferentes de especificar uma ferramenta de comparação externa:
GIT_EXTERNAL_DIFFeo GIT_DIFF_OPTSambiente variáveis.git configVeja também:
git diff --helpAo fazer a git diff, o Git verifica as configurações das variáveis de ambiente acima e seu .gitconfigarquivo.
Por padrão, o Git passa os sete argumentos a seguir para o programa diff:
path old-file old-hex old-mode new-file new-hex new-mode
Normalmente, você só precisa dos parâmetros do arquivo antigo e do novo arquivo. É claro que a maioria das ferramentas diff usa apenas dois nomes de arquivos como argumento. Isso significa que você precisa escrever um pequeno script wrapper, que aceita os argumentos que o Git fornece ao script e os entrega ao programa externo do git de sua escolha.
Digamos que você coloque seu wrapper-script em ~/scripts/my_diff.sh:
#!/bin/bash
# un-comment one diff tool you'd like to use
# side-by-side diff with custom options:
# /usr/bin/sdiff -w200 -l "$2" "$5"
# using kdiff3 as the side-by-side diff:
# /usr/bin/kdiff3 "$2" "$5"
# using Meld
/usr/bin/meld "$2" "$5"
# using VIM
# /usr/bin/vim -d "$2" "$5"
você precisa tornar esse script executável:
chmod a+x ~/scripts/my_diff.sh
você precisará informar ao Git como e onde encontrar seu script de wrapper diff personalizado. Você tem três opções de como fazer isso: (prefiro editar o arquivo .gitconfig)
Usando GIT_EXTERNAL_DIFF,GIT_DIFF_OPTS
Por exemplo, no seu arquivo .bashrc ou .bash_profile, você pode definir:
GIT_EXTERNAL_DIFF=$HOME/scripts/my_diff.sh
export GIT_EXTERNAL_DIFF
Usando git config
use "git config" para definir onde seu script wrapper pode ser encontrado:
git config --global diff.external ~/scripts/my_diff.sh
Editando seu ~/.gitconfigarquivo
você pode editar seu ~/.gitconfigarquivo para adicionar estas linhas:
[diff]
external = ~/scripts/my_diff.sh
Nota:
De maneira semelhante à instalação da ferramenta diff personalizada, você também pode instalar uma ferramenta de mesclagem personalizada, que pode ser uma ferramenta de mesclagem visual para ajudar a visualizar melhor a mesclagem. (veja a página progit.org)
Consulte: http://fredpalma.com/518/visual-diff-and-merge-tool/ e https://git-scm.com/book/en/v2/Customizing-Git-Git-Configuration
meld,?
meldversão pode ser configurada para fazer uma comparação de diretório, onde posso escolher para quais arquivos quero ver a comparação? Atualmente, ele executa um meldcomando separado para cada arquivo, e eu tenho que sair meldpara ver o próximo arquivo. Prefiro meldme mostrar uma lista de diretórios de arquivos alterados, como se comporta quando meldé usado no Mercurial.
Use em git difftoolvez de git diff. Você nunca voltará.
Aqui está um link para outro stackoverflow que fala sobre git difftool: Como visualizo a saída 'git diff' com minha ferramenta / visualizador preferido de diff?
Para versões mais recentes do git, o difftoolcomando suporta muitas ferramentas externas diff prontas para uso. Por exemplo, vimdiffé suportado automaticamente e pode ser aberto na linha de comando:
cd /path/to/git/repo
git difftool --tool=vimdiff
Outras ferramentas de diff externas suportadas são listadas git difftool --tool-helpaqui, é um exemplo de saída:
'git difftool --tool=<tool>' may be set to one of the following:
araxis
kompare
vimdiff
vimdiff2
The following tools are valid, but not currently available:
bc3
codecompare
deltawalker
diffuse
ecmerge
emerge
gvimdiff
gvimdiff2
kdiff3
meld
opendiff
tkdiff
xxdiff
This message is displayed because 'diff.tool' is not configured.. Talvez atualize a resposta com o mínimo de como configurar essa coisa, para que ela exiba diferenças lado a lado no terminal, o que o OP pediu? As ferramentas da GUI são bastante inúteis no servidor remoto onde você se conecta usando o ssh.
git difftoolcom vimdiffnem sempre se alinham os dois arquivos / buffers corretamente.
git difftool -ypara evitar tkdiff pronta
git difftoolno Windows e Linux: stackoverflow.com/a/48979939/4561887
Você também pode tentar git diff --word-diff. Não é exatamente lado a lado, mas de alguma forma melhor, então você pode preferir à sua real necessidade lado a lado.
git diff --word-diff=color
--word-diff=colorme dá um erro de opção inválida. Em qual versão foi introduzida?
git diff --color-wordsfunciona.
git diff --color-wordsé o caminho a seguir nas versões modernas do git.
ydiff
Anteriormente chamada cdiff, essa ferramenta pode exibir diferenças lado a lado , incremental e colorida .
Em vez de fazer git diff, faça:
ydiff -s -w0
Isso será iniciado ydiffno modo de exibição lado a lado para cada um dos arquivos com diferenças.
Instale com:
python3 -m pip install --user ydiff
-ou-
brew install ydiff
Para git log, você pode usar:
ydiff -ls -w0
-w0detecta automaticamente a largura do seu terminal. Veja a ydiff página do repositório do GitHub para detalhes e demonstração.
Testado no Git 2.18.0, ydiff 1.1.
git diff | cdiff -sao icdiff?
ydiff -spartir de um espaço de trabalho git / svn / hg, você não precisa
cd <git repo>e , em seguida, executeydiff -ls <path/to/file>
Você pode fazer um lado a lado diffusando sdiffo seguinte:
$ git difftool -y -x sdiff HEAD^ | less
Onde HEAD^está um exemplo que você deve substituir pelo que você quer diferenciar.
Encontrei esta solução aqui, onde há algumas outras sugestões também. No entanto, essa resposta é a pergunta do OP de maneira sucinta e clara.
Veja o man git-difftool para uma explicação dos argumentos.
Levando os comentários em consideração, você pode criar um git sdiffcomando útil escrevendo o seguinte script executável:
#!/bin/sh
git difftool -y -x "sdiff -w $(tput cols)" "${@}" | less
Salve como /usr/bin/git-sdiffe chmod -x. Então você poderá fazer isso:
$ git sdiff HEAD^
tput colsem vez disso, por exemplo: git difftool -x "sdiff -s -w $(tput cols)".
export GIT_EXTERNAL_DIFF='meld $2 $5; echo >/dev/null'
então simplesmente:
git diff
Se você quiser ver diferenças lado a lado em um navegador sem envolver o GitHub, poderá desfrutar do git webdiff , um substituto para git diff:
$ pip install webdiff
$ git webdiff
Isso oferece várias vantagens sobre os difftools da GUI tradicional, como tkdiffno sentido de oferecer realce de sintaxe e mostrar diferenças de imagem.
Leia mais sobre isso aqui .
Eu uso colordiff .
No Mac OS X, instale-o com
$ sudo port install colordiff
No Linux, é possível apt get install colordiffou algo assim, dependendo da sua distribuição.
Então:
$ git difftool --extcmd="colordiff -ydw" HEAD^ HEAD
Ou crie um alias
$ git alias diffy "difftool --extcmd=\"colordiff -ydw\""
Então você pode usá-lo
$ git diffy HEAD^ HEAD
Eu o chamei de "diffy" porque diff -yé o diff lado a lado no unix. Colordiff também adiciona cores mais agradáveis. Na opção -ydw, yé para o lado a lado, wé para ignorar espaços em branco e dé para produzir a diferença mínima (geralmente você obtém um melhor resultado como diferença)
-ypara ignorar o Launch 'colordiff' [Y/n]:prompt.
git alias diffy "difftool --extcmd=\"colordiff -ydw\""? Não deveria ser git config --global alias.diffy "difftool --extcmd=\"colordiff -ydw\""?
Para unix, combinando just gite o built-in diff:
git show HEAD:path/to/file | diff -y - path/to/file
Obviamente, você pode substituir HEAD por qualquer outra referência git e provavelmente deseja adicionar algo como -W 170o comando diff.
Isso pressupõe que você está apenas comparando o conteúdo do diretório com uma confirmação anterior. Comparar entre dois commits é mais complexo. Se o seu shell for, bashvocê pode usar "substituição de processo":
diff -y -W 170 <(git show REF1:path/to/file) <(git show REF2:path/to/file)
onde REF1e REF2são referências git - tags, ramificações ou hashes.
Eu pessoalmente gosto muito de icdiff !
Se você estiver em Mac OS Xcom HomeBrew, apenas faça brew install icdiff.
Para obter os rótulos dos arquivos corretamente, além de outros recursos interessantes, tenho no meu ~/.gitconfig:
[pager]
difftool = true
[diff]
tool = icdiff
[difftool "icdiff"]
cmd = icdiff --head=5000 --highlight --line-numbers -L \"$BASE\" -L \"$REMOTE\" \"$LOCAL\" \"$REMOTE\"
E eu uso como: git difftool
Essa pergunta apareceu quando eu estava procurando uma maneira rápida de usar o git builtin para localizar diferenças. Meus critérios de solução:
Encontrei esta resposta para obter cores no git.
Para obter diferenças lado a lado em vez de diferenças de linha, ajustei a excelente resposta do mb14 nesta pergunta com os seguintes parâmetros:
$ git diff --word-diff-regex="[A-Za-z0-9. ]|[^[:space:]]"
Se você não gostar do extra [- ou {+, a opção --word-diff=colorpode ser usada.
$ git diff --word-diff-regex="[A-Za-z0-9. ]|[^[:space:]]" --word-diff=color
Isso ajudou a obter uma comparação adequada com o texto json e xml e o código java.
Em resumo, as --word-diff-regexopções têm uma visibilidade útil, juntamente com as configurações de cores, para obter uma experiência colorida do código-fonte lado a lado em comparação com o diferencial de linha padrão, ao navegar por arquivos grandes com pequenas alterações de linha.
Vários outros já mencionaram o cdiff para diferenciar lado a lado do git, mas ninguém deu uma implementação completa dele.
Setup cdiff:
git clone https://github.com/ymattw/cdiff.git
cd cdiff
ln -s `pwd`/cdiff ~/bin/cdiff
hash -r # refresh your PATH executable in bash (or 'rehash' if you use tcsh)
# or just create a new terminal
Edite ~ / .gitconfig inserindo estas linhas:
[pager]
diff = false
show = false
[diff]
tool = cdiff
external = "cdiff -s $2 $5 #"
[difftool "cdiff"]
cmd = cdiff -s \"$LOCAL\" \"$REMOTE\"
[alias]
showw = show --ext-dif
O pager desativado é necessário para que o cdiff funcione com o Diff, ele é essencialmente um pager de qualquer maneira, portanto está ótimo. A ferramenta Difftool funcionará independentemente dessas configurações.
O alias show é necessário porque o git show suporta apenas ferramentas diff externas via argumento.
O '#' no final do comando externo diff é importante. O comando diff do Git anexa um $ @ (todas as variáveis diff disponíveis) ao comando diff, mas queremos apenas os dois nomes de arquivos. Então, chamamos esses dois explicitamente com US $ 2 e US $ 5 e, em seguida, ocultamos o $ @ por trás de um comentário que, de outra forma, confundiria sdiff. Resultando em um erro parecido com:
fatal: <FILENAME>: no such path in the working tree
Use 'git <command> -- <path>...' to specify paths that do not exist locally.
Comandos Git que agora produzem diferenças lado a lado:
git diff <SHA1> <SHA2>
git difftool <SHA1> <SHA2>
git showw <SHA>
Uso de Cdiff:
'SPACEBAR' - Advances the page of the current file.
'Q' - Quits current file, thus advancing you to the next file.
Agora você tem diff lado a lado via git diff e difftool. E você tem o código-fonte cdiff python para personalização de usuários avançados, caso precise.
Aqui está uma abordagem. Se você passar por menos, a largura xterm é definida como 80, o que não é tão quente. Mas se você prosseguir com o comando, por exemplo, COLS = 210, poderá utilizar o xterm expandido.
gitdiff()
{
local width=${COLS:-$(tput cols)}
GIT_EXTERNAL_DIFF="diff -yW$width \$2 \$5; echo >/dev/null" git diff "$@"
}
Abra Intellij IDEA , selecione uma confirmação única ou múltipla na janela da ferramenta "Controle de Versão", procure os arquivos alterados e clique duas vezes neles para inspecionar as alterações lado a lado de cada arquivo.
Com o iniciador de linha de comando incluído, você pode trazer o IDEA para qualquer lugar com um simples idea some/path
Há muitas boas respostas neste tópico. Minha solução para esse problema foi escrever um script.
Nomeie esse 'git-scriptname' (e torne-o executável e coloque-o no PATH, como qualquer script), e você pode invocá-lo como um comando normal do git executando
$ git scriptname
A funcionalidade real é apenas a última linha. Aqui está a fonte:
#!/usr/bin/env zsh
#
# Show a side-by-side diff of a particular file how it currently exists between:
# * the file system
# * in HEAD (latest committed changes)
function usage() {
cat <<-HERE
USAGE
$(basename $1) <file>
Show a side-by-side diff of a particular file between the current versions:
* on the file system (latest edited changes)
* in HEAD (latest committed changes)
HERE
}
if [[ $# = 0 ]]; then
usage $0
exit
fi
file=$1
diff -y =(git show HEAD:$file) $file | pygmentize -g | less -R
Esta pode ser uma solução um tanto limitada, mas executa o trabalho usando o diffcomando do sistema sem ferramentas externas:
diff -y <(git show from-rev:the/file/path) <(git show to-rev:the/file/path)
--suppress-common-lines(se o seu diffsuportar a opção).diffmarcadores usuais--width=term-width; no Bash pode obter a largura como $COLUMNSou tput cols.Isso também pode ser envolvido em um script git helper para maior comodidade, por exemplo, uso como este:
git diffy the/file/path --from rev1 --to rev2