git可以忽略一个特定的行吗?
我正在使用git在电话的本地浏览器上进行testing时同步到phonegap。 因此,我有以下行:
var isPhoneGap = false;
显然我在修改时会改变这个,但是有什么办法可以让git忽略这一行,或者我必须把它放在它自己的文件中并且忽略它吗?
我在OSX 10.6上使用Gitx和terminal。
如果你的文件是一个特定的types,你可以声明一个内容filter驱动程序 ,你可以在.gitattributes
文件中声明(如“ Git Attributes ”的“关键字扩展”所示):
*.yourType filter=yourFilterName
(你甚至可以为特定的文件设置filter ,如果你想的话)
实行:
-
yourFilterName.smudge
(在git checkout
上触发)和git config --global filter.yourFilterName.smudge 'sed "s/isPhoneGap = .*/isPhoneGap = true/"'
-
yourFilterName.clean
(触发git add
)git config --global filter.yourFilterName.clean 'sed "s/isPhoneGap = .*/isPhoneGap = false/"'
您的文件在git status
显示不变,但其检出版本对于isPhoneGap
将具有正确的值。
您可以使用
git update-index --assume-unchanged [file]
忽略一个你不想跟踪的文件的变化。 当我需要在存储库中有一个文件时,我使用这个解决scheme,但是这个文件有一些改变的部分,我不需要总是跟踪。
当文件有重要的变化,你必须这样做:
git update-index --no-assume-unchanged [file]
另外,请参阅Git doc update-index for --[no-]assume-unchanged
参数。
当指定这些标志时,为pathlogging的对象名称不会更新。 相反,这些选项设置和取消path的“假定不变”位。 当“假设不变”位打开时,git停止检查工作树文件以进行可能的修改,因此当您更改工作树文件时,需要手动取消该位以告诉git。
Gitx应该允许你提交或忽略单行(你可能已经知道),但是每次提交时都必须这样做。 我认为最好每个部署目标都有一个configuration文件(你可以对它们进行版本控制),而对于你启动服务器的一些运行时参数(比如./myserver --config=whatever.js
)。
内容filter驱动程序不是一个好的解决scheme。 你可能可以隐藏这条线从git status
/ etc,但它并没有真正被忽略。 只要您更改该值,即使更改可能不可见,您的工作目录将被标记为脏。
如果你真的想把这一行放在版本控制之外,把它改成一个命令行参数,或者把它放在一个被忽略的包含或构build文件中,这可能是唯一的实际方法。
这就是你可以用gitfilter来做的事情:
- 创build/打开gitattributes文件:
- <project root> /。gitattributes(将会被提交回购)
要么 - <project root> /。git / info / attributes(不会被提交回购)
- <project root> /。gitattributes(将会被提交回购)
- 添加一行定义要过滤的文件:
-
*.rb filter=gitignore
,即在所有*.rb
文件上运行名为gitignore
filter
-
- 在你的
gitconfig
定义gitignore
filter:-
$ git config --global filter.gitignore.clean "sed '/#gitignore$/'d"
,即删除这些行 -
$ git config --global filter.gitignore.smudge cat
,即从回购库中拉取文件时什么也不做
-
笔记:
当然,这是针对ruby文件的,当一行以#gitignore
时应用,在~/.gitconfig
全局应用。 修改这个,但你需要你的目的。
警告!!
这使您的工作文件与回购(当然)不同。 任何退房或重新绑定将意味着这些线路将会丢失! 这个技巧可能看起来没有用处,因为这些行在检出,重定位或拉动时会反复丢失,但是我已经有了一个特定的用例来使用它。
只是git stash save "proj1-debug"
而filter是无效的 (只是暂时禁用它在gitconfig
或东西)。 这样一来,我的debugging代码就可以随时将git stash apply
到我的代码中,而不必担心这些行会被意外提交。
我有一个可能的想法来处理这些问题,但我会尝试在其他时间实施。
感谢Rudi和jw013提到gitfilter和gitattributes。
继续https://stackoverflow.com/a/20574486/4935114,@Mikebuild议创build一个;pre-commit
钩子,它将在可能要忽略的行的staged文件中grep
。 钩子检查这些线是否已经上演。 如果是这样,它会echo
一个警告,并exit
与代码1
所以提交过程将不会继续。
受@ Mike的回答的启发,我发现自己也许使用了一个改进版本的hook,它会自动 reset
s(用-p
标记) reset
为我们想要忽略的特定行。
我不确定这个钩子是否适用于这样的情况,即有许多文件的这一行被忽略,但是这个pre-commit
钩子在特定的文件buildVars.java
这一行中的一个改变。 当我在我的机器上testing它时,钩子脚本看起来像这样。
#!/bin/sh # this hook looks for lines with the text `var isPhoneGap = false;` in the file `buildVars.java` and it resets these lines to the previous state before staged with `reset -p` if [[ $(git diff --no-ext-diff --cached buildVars.java | grep --count -e "var\ isPhoneGap[\ ]*=[\ ]*") -ne 0 ]]; then cat <<EOW WARNING: You are attempting to commit changes which are not supposed to be commited according to this \`pre-commit\` hook This \`pre-commit\` hook will reset all the files containing this line to it's previous state in the last commit. EOW echo /$'\n'isPhoneGap$'\n'y$'\n'q | git reset -p # BONUS: Check if after reseting, there is no actual changes to be commited and if so, exit 1 so the commit process will abort. if [[ $(git diff --no-ext-diff --cached | wc -l) -eq 0 ]]; then echo there are no actual changes to be commited and besides the change to the variable \'isPhoneGap\' so I won\'t commit. exit 1 fi fi
说明
我所做的是回应一个控制序列,在交互式reset
过程中search正则expression式是isPhoneGap
。 因此,模仿按下/
search的用户是isPhoneGap
,当询问是否要放弃该补丁并按q
退出交互式reset
时,按y
。
交互式反转补丁程序logging在这里: https : //git-scm.com/docs/git-add#git-add-patch
注:上面的脚本假定variablesinteractive.singleKey
为false
。 如果您将您的configuration设置为true
,请在警告之后立即从echo
命令中删除任何$'\n'
。
我猜这可能是你的来源不止一行的东西。
我认为有一个.userbuildconfig文件是最简洁的,你只需要包含一个.userbuildconfig文件,并且默认选中。然后你可以使用Carlos的build议来将这个文件单独标记为假定不变。 通过这种方式,您不必错过需要检查设置的其他文件更改。
这可以让你调整本地预处理macros(或者对于像这样的https://stackoverflow.com/a/1813873/1270965 )。
不。 由于.gitignore中的行匹配文件名而不是文件内容,因此只能忽略单个文件(以及更多)。 您已经提到了解决scheme,即忽略包含您要忽略的内容的单个文件。