【问题标题】:Why does "git status" show I'm on the master branch and "git branch" does not in a newly created repository?为什么“git status”显示我在主分支上,而“git 分支”不在新创建的存储库中?
【发布时间】:2019-07-16 06:15:06
【问题描述】:

我正在尝试自动化流程并发出git branch 命令以找出我所在的分支。除了git branch 什么都不返回的新初始化的回购之外,一切都运行良好。鉴于我没有对 repo 做任何事情,甚至没有对初始提交做任何事情,我可以接受答案。但是,如果我运行 git status,它会告诉我我在 master 分支上,如下所示:

$ mkdir todelete
$ cd todelete
$ git init
Initialized empty Git repository in /u/u70021a/todelete/.git
$ git status
On branch master

No commits yet

nothing to commit (create/copy files and use "git add" to track)
$ git branch
$

我做错了吗?是不是有些设置我没设置好?

我也有许多 Git 新人,我无法向他们解释为什么显示他们所在分支的命令什么也没显示,而 status 命令却显示。

【问题讨论】:

    标签: git


    【解决方案1】:

    我赞成另外两个答案,但我认为思考这个问题的方法很简单:你可以在一个不存在的分支上。这是正常一个新的空存储库,因为要存在一个分支名称,该分支名称​​必须标识一个现有的有效提交的哈希 ID。一个新的空存储库没有提交,因此还不允许存在分支名称。

    尽管如此,您最初是在 some 分支上。您所在的分支是其名称存储在特殊名称HEAD 中的分支。在一个新的空存储库中,Git 将名称 master(更准确地说,refs/heads/master——分支的全名)存储在 HEAD 中,因此您在 master 上,而 master 不存在。

    您可以使用git checkout -b 更改您所在的不存在的分支:

    $ git init
    Initialized empty Git repository in [path]
    $ git checkout -b asdf
    Switched to a new branch 'asdf'
    $ git checkout -b hello
    Switched to a new branch 'hello'
    

    只要你在一个不存在的分支上,你下一次提交创建这个分支。这也是git checkout --orphan 的工作原理。

    【讨论】:

    • 谢谢。虽然我不同意 git 显示的内容。至少我明白为什么。您的结帐示例很有趣。根据“git checkout”的文档, -b 的意思是:创建一个名为 的新分支,这并不完全正确。在您的示例中,实际上都没有创建分支 asdf 或 hello 。但如果执行提交,它们将是。我个人的意见是“On branch master”消息应该更改为“Next Commit to branch master”,因为在执行提交之前,主分支不存在。
    • 我不确定这是否与您的情况有关,但我想指出的是,对于 Git,它可能根本不在任何分支上。
    • Git 内部使用cat .git/HEAD 来查看它在哪个分支上,找出分支存在会消耗更多的 CPU 和磁盘时间,所以这可能是他们没有这样做的原因
    • 应该提到的是,您根本不应该在自动化过程中使用git branch,因为它不是为该用例设计的。看看这里显示的非瓷命令会很有趣,git symbolic-ref --short HEAD 是否有相同的行为?
    • @Voo: git symbolic-ref 显示包含在 HEAD 中的名称(因此是孤立/未出生的分支引用),前提是 HEAD 未分离。在新的空存储库中,HEAD 无法 被分离,因为分离的 HEAD 必须包含现有有效提交的哈希 ID。 (在非空存储库中,带有分离的 HEAD,git symbolic-ref 会产生错误。)
    【解决方案2】:

    git branch 什么都不显示,因为没有分支。但是,正如您在man git init 中看到的那样:

    此命令创建一个空的 Git 存储库 - 基本上是一个 .git 目录,其中包含对象的子目录, refs/heads、refs/tags 和模板文件。 一个初始的 HEAD 文件,它引用了 master 的 HEAD 分支也被创建。

    我将我认为相关的部分加粗 - 看起来虽然还没有 master 分支,但对它的引用已经存在,这就是它显示在 git status 中的原因。提交时将创建一个适当的分支。

    【讨论】:

    • 所以看起来“git status”只是显示在 .git/HEAD 中看到的“分支名称”(参考:refs/heads/master)但没有通过查看 .git/refs/heads 来检查它是否确实存在。
    • 我无法确定,因为我没有检查 git 的代码,但你写的对我来说很有意义。但我仍然更喜欢 torek 的回答而不是我的 :)。
    【解决方案3】:

    现有的答案解决了为什么输出是这样的字面问题,但我认为他们掩盖了真正的问题......

    您说您正在自动化某些东西,所以我建议git statusgit branch 都不是脚本环境中的最佳工具。

    可以在此讨论中找到一些替代方案:How to programmatically determine the current checked out Git branch

    在不知道您的需求(或您希望未出生的分支如何表现)的情况下,我不一定会提出建议,但我要说的是,有些命令是用于人机交互的(瓷器),而另一些是用于脚本(管道)

    【讨论】:

      【解决方案4】:

      分支尚未诞生。因此git branch 没有显示它(git symbolic-ref HEAD 表示你的 HEAD 指向默认的分支 master 并且它是未出生的,因为git branch 没有显示它,即你可以在一个没有还存在)。但是,提交某些内容会创建分支。

      如果您签出 orphan 分支,情况也是如此。

      我想git status 显示了分支名称,因为这是将要创建的分支。

      脚本见How to programmatically determine the current checked out Git branch

      【讨论】:

        【解决方案5】:

        在 git 中,默认分支是 master。 当您提交时,git 将“使用”您现在所在的当前分支。 由于您已经初始化了一个新存储库,因此您位于“默认”分支上,这就是您在分支列表中看不到它的原因,一旦您提交更改,它就会显示出来。

        【讨论】:

        • 我理解分支,我不明白为什么“git status”说我在一个不存在的分支上。
        猜你喜欢
        • 1970-01-01
        • 2015-02-22
        • 1970-01-01
        • 2015-04-06
        • 1970-01-01
        • 1970-01-01
        • 2012-03-20
        • 2014-09-19
        • 1970-01-01
        相关资源
        最近更新 更多