简体   繁体   中英

Git status ignore line endings / identical files / windows & linux environment / dropbox / meld

How do I make

git status

ignore line ending differences?

Background info:

I use randomly Windows and Linux to work on the project. The project is in Dropbox.

I found a lot about how do make git diff ignore line endings. Since i use meld git diff opens meld for each file. And meld says "identical file".

So how do I avoid this. Git should only open meld for changed files. And git status should not report files as changed if only the file ending is different.

EDIT: Cause:

This happened because of this setting on Windows

core.autocrlf true

So I checked out the working copy on Linux and set core.autocrlf false on Windows.

It would be still nice to know how to make git status ignore different new lines.

尝试像这样设置 core.autocrlf 值:

git config --global core.autocrlf true

This answer seems relevant since the OP makes reference to a need for a multi-OS solution. This Github help article details available approaches for handling lines endings cross-OS. There are global and per-repo approaches to managing cross-os line endings.

Global approach

Configure Git line endings handling on Linux or OS X:

git config --global core.autocrlf input

Configure Git line endings handling on Windows:

git config --global core.autocrlf true

Per-repo approach:

In the root of your repo, create a .gitattributes file and define line ending settings for your project files, one line at a time in the following format: path_regex line-ending-settings where line-ending-settings is one of the following:

  • text
  • binary (files that Git should not modify line endings for - as this can cause some image types such as PNGs not to render in a browser)

The text value can be configured further to instruct Git on how to handle line endings for matching files:

  • text - Changes line endings to OS native line endings.
  • text eol=crlf - Converts line endings to CRLF on checkout.
  • text eol=lf - Converts line endings to LF on checkout.
  • text=auto - Sensible default that leaves line handle up to Git's discretion.

Here is the content of a sample .gitattributes file:

# Set the default behavior for all files.
* text=auto

# Normalized and converts to 
# native line endings on checkout.
*.c text
*.h text

# Convert to CRLF line endings on checkout.
*.sln text eol=crlf

# Convert to LF line endings on checkout.
*.sh text eol=lf

# Binary files.
*.png binary
*.jpg binary

More on how to refresh your repo after changing line endings settings here . Tldr:

backup your files with Git, delete every file in your repository (except the .git directory), and then restore the files all at once. Save your current files in Git, so that none of your work is lost.

git add . -u

git commit -m "Saving files before refreshing line endings"

Remove the index and force Git to rescan the working directory.

rm .git/index

Rewrite the Git index to pick up all the new line endings.

git reset

Show the rewritten, normalized files.

In some cases, this is all that needs to be done. Others may need to complete the following additional steps:

git status

Add all your changed files back, and prepare them for a commit. This is your chance to inspect which files, if any, were unchanged.

git add -u

It is perfectly safe to see a lot of messages here that read[s] "warning: CRLF will be replaced by LF in file."

Rewrite the .gitattributes file.

git add .gitattributes

Commit the changes to your repository.

git commit -m "Normalize all the line endings"

Use .gitattributes instead, with the following setting:

# Ignore all differences in line endings
*        -crlf

.gitattributes would be found in the same directory as your global .gitconfig. If .gitattributes doesn't exist, add it to that directory. After adding/changing .gitattributes you will have to do a hard reset of the repository in order to successfully apply the changes to existing files.

Issue related to git commands on Windows operating system:

$ git add --all

warning: LF will be replaced by CRLF in ...

The file will have its original line endings in your working directory.

Resolution :

$ git config --global core.autocrlf false     
$ git add --all 

No any warning messages come up.

I created a script to ignore differences in line endings:

It will display the files which are not added to the commit list and were modified (after ignoring differences in line endings). You can add the argument "add" to add those files to your commit.

#!/usr/bin/perl

# Usage: ./gitdiff.pl [add]
#    add : add modified files to git

use warnings;
use strict;

my ($auto_add) = @ARGV;
if(!defined $auto_add) {
    $auto_add = "";
}

my @mods = `git status --porcelain 2>/dev/null | grep '^ M ' | cut -c4-`;
chomp(@mods);
for my $mod (@mods) {
    my $diff = `git diff -b $mod 2>/dev/null`;
    if($diff) {
        print $mod."\n";
        if($auto_add eq "add") {
            `git add $mod 2>/dev/null`;
        }
    }
}

Source code: https://github.com/lepe/scripts/blob/master/gitdiff.pl

Updates :

  • fix by evandro777 : When the file has space in filename or directory

I use both windows and linux, but the solution core.autocrlf true didn't help me. I even got nothing changed after git checkout <filename> .

So I use workaround to substitute git status - gitstatus.sh

#!/bin/bash

git status | grep modified | cut -d' ' -f 4 | while read x; do
 x1="$(git show HEAD:$x | md5sum | cut -d' ' -f 1 )"
 x2="$(cat $x | md5sum | cut -d' ' -f 1 )"

 if [ "$x1" != "$x2" ]; then
    echo "$x NOT IDENTICAL"
 fi
done

I just compare md5sum of a file and its brother at repository.

Example output:

$ ./gitstatus.sh
application/script.php NOT IDENTICAL
application/storage/logs/laravel.log NOT IDENTICAL

I've changed + shukshin.ivan script a bit - to ignore windows / linux line ending.

#!/bin/bash

git status | grep modified | cut -d' ' -f 4 | while read x; do
  d="$(git --no-pager diff --ignore-cr-at-eol $x)"

  if [ "$d" ]; then
    echo "$x NOT IDENTICAL"
  else
    echo "$x IDENTICAL"
    # uncomment the next line to undo the line ending changes
    # git checkout $x
  fi
done

In vscode, just stage everything - the files that differ only by line endings should disappear, leaving behind only the files that differ in content. You can then unstage to get to the state you expected.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM