Git在rm--缓存并在分支之间移动之后删除工作树中的一些文件
当我执行这些步骤时,工作树中的文件将被删除,但不应发生这种情况: 来自新的本地回购协议Git在rm--缓存并在分支之间移动之后删除工作树中的一些文件,git,commit,gitignore,checkout,rm,Git,Commit,Gitignore,Checkout,Rm,当我执行这些步骤时,工作树中的文件将被删除,但不应发生这种情况: 来自新的本地回购协议 git init 我创建了一些文件 touch file1.txt | touch file2.txt 我想忽略文件1 echo file1.txt > .gitignore 我策划并承诺 git add . git commit -m "Initial commit" git add . git commit -m "file2 in gitignore" 我创建一个新分支(不带签出) 我错
git init
我创建了一些文件
touch file1.txt | touch file2.txt
我想忽略文件1
echo file1.txt > .gitignore
我策划并承诺
git add .
git commit -m "Initial commit"
git add .
git commit -m "file2 in gitignore"
我创建一个新分支(不带签出)
我错了,我也想忽略文件2!所以我取消了文件2
git rm --cached file2.txt
我把文件2放在gitignore中
echo file2.txt >> .gitignore
我策划并承诺
git add .
git commit -m "Initial commit"
git add .
git commit -m "file2 in gitignore"
我转到开发分支(不做其他事情)
我回到大师身边(别无选择)
file2.txt已在我的工作树中删除
我做错了什么??:(
file2.txt是否已被删除,因为我从.gitignore不同的分支签出?看起来很奇怪,对吗
git rm
可用于两种不同的级别
- 从工作目录中删除文件
- 从git暂存索引中删除文件
rm--cached
将仅在暂存索引中将文件标记为已删除。它将保持文件在工作目录中的原样
然后通过命令git checkout
根据官方文件。
上面说
更新工作树中的文件以匹配索引中的版本
这意味着它将使用staging index
的内容更新工作目录
。由于您已使用命令git rm--cached
从staging index中删除了文件,那么工作目录将被命令git checkout master
替换为staging index
内容> 看起来很奇怪,对吧
git rm
可用于两种不同的级别
- 从工作目录中删除文件
- 从git暂存索引中删除文件
rm--cached
将仅在暂存索引中将文件标记为已删除。它将保持文件在工作目录中的原样
然后通过命令git checkout
根据官方文件。
上面说
更新工作树中的文件以匹配索引中的版本
这意味着它将使用
staging index
的内容更新工作目录
。由于您已使用命令git rm--cached
从staging index中删除了文件,那么工作目录将被命令git checkout master
替换为staging index
内容> 由于忽略了file2.txt
,我假设您的预期行为是git在切换分支时不会删除它
但是在您要离开的分支上,file2.txt
并没有被忽略;事实上,它不能被忽略,因为它已被索引。从那里移动到master
,其中一个变化是删除file2.txt
这是一个边缘案例,“正确”的行为是有争议的。有时一个人可能期望(或至少想要)一件事,有时一个人可能期望另一件事
但您所观察到的是git的记录行为
请注意,如果您还从dev
git checkout dev
git rm --cached file2.txt
git echo file2.txt >> .gitignore
git add .
git commit
然后在分支之间切换会使file2.txt
保持不变。如果提交file2.txt
首先是一个错误,那么从所有分支中删除它至少是有意义的
该建议的问题在于,根据每个分支上发生的其他情况,它可能会导致合并冲突。解决这些冲突相当简单,但仍然可能会变得烦人。出于这个原因(或其他原因)实际上,您可能需要考虑进行历史编辑,尤其是如果这些提交尚未被其他开发人员推/共享。
请注意如果执行此操作,您希望确保恢复了file2.txt
的工作树副本(如果不恢复,以后仍有可能(暂时)恢复它们,但不那么容易。)因此,一旦安全恢复了这些文件
git filter-branch --index-filter 'git rm --cached --ignore-unmatch :/:file2.txt' -- --all
由于忽略了
file2.txt
,我假设您的预期行为是git在切换分支时不会删除它
但是在您要离开的分支上,file2.txt
并没有被忽略;事实上,它不能被忽略,因为它已被索引。从那里移动到master
,其中一个变化是删除file2.txt
这是一个边缘案例,“正确”的行为是有争议的。有时一个人可能期望(或至少想要)一件事,有时一个人可能期望另一件事
但您所观察到的是git的记录行为
请注意,如果您还从dev
git checkout dev
git rm --cached file2.txt
git echo file2.txt >> .gitignore
git add .
git commit
然后在分支之间切换会使file2.txt
保持不变。如果提交file2.txt
首先是一个错误,那么从所有分支中删除它至少是有意义的
该建议的问题在于,根据每个分支上发生的其他情况,它可能会导致合并冲突。解决这些冲突相当简单,但仍然可能会变得烦人。出于这个原因(或其他原因)实际上,您可能需要考虑进行历史编辑,尤其是如果这些提交尚未被其他开发人员推/共享。
请注意如果执行此操作,您希望确保恢复了file2.txt
的工作树副本(如果不恢复,以后仍有可能(暂时)恢复它们,但不那么容易。)因此,一旦安全恢复了这些文件
git filter-branch --index-filter 'git rm --cached --ignore-unmatch :/:file2.txt' -- --all
你是从哪里想到将
.gitignore
应用于已跟踪的文件的?我知道.gitignore对已跟踪的文件不起作用。这就是为什么我试图在将其添加到.gitignore之前将其从索引中删除的原因。我遗漏了什么吗?啊,我明白了,我们都遗漏了。签出删除了以前签出的一部分文件