繁体   English   中英

Git:如何取消跟踪文件而不将它们暂存以进行删除

[英]Git: how to untrack files without staging them for deletion

我有一些我想在本地更改的配置文件,但不会冒意外提交这些更改的风险。 它们也不能添加到 gitignore 中,因为它们需要在整个项目中进行跟踪。 当我修改这些文件以满足我的环境需要时,我的git status如下所示:

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:   config1.cfg
        modified:   config2.cfg

Untracked files:
    (use "git add <file>..." to include in what will be committed)

        whatever.html
        somethingElse.js

然后我运行:

git rm --cached config1.cfg config2.cfg

git status看起来像这样:

Changes to be committed:
  (use "git reset HEAD <file>..." to unstage)

        deleted:    config1.cfg
        deleted:    config2.cfg

Untracked files:
  (use "git add <file>..." to include in what will be committed)

    config1.cfg
    config2.cfg
    whatever.html
    somethingElse.js
    

运行git reset --HEAD config1.cfg config2.cfg可预见地将它们返回到暂存区。 但是,即使该暂存是为了删除,某些内容可以未被跟踪并仍然同时上演,这有点没有意义。 但也 - 我没有删除文件,但如果我现在提交,那么它们将被删除。

我意识到这可能是污迹和清洁过滤器的更好用例,但是是否有可能达到以前跟踪的文件未被跟踪并且就好像它从未被跟踪过的状态? 如果没有,是否有充分的理由不可能?

编辑以澄清现在我对情况的理解更好一点:我尝试创建的场景是在我工作时在本地未跟踪文件的场景,而不影响它们在遥控器上的跟踪状态。

但如果我现在提交,那么它们将被删除。

不会。文件(您在工作树中看到的内容)不会被删除。 提交对工作树没有影响

提交会将它们记录为已删除,这是必须的,因为它们存在于上一次提交中,现在您说它们不应该出现在下一次提交中。 这就是删除:曾经存在的东西现在不再存在。

Git 的三个地方

听起来您可能会从了解 Git“是什么”中受益。 Git 练习影响了三个地方:

  • 工作树 这就是 Git 向您展示的内容。 它是将一个充满文件的文件夹渲染到磁盘上,以便您可以编辑这些文件。

  • 指数 也称为暂存区或缓存。 这是一个不可见的文件引用集合,用于构建您的下一次提交将包含的内容。

  • 实际的存储库 一个不可见的提交集合。 提交本身每个都包含文件,从某种意义上说,“包含”这个词的细节在这里并不重要。

当您检出一个分支时,您正在检出一个提交。 提交用于填充工作树和索引; 他们都在那一刻匹配。

如果您更改工作树中的一个文件(这是您可以更改任何内容的唯一位置)并添加它并提交,那么只有那个文件更改了,是的,但所有其他文件仍然存在于工作树中,并且index,所以这次提交包含所有文件——而不仅仅是你更改的文件(这是一个常见的误解)。 每次提交都是索引创建时整个状态的快照,这反过来又反映了工作树的整个状态,由您选择添加到索引的内容介导。

因此,索引是您可以操纵您在工作树中所做的事情与将进入下一次提交的内容之间的关系的地方。 当你说git add . ,您实际上是在说“索引应该反映我在工作树中所做的一切”。 但这是一个非常广泛的命令; 您对索引在下一次提交的准备阶段应该是什么样子有绝对的逐个文件精细控制。

你做了什么

当你说git rm --cached config1.cfg ,你说,“从索引中删除对config1.cfg引用。” 当您提交时,这不会对工作树产生影响; 它只会进行一次提交,其中config1.cfg恰好不存在。

但是现在您正在考虑这一点,并且您意识到这不是您的意思,因为下一次提交将构成对config1.cfg删除 你不喜欢那样。 确实希望下一次提交仍包含config1.cfg 你只是不希望它从以前的提交中改变

我认为,这就是您说的意思:

我有一些我想在本地更改的配置文件,但不会冒意外提交这些更改的风险

你应该做的

您的目标不是进行不存在config1.cfg的提交。 您的目标是进行提交,其中config1.cfg与其之前的状态没有变化,即使您实际上已经在工作树中对其进行了编辑。

好的,那么你应该怎么做才能做到这一点? 嗯,第一道防线是:不要说git add . 或一些像这样的笼统声明。 相反,为了将更改的文件添加到索引中,请不要添加它们 只需添加到索引修改过的文件,想在反映下一个承诺。

但是,假设您不顾一切地突破了该保护措施,并且确实将处于更改状态的config1.cfg添加到索引中。 (你做到了。)然后说git restore --staged config1.cfg 会将 config1.cfg从上次提交(每个提交都包含所有文件,还记得吗?)复制到索引中。 所以现在索引中的config1.cfg看起来像以前的提交,而不像工作树版本。 状态将是 git 知道您已经修改了工作树中的config1.cfg (除非您已将其添加到 gitignores 文件中),但该更改不会包含在您进行的下一次提交中。

(在 Git 2.25.0 版本之前,你会使用一种git reset形式来实现这个目标,即git reset config1.cfg 。但是git reset很可怕,所以如果你有一个足够新的 Git,请改用restore 。)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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