2013-04-30 167 views
15

這裏是一個簡短的片斷例子(你可以在你的Linux終端粘貼),創建一個新的git存儲庫,並增加了一些文件給它(使用Git版本1.7.9.5):使git狀態顯示未修改/未更改的跟蹤文件?

cd /tmp/ 
mkdir myrepo_git 
cd myrepo_git/ 
git init 
git config user.name "Your Name" 
git config user.email [email protected] 
echo "test" > file_tracked_unchanged.txt 
echo "test" > file_tracked_changed.txt 
echo "test" > file_untracked.txt 
git add file_tracked_unchanged.txt 
git add file_tracked_changed.txt 
git commit -m "initial commit" 

現在,經過初始提交,我想更改file_tracked_changed.txt文件,並使其他人(此處僅爲file_tracked_unchanged.txt)保持不變,以用於下一次提交。下面是一個片斷這表明,和git status VS git ls-files多樣化的輸出(git外殼輸出前綴#):

echo "test more" >> file_tracked_changed.txt 

git status -uno 
# # On branch master 
# # Changes not staged for commit: 
# # (use "git add <file>..." to update what will be committed) 
# # (use "git checkout -- <file>..." to discard changes in working directory) 
# # 
# # modified: file_tracked_changed.txt 
# # 
# no changes added to commit (use "git add" and/or "git commit -a") 
git status 
# # On branch master 
# # Changes not staged for commit: 
# # (use "git add <file>..." to update what will be committed) 
# # (use "git checkout -- <file>..." to discard changes in working directory) 
# # 
# # modified: file_tracked_changed.txt 
# # 
# # Untracked files: 
# # (use "git add <file>..." to include in what will be committed) 
# # 
# # file_untracked.txt 
# no changes added to commit (use "git add" and/or "git commit -a") 
git status -uno --short 
# M file_tracked_changed.txt 
git status --short 
# M file_tracked_changed.txt 
# ?? file_untracked.txt 
git ls-files -v 
# H file_tracked_changed.txt 
# H file_tracked_unchanged.txt 

git add file_tracked_changed.txt 

git status -uno 
# # On branch master 
# # Changes to be committed: 
# # (use "git reset HEAD <file>..." to unstage) 
# # 
# # modified: file_tracked_changed.txt 
# # 
# # Untracked files not listed (use -u option to show untracked files) 
git status 
# # On branch master 
# # Changes to be committed: 
# # (use "git reset HEAD <file>..." to unstage) 
# # 
# # modified: file_tracked_changed.txt 
# # 
# # Untracked files: 
# # (use "git add <file>..." to include in what will be committed) 
# # 
# # file_untracked.txt 
git status -uno --short 
# M file_tracked_changed.txt 
git status --short 
# M file_tracked_changed.txt 
# ?? file_untracked.txt 
git ls-files -v 
# H file_tracked_changed.txt 
# H file_tracked_unchanged.txt 

我在找什麼,是一個命令,它會顯示所有在跟蹤文件一個目錄(git ls-files -v),它們的準確存儲庫狀態(其中git ls-files未顯示,因爲它顯示H爲所有跟蹤文件的狀態)。舉例來說,我想獲得類似的僞代碼:

git status-tracked 
# M file_tracked_changed.txt 
# . file_tracked_unchanged.txt 

...其中點.將一個符號指示跟蹤,但不變的文件(如果我沒有記錯,SVN可以使用U字符對於這些)。

最後,我想也顯示所有文件的狀態在一個目錄,如僞代碼:

git status-tracked-and-untracked 
# M file_tracked_changed.txt 
# . file_tracked_unchanged.txt 
# ?? file_untracked.txt 

...但要獲得所有的狀態,這是對我來說更重要跟蹤文件,如上面的僞git status-tracked

git中的任何命令,已經做了這樣的事情?

+0

嘗試'混帳地位的評論-sb' – Kartik 2013-04-30 19:05:55

+2

非常感謝@Kartik - 但該命令顯示跟蹤修改+ untracked;我正在尋找一個命令,顯示跟蹤修改+跟蹤未修改。乾杯! – sdaau 2013-04-30 19:15:34

回答

0
git status -s | egrep -v '^\?\?' 

這會過濾掉以??開頭的行,即未跟蹤的文件。

+1

感謝您的答案,@Andomar - 但不幸的是,該命令不顯示跟蹤但未修改的文件,這正是我所要求的。乾杯! – sdaau 2013-04-30 19:13:31

+1

'git ls-tree --name-status HEAD'應該做你想做的事情,但是它默默地忽略了'-status'部分:) – Andomar 2013-04-30 19:28:31

+0

非常感謝,@Andomar - 很棒的提示,我對'ls-tree ',但正如你所說,狀態沒有顯示 - 所以我剛剛發佈了[答案](http://stackoverflow.com/a/16308182/277826),它將來自'git's'status'的狀態「交錯」和'ls-files'。乾杯! – sdaau 2013-04-30 20:12:31

3

感謝@Andomar,對於git ls-tree提示;這是它表明:

git ls-tree --name-status HEAD 
# file_tracked_changed.txt 
# file_tracked_unchanged.txt 

...但我想狀態:)

 

OK,這裏是一個解決方案,既呼喚和ls-filesstatus,並將它們與位的交織bash解析:

git ls-files -cdmoskt --abbrev=8 | while read -r line; do \ 
    fn=$(echo "$line" | sed 's/.*\s\(\w\+\)/\1/'); \ 
    st=$(git status -s "$fn" | printf "%-02s " $(sed 's/\([[:print:]]\+\)\s.*/\1/')); \ 
    echo "$st- $line"; \ 
done 

如果運行此作爲OP例子,你就會得到:

git ls-files -cdmoskt --abbrev=8 | while read -r line; do fn=$(echo "$line" | sed 's/.*\s\(\w\+\)/\1/'); st=$(git status -s "$fn" | printf "%-02s " $(sed 's/\([[:print:]]\+\)\s.*/\1/')); echo "$st- $line"; done 
# ?? - ? file_untracked.txt 
# M - H 100644 52e7a08e 0 file_tracked_changed.txt 
# - H 100644 9daeafb9 0 file_tracked_unchanged.txt 

......這基本上是我想要的。 (如果我有幸將其轉換爲git別名,我會在這裏回覆)。


編輯:這裏git別名(~/.gitconfig):

ls-fstatus = "! cd $PWD/$GIT_PREFIX; git ls-files -cdmoskt --abbrev=8 | while read -r line; do \ 
    fn=$(echo \"$line\" | sed \"s/.*\\s\\([[:print:]]\\+\\)/\\1/\"); \ 
    st=$(git status -s "$fn" | printf \"%-02s \" $(sed \"s/\\([[:print:]]\\+\\)\\s.*/\\1/\")); \ 
    echo \"$st- $line\"; \ 
    done " 

...這樣一個可以叫git ls-fstatus在一個給定的git回購子目錄。

+0

這不處理帶空格的路徑。通過在cd參數中加上引號,它可以工作:'cd \「$ PWD/$ GIT_PREFIX \」;' – KeithB 2015-03-27 14:48:19

7

謝謝@sdaau。

git ls-files | while read -r line; 
do 
    st=$(git status -s "$line"); 
    if [ -n "$st" ]; then 
     echo "$st"; 
    else 
     echo " $line"; 
    fi; 
done 
+0

^非常有用,但仍然有點慢,因爲它爲每個文件運行一個git_status。 – frnhr 2015-07-04 12:15:44

1

通過@RogerDueck's answer的啓發,我做了執行git ls-filesgit status只有一次每一個腳本:所以它的運行速度更快,並提供相同的格式結果git status我做了一些新的變化。它在約1700個文件的回購期內運行速度提高了15倍,僅需不到2秒。

編輯:增加了一些修復和一些單元測試中,轉移到GitHub上:https://github.com/frnhr/git-fullstatus

輸出示例:

M some/file 
D another/file 
D more/files/blahblah 
A this/is/an/added/file/i/think 
    an/unchanged_file 
    another/unchanged_file