我在git上弄湿了脚,并遇到以下问题:
我的项目源码树:
/
|
+--src/
+----refs/
+----...
|
+--vendor/
+----...
我在我的供应商分支中有代码(目前是MEF),我将在那里编译,然后将引用移动到/src/refs
,这是项目从中获取的。
我的问题是我的.gitignore
设置为忽略*.dll
和*.pdb
。我可以做一个git add -f bar.dll
强制添加被忽略的文件,这是好的,问题是我无法弄清楚列出哪些文件存在被忽略。
我想列出被忽略的文件,以确保我不会忘记添加它们。
我已经阅读了git ls-files
上的手册页,但无法使其正常工作。在我看来,git ls-files --exclude-standard -i
应该做我想要的。我错过了什么?
笔记:
git status --ignored
(详见“Is there a way to tell git-status to ignore the effects of .gitignore
files?”)git clean -ndX
适用于较旧的gits,显示可以删除被忽略文件的预览(不删除任何内容)同样有趣(在qwertymk的answer中提到),你也可以使用git check-ignore -v
命令,至少在Unix上(在CMD Windows会话中不起作用)
git check-ignore *
git check-ignore -v *
第二个显示.gitignore
的实际规则,它使你的git仓库中的文件被忽略。
在Unix上,使用“What expands to all files in current directory recursively?”和bash4 +:
git check-ignore **/*
(或find -exec
命令)
原始答案42009)
git ls-files -i
应该工作,除了its source code表明:
if (show_ignored && !exc_given) {
fprintf(stderr, "%s: --ignored needs some exclude pattern\n",
argv[0]);
exc_given
?
事实证明,在-i
之后需要一个更多的参数来实际列出任何东西:
尝试:
git ls-files -i --exclude-from=[Path_To_Your_Global].gitignore
(但这只列出你的缓存(非忽略)对象,带有过滤器,所以这不是你想要的)
例:
$ cat .git/ignore
# ignore objects and archives, anywhere in the tree.
*.[oa]
$ cat Documentation/.gitignore
# ignore generated html files,
*.html
# except foo.html which is maintained by hand
!foo.html
$ git ls-files --ignored \
--exclude='Documentation/*.[0-9]' \
--exclude-from=.git/ignore \
--exclude-per-directory=.gitignore
实际上,在我的'gitignore'文件(称为'exclude')中,我找到了一个可以帮助你的命令行:
F:\prog\git\test\.git\info>type exclude
# git ls-files --others --exclude-from=.git/info/exclude
# Lines that start with '#' are comments.
# For a project mostly in C, the following would be a good set of
# exclude patterns (uncomment them if you want to use them):
# *.[oa]
# *~
所以....
git ls-files --others --ignored --exclude-from=.git/info/exclude
git ls-files -o -i --exclude-from=.git/info/exclude
git ls-files --others --ignored --exclude-standard
git ls-files -o -i --exclude-standard
应该做的伎俩。
正如ls-files man page中所提到的,--others
是重要的部分,以向您展示非缓存,未提交,通常被忽略的文件。
--exclude_standard
不仅仅是一种捷径,而是一种包含所有标准“忽略模式”设置的方法。
exclude-standard
在每个目录中添加标准git排除:.git/info/exclude
,.gitignore
和user's global exclusion file
。
有一种更简单的方法(git 1.7.6+):
git status --ignored
见Is there a way to tell git-status to ignore the effects of .gitignore files?
另一个非常干净的选择(没有双关语。):
git clean -ndX
说明:
$ git help clean
git-clean - Remove untracked files from the working tree
-n, --dry-run - Don't actually remove anything, just show what would be done.
-d - Remove untracked directories in addition to untracked files.
-X - Remove only files ignored by Git.
注意:此解决方案不会显示已删除的已忽略文件。
虽然通常正确,但您的解决方案并不适用于所有情况。假设一个repo dir是这样的:
# ls **/*
doc/index.html README.txt tmp/dir0/file0 tmp/file1 tmp/file2
doc:
index.html
tmp:
dir0 file1 file2
tmp/dir0:
file0
和.gitignore这样:
# cat .gitignore
doc
tmp/*
这忽略了doc
目录和tmp
下面的所有文件。 Git按预期工作,但列出被忽略文件的给定命令却没有。让我们来看看git有什么话要说:
# git ls-files --others --ignored --exclude-standard
tmp/file1
tmp/file2
请注意,列表中缺少doc
。你可以得到它:
# git ls-files --others --ignored --exclude-standard --directory
doc/
注意额外的--directory
选项。
据我所知,没有一个命令可以一次列出所有被忽略的文件。但我不知道为什么tmp/dir0
根本没有出现。
它应该足够使用
git ls-files --others -i --exclude-standard
因为它涵盖了所涵盖的一切
git ls-files --others -i --exclude-from=.git/info/exclude
因此后者是多余的。
~/.gitconfig
file:
git config --global alias.ignored "ls-files --others -i --exclude-standard"
现在您只需输入git ignored
即可查看列表。更容易记住,更快打字。
如果您更喜欢Jason Geng解决方案的更简洁的显示,您可以为此添加别名:
git config --global alias.ignored "status --ignored -s"
但是,更详细的输出对于解决.gitignore文件的问题更有用,因为它列出了被忽略的每个棉花挑选文件。您通常会通过grep
管道结果,以查看您希望被忽略的文件是否在那里,或者您不希望忽略的文件在那里。
git ignored | grep some-file-that-isnt-being-ignored-properly
然后,当您只想看一个简短的显示时,它很容易记住并输入
git status --ignored
(-s
通常可以不用了。)
以下是如何在工作树中打印完整的文件列表,这些文件列表位于Git的多个gitignore源中的任何位置(如果您使用的是GNU find
):
$ cd {your project directory}
$ find . -path ./.git -prune -o -print \
| git check-ignore --no-index --stdin --verbose
它将检查存储库当前分支中的所有文件(除非您已在本地删除它们)。
它还标识了特定的gitignore源代码行。
Git继续跟踪一些与gitignore模式匹配的文件的变化,因为这些文件已经添加了。有用的是,上面的命令也会显示这些文件。
负gitignore模式也匹配。但是,这些在列表中很容易区分,因为它们以!
开头。
如果你使用Windows,Git Bash包括GNU find
(由find --version
透露)。
如果列表很长(并且你有rev
),你也可以通过扩展(稍微)显示它们:
$ cd {your project directory}
$ find . -path ./.git -prune -o -print \
| git check-ignore --no-index --stdin --verbose \
| rev | sort | rev
有关更多详细信息,请参阅man find
,man git-check-ignore
,man rev
和man sort
。
整个方法的关键在于Git(软件)正在快速变化并且非常复杂。相比之下,GNU的find
非常稳定(至少在这里使用的功能)。因此,任何希望通过展示他们对Git的深入了解而具有竞争力的人都会以不同的方式回答这个问题。
什么是最好的答案?这个答案有意地最大限度地减少了对Git知识的依赖,通过模块化(信息隔离)实现稳定性和简单性的目标,并且旨在持续很长时间。
(扩展其他答案)
注意,git check-ignore
使用提交的.gitignore
而不是你工作树中的那个!要使用它而不污染您的git历史记录,您可以自由地尝试编辑它,然后使用git commit --amend
进行提交。
出现此问题主要是因为您需要解决问题的方法,即git不遵循目录。输入.gitignore
:
dirtokeep/**
!dirtokeep/.keep
.keep
应该是dirtokeep
中的零长度文件。
结果将是dirtokeep
中的所有内容都将被忽略,除了dirtokeep/.keep
,这将导致dirtokeep
目录将在clone / checkout上构建。
假设有一些忽略目录,为什么不使用“git status node / logs /”来告诉你要添加哪些文件?在目录中,我有一个不属于状态输出的文本文件,例如:
在分支大师 您的分支机构与“origin / master”保持同步。 未跟踪的文件: (使用“git add ...”包含将要提交的内容)
node/logs/.gitignore
.gitignore是:
* !的.gitignore