--- ATUALIZAÇÃO 3 --- (não entra em conflito com a ATUALIZAÇÃO 2)
Considerando o caso em que os usuários do Windows preferem trabalhar CRLF
e os usuários Linux / Mac preferem trabalhar em LF
arquivos de texto. Fornecendo a resposta da perspectiva de um mantenedor de repositório :
Para mim, a melhor estratégia (menos problemas a resolver) é: mantenha todos os arquivos de texto com o LF
git repo, mesmo se você estiver trabalhando em um projeto somente para Windows. Em seguida, permita que os clientes trabalhem no estilo de final de linha de sua preferência , desde que eles escolham um core.autocrlf
valor de propriedade que respeite sua estratégia (LF no repo) enquanto prepara arquivos para confirmação.
A preparação é o que muitas pessoas confundem ao tentar entender como as estratégias de nova linha funcionam. É essencial entender os seguintes pontos antes de escolher o valor correto para a core.autocrlf
propriedade:
- Adicionar um arquivo de texto para confirmação ( prepará- lo) é como copiar o arquivo para outro local dentro
.git/
do subdiretório com finais de linha convertidos (dependendo do core.autocrlf
valor da configuração do cliente). Tudo isso é feito localmente.
- configuração
core.autocrlf
é como fornecer uma resposta para a pergunta (exatamente a mesma pergunta em todos os sistemas operacionais):
- "O git-client a. Converte LF em CRLF ao fazer check-out (puxando) o repo muda do controle remoto ou b. Converte CRLF em LF ao adicionar um arquivo para confirmação? " E as possíveis respostas (valores) estamos:
false:
" não execute nenhuma das opções acima ",
input:
" faça apenas b "
true
: " faça aeb "
- note que NÃO existe " faça apenas um "
Felizmente
- Os padrões do cliente git (windows
core.autocrlf: true
:, linux / mac:)
core.autocrlf: false
serão compatíveis com a estratégia LF-only-repo .
Significado : os clientes do Windows, por padrão, serão convertidos em CRLF ao fazer check-out do repositório e convertidos em LF ao adicionar para confirmação. E os clientes linux, por padrão, não fazem conversões. Teoricamente, isso mantém o seu repositório apenas.
Infelizmente:
- Pode haver clientes GUI que não respeitam o
core.autocrlf
valor git
- Pode haver pessoas que não usam um valor para respeitar sua estratégia de lf-repo. Por exemplo, eles usam
core.autocrlf=false
e adicionam um arquivo com CRLF para confirmação.
Para detectar arquivos de texto ASAP não lf confirmados pelos clientes acima, você pode seguir o que está descrito em --- atualização 2 ---: ( git grep -I --files-with-matches --perl-regexp '\r' HEAD
, em um cliente compilado usando: --with-libpcre
flag)
E aqui está o problema: . Como mantenedor de repositório, mantenho um git.autocrlf=input
arquivo para que eu possa corrigir todos os arquivos confirmados incorretamente apenas adicionando-os novamente para confirmação. E forneço um texto de confirmação: "Corrigindo arquivos confirmados incorretamente".
Tanto quanto .gitattributes
é aprendido. Não conto com isso, porque há mais clientes de interface do usuário que não entendem. Só o uso para fornecer dicas para arquivos binários e de texto e talvez sinalizar alguns arquivos excepcionais que devem manter em todos os lugares as mesmas terminações de linha:
*.java text !eol # Don't do auto-detection. Treat as text (don't set any eol rule. use client's)
*.jpg -text # Don't do auto-detection. Treat as binary
*.sh text eol=lf # Don't do auto-detection. Treat as text. Checkout and add with eol=lf
*.bat text eol=crlf # Treat as text. Checkout and add with eol=crlf
Pergunta: Mas por que estamos interessados na estratégia de manipulação de novas linhas?
Resposta: Para evitar uma confirmação de alteração de letra única, apareça como uma alteração de 5000 linhas , apenas porque o cliente que executou a alteração converteu automaticamente o arquivo completo de crlf para lf (ou o oposto) antes de adicioná-lo para confirmação. Isso pode ser bastante doloroso quando há uma resolução de conflito envolvida. Ou, em alguns casos, pode ser a causa de conflitos irracionais.
--- ATUALIZAÇÃO 2 ---
Os padrões do cliente git funcionarão na maioria dos casos. Mesmo se você tiver apenas clientes com Windows, Linux apenas com clientes ou ambos. Esses são:
- windows:
core.autocrlf=true
significa converter linhas em CRLF no checkout e converter linhas em LF ao adicionar arquivos.
- linux:
core.autocrlf=input
significa não converter linhas no checkout (não é necessário, pois é esperado que os arquivos sejam comprometidos com o LF) e converter linhas em LF (se necessário) ao adicionar arquivos. ( - update3 - : parece que está false
por padrão, mas novamente está bom)
A propriedade pode ser configurada em diferentes escopos. Eu sugeriria definir explicitamente o --global
escopo, para evitar alguns problemas de IDE descritos no final.
git config core.autocrlf
git config --global core.autocrlf
git config --system core.autocrlf
git config --local core.autocrlf
git config --show-origin core.autocrlf
Também desencorajaria fortemente o uso no Windows git config --global core.autocrlf false
(no caso de você possuir apenas clientes Windows), em contraste com o que é proposto para a documentação do git . Definir como false confirmará os arquivos com CRLF no repositório. Mas realmente não há razão. Você nunca sabe se precisará compartilhar o projeto com os usuários do Linux. Além disso, é uma etapa extra para cada cliente que ingressa no projeto em vez de usar os padrões.
Agora, para alguns casos especiais de arquivos (por exemplo *.bat
*.sh
), nos quais você deseja que eles sejam verificados com LF ou com CRLF, você pode usar.gitattributes
Para resumir, a melhor prática é:
- Verifique se todos os arquivos não binários estão confirmados com o LF no git repo (comportamento padrão).
- Use este comando para certificar-se de que nenhum arquivo seja confirmado com o CRLF:
git grep -I --files-with-matches --perl-regexp '\r' HEAD
( Nota: no windows clients funciona apenas através git-bash
e no linux clients somente se compilado usando --with-libpcre
in ./configure
).
- Se você encontrar esses arquivos executando o comando acima, corrija-os. Isso envolve (pelo menos no linux):
- set
core.autocrlf=input
( --- atualização 3 - )
- mudar o arquivo
- reverter a alteração (o arquivo ainda é mostrado como alterado)
- comprometa
- Use apenas o mínimo necessário
.gitattributes
- Instrua os usuários a definir o
core.autocrlf
descrito acima para seus valores padrão.
- Não conte 100% na presença de
.gitattributes
. os clientes-git dos IDEs podem ignorá-los ou tratá-los de maneira diferente.
Como dito, algumas coisas podem ser adicionadas nos atributos git:
# Always checkout with LF
*.sh text eol=lf
# Always checkout with CRLF
*.bat text eol=crlf
Eu acho que algumas outras opções seguras para, em .gitattributes
vez de usar a detecção automática de arquivos binários:
-text
(por exemplo, para *.zip
ou *.jpg
arquivos: não serão tratados como texto. Portanto, nenhuma conversão de final de linha será tentada. A diferença pode ser possível através de programas de conversão)
text !eol
(por exemplo *.java
, for *.html
:: tratado como texto, mas a preferência de estilo eol não está definida. Portanto, a configuração do cliente é usada.)
-text -diff -merge
(por exemplo, para *.hugefile
: Não tratado como texto. Não é possível obter diferenças / mesclagens)
--- ATUALIZAÇÃO ANTERIOR ---
Um exemplo doloroso de um cliente que confirmará arquivos incorretamente:
O netbeans 8.2 (no Windows) comprometerá erroneamente todos os arquivos de texto com CRLFs, a menos que você tenha definido explicitamente core.autocrlf
como global . Isso contradiz o comportamento padrão do cliente git e causa muitos problemas posteriormente, durante a atualização / mesclagem. É isso que faz com que alguns arquivos pareçam diferentes (embora não sejam), mesmo quando você reverte .
O mesmo comportamento no netbeans acontece mesmo se você adicionou o correto .gitattributes
ao seu projeto.
Usar o comando a seguir após uma confirmação, pelo menos, ajudará a detectar com antecedência se o seu repositório git tem problemas de final de linha: git grep -I --files-with-matches --perl-regexp '\r' HEAD
Passei horas para encontrar o melhor uso possível .gitattributes
, para finalmente perceber, que não posso contar com isso.
Infelizmente, enquanto existirem editores baseados em JGit (que não podem ser manipulados .gitattributes
corretamente), a solução segura é forçar o LF em qualquer lugar, mesmo no nível do editor.
Use os seguintes anti-CRLF
desinfetantes.
.gitattributes
?