O git é bom com arquivos binários?

97

O git é bom com arquivos binários?

Se eu tivesse muitos arquivos descompactados sendo modificados, e muitos arquivos compactados nunca (ou quase nunca) modificados, o git lidaria bem com isso? Por exemplo, se eu inserir ou remover o meio e inserir dados perto do final, ele notará isso como acontece com o texto?

Se o git não for bom com arquivos binários, qual ferramenta devo considerar?

TRiG
fonte
1
muito bom com binário - eu mesmo uso
tekknolagi
É meio verdade. Você pode colocar seu / home na revisão git e deve funcionar muito bem.
Loïc Faure-Lacroix
1
Isso não está no espírito da pergunta, que foi claramente observada como preocupação sobre se os arquivos binários tinham diferenças feitas neles (provavelmente por excesso de repositório e por motivos de desempenho). No entanto, não votei contra ele (e parece que quem o fez o removeu).
coreyward de
1
Observação: agora você tem git-lts, para armazenar seus binários em outro lugar: stackoverflow.com/a/29530784/6309
VonC,
1
Isso incha a pasta .git?
Nikhil

Respostas:

47

Pronto para uso, o git pode facilmente adicionar arquivos binários ao seu índice e também armazená-los de uma maneira eficiente, a menos que você faça atualizações frequentes em grandes arquivos não compactáveis.

Os problemas começam quando o git precisa gerar diffs e mesclagens: git não pode gerar diffs significativos ou mesclar arquivos binários de qualquer maneira que possa fazer sentido. Portanto, todas as mesclagens, rebases ou escolhas que envolvem uma alteração em um arquivo binário envolvem você na resolução manual de conflitos nesse arquivo binário.

Você precisa decidir se as alterações no arquivo binário são raras o suficiente para que você possa conviver com o trabalho manual extra que elas causam no fluxo de trabalho normal do git envolvendo mesclagens, rebases, escolhas seletivas.

ndim
fonte
26
Eu teria que salientar que as alterações em arquivos binários não são um problema, fazer alterações em vários lugares e, em seguida, tentar mesclá-los é.
Winston Ewert
15
git pode gerar diferenças significativas. Um diff criado com git diff --binaryserá capaz de corrigir arquivos binários.
CB Bailey de
46

Além de outras respostas.

  • Você pode enviar um diff para um arquivo binário usando o chamado formato diff binário . Não é legível por humanos e só pode ser aplicado se você tiver uma pré-imagem exata em seu repositório, ou seja, sem fuzz.
    Um exemplo:

    diff --git a/gitweb/git-favicon.png b/gitweb/git-favicon.png
    index de637c0608090162a6ce6b51d5f9bfe512cf8bcf..aae35a70e70351fe6dcb3e905e2e388cf0cb0ac3 100
    GIT binary patch
    delta 85
    zcmZ3&SUf?+pEJNG#Pt9J149GD|NsBH{?u>)*{Yr{jv*Y^lOtGJcy4sCvGS>LGzvuT
    nGSco!%*slUXkjQ0+{(x>@rZKt$^5c~Kn)C@u6{1-oD!M<s|Fj6
    
    delta 135
    zcmXS3!Z<;to+rR3#Pt9J149GDe=s<ftM(tr<t*@sEM{Qf76xHPhFNnYfP!|OE{-7;
    zjI0MY3OYE5upapO?DR{I1pyyR7cx(jY7y^{FfMCvb5IaiQM`NJfeQjFwttKJyJNq@
    hveI=@x=fAo=hV3$-MIWu9%vGSr>mdKI;RB2CICA_GnfDX
    
  • Você pode usar textconv gitattribute para git diffmostrar diff legível por humanos para arquivos binários ou partes de arquivos binários. Por exemplo, para arquivos * .jpg, pode haver diferença nas informações EXIF, para arquivos PDF pode haver diferença entre sua representação de texto (pdf2text ou algo parecido).

HTH.

Jakub Narębski
fonte
5
Muito obrigado por me ensinar sobre gitattributes! Abre um novo mundo de possibilidades.
hermannloose
15

Se você tiver arquivos binários realmente grandes, pode usar git-attachment para armazenar os dados fora do repositório. Confira: http://git-annex.branchable.com/

John Gibb
fonte
6
O anexo Git é maravilhoso, mas provavelmente mais adequado para arquivos que não mudam com
tanta
@sr_ exatamente, Git LFS também. Parece que não existe um sistema de controle de versão adequado para este tipo de casos de uso, tendo também um sistema distribuído como base (como o Git).
Marc J. Schmidt
5

Não conheço nenhuma ferramenta que tente armazenar diffs de arquivos binários para controle de versão, mas é importante notar que o Git não faz isso nem mesmo para arquivos de texto. O Git armazena arquivos como blobs e faz uma diferença entre eles quando necessário.

Se você está procurando fazer o controle de versão em algo como documentos do Photoshop / Illustrator, o GridIron Flow pode fazer o truque para você. Se você está tentando mantê-los sincronizados entre as máquinas, o Dropbox ou Rsync pode lidar com isso, mas eles não farão diferenças inteligentes.

Coreyward
fonte
1
Do livro da comunidade git ( book.git-scm.com/7_how_git_stores_objects.html ): "Para economizar esse espaço, o Git utiliza o packfile. Este é um formato onde o Git salvará apenas a parte que foi alterada no segundo arquivo , com um ponteiro para o arquivo ao qual é semelhante. "
Wayne Conrad
2
Sim, é se / quando você corre git gcpara fazer a coleta de lixo. Da mesma página: "Como o Git armazena cada versão de cada arquivo como um objeto separado, ele pode se tornar bastante ineficiente. Imagine ter um arquivo com vários milhares de linhas e alterar uma única linha. O Git armazenará o segundo arquivo por completo, o que é um grande desperdício de espaço. "
coreyward de
2
Fair 'nuff. git faz gc automaticamente de vez em quando, pelo menos para o projeto em que o uso. Não sei qual métrica ele usa para decidir quando executar - talvez haja árvores que nunca (ou raramente) acionariam o gc.
Wayne Conrad
1
Na página de manual de git gc: "Os usuários são incentivados a executar esta tarefa regularmente em cada repositório para manter uma boa utilização do espaço em disco e um bom desempenho operacional. Alguns comandos git podem executar git gc automaticamente; consulte a sinalização --auto abaixo para obter detalhes . "
Jacob Akkerboom,
1
@KennyEvitt Há uma tonelada agora. Abstract é um, e Kactus é outro que usa git nos bastidores.
coreyward
3

Bem, git é bom com binários. Mas não lida com binários como arquivos de texto. É como se você quisesse mesclar arquivos binários. Quero dizer, um diff em um jpeg nunca retornará nada. Git funciona muito bem com arquivos de texto e provavelmente tão ruim quanto qualquer outra solução com arquivos binários!

Loïc Faure-Lacroix
fonte
2

se você quiser uma solução para o controle de versão, pode considerar git-lfs, que possui um ponteiro leve para o seu arquivo.

significa que quando você clona seu repo, ele não baixa todas as versões, mas apenas aquela que está em check-out.

Aqui está um bom tutorial de como usá-lo

Danfromisrael
fonte