git 获取远程分支,但在本地存储库或工作副本中看不到

git fetch remote branch, but cannot see in local repository or working copy

我当前的分支是staging_kei20201211,我想从origin/staging分支获取最新的代码,我输入以下命令

git fetch origin staging

它说

1) 然后我去 visual studio 查看我的分支 staging_kei20201211 的历史记录,但是我看不到 fetch 输出中所述的提交 c03c99691,为什么?

  1. 获取输出屏幕的含义是什么? 来自 http:///XXXXXX/gitea/elm-ha/CFMS

请注意,获取只会更新本地 tracking 分支。在这种情况下,您的提取更新了以下分支:

origin/staging_kei20201211

要更新实际的本地分支 staging_kei20201211,您需要执行以下附加步骤:

# from staging_kei20201211
git merge origin/staging_kei20201211

但更典型的是,您会检查当地的分支机构并执行 git pull:

git checkout staging_kei20201211
git pull origin staging_kei20201211

让我们先从问题 2 开始,因为它对查看问题 1 很有用:

what is the meaning of the fetch output screen?

From http://XXXXXX/gitea/elm-ha/CFMS
 * branch                staging  -> FETCH_HEAD
   c97e1dbb7..c03c99691  staging  -> origin/staging

实际上还有更多的输出,其中大部分都以单词 remote: 为前缀。 remote: 前缀的文本是服务器本身 运行 命令的输出。这导致服务器发现 59 个内部 Git 对象,他们的 Git 想要发送给您的 Git,以便您的 Git 获得他们拥有的一切,而您没有但在这个时候要求。然后他们“打包”这些对象,实际上进一步压缩到大约 2 KiB 以发送,然后发送;您的 Git 然后解压缩此数据,并将内部对象放入您的存储库。

此时,您拥有所有新的提交,但是您无法在您的存储库中找到新的提交。新提交是 From http://...,所以这是 From 部分。这些提交是在 other Git 存储库中找到的,通过使用名称 staging in that other Git 存储库。因此,您的 Git 将您给 git fetch 的 b运行ch 名称写入了一个名为 FETCH_HEAD 的内部文件,即 staging,对应于提交 c03c99691,它现在存在于您的存储库中(但是,到目前为止,仍然 没有 name 可以让您找到它)。

last 行告诉您 Git 在您的存储库中做了什么使您可以 find 提交c03c99691。您自己的 Git 更新了 您的 姓名 origin/staging。您的 origin/staging 用于查找提交 c97e1dbb7。现在它找到提交 c03c99691。那就是:

 c97e1dbb7..c03c99691  staging -> origin/staging

意味着:他们的 staging 变成了你的 origin/staging 而你的 origin/staging 曾经持有 c97e1dbb7,但现在持有 c03c99691,与他们的 staging.

相同

这里的最终结果是您的 origin/staging,这是一个 远程跟踪名称 而不是 b运行ch 名称,拥有与他们的 b运行ch 名称 staging 相同的 提交哈希 ID。因此,您可以使用名称 origin/staging 来查找提交。您还可以使用原始哈希 ID:c03c99691.

Git 真的是关于提交

在 Git 中,重要的是 提交 。每个提交都有一个唯一的编号。您刚刚从他们那里获得的提交 end 具有唯一编号为 c03c99691 的提交。 (这实际上是一个缩短的形式:完整的哈希 ID 更大更丑。Git 有时会缩短它们,只保留前几个字符,以帮助避免让人类不知所措。)这个数字在每个Git存储库中都是一样的。你的存储库使用这个数字,他们的也是。

每个提交本身由两部分组成:

  • 提交包含每个文件的完整快照。提交中的文件以特殊的、压缩的、只读的、Git-only 和去重格式存储。这样一来,当您进行新提交时,您主要是在重新使用 先前 提交中的文件,新提交并不需要太多 space .只有 changed 文件需要新的内部对象。对于所有未更改的文件,它们的内容与其他提交中的文件相同,因此它们可以共享去重部分。

  • 同时,每个提交还包含一些关于关于提交本身的信息,例如提交人、时间和原因。在提交中的此信息中,每个提交都包含用于进行 this 提交的任何 earlier 提交的原始哈希 ID 列表。通常只有一个这样的哈希 ID,我们称之为提交的 parent

这个 父哈希 ID 技巧使 Git 起作用。假设我们有一系列的提交,都在一个很好的简单行中,没有 b运行ching 和合并正在进行。此序列中的 last 提交有一些丑陋的哈希 ID,但我们将其称为提交 H。提交 H 在其内部有其 parent 提交的丑陋的大哈希 ID;我们将调用该提交 G.

我们说子提交指向父,我们可以得出:

        <-G <-H

您可以看到如何从 H 出来一个箭头,向后指向 G。当然,G 也有一个箭头。它向后指向 G 之前的提交,我们称之为 F:

... <-F <-G <-H

和以前一样,F也指向后面。这个向后看的链让我们——或者 Git——从 last 提交开始并找到历史。 存储库中的历史不多于或少于存储库中的提交。仅此而已,但也仅此而已。每个提交都向后指向较早的提交。

B运行ch名称和其他名称发生变化;哈希 ID 保持不变

这就是 b运行ch 名字进入我们画面的地方。为了找到所有提交,我们需要last提交的哈希ID。上面是提交 H。所以我们把last提交的hash ID放到一个名字里,比如一个b运行ch名字。如果b运行ch名称master包含提交G的哈希ID,b运行ch名称staging_kei20201211包含提交[=的哈希ID 51=],我们可以这样画:

...--F--G   <-- master
         \
          H   <-- staging_kei20201211

在这里,提交 H 指向更早的提交 G。名称 master 也指向提交 G。这意味着通过 G 的提交都在 both b运行ches,而提交 H 仅在 staging_kei20201211.

(在 你的 存储库中是否是这种情况,我不知道。请注意,我们还使用了符号名称,GH, 对于提交;它们的真实名称是又大又丑的哈希 ID。要查找哈希 ID,请使用 git rev-parse:

git rev-parse master
例如,

会告诉您 master 指向的提交的真实哈希 ID。)

考虑到这一点,让我们看看将 new 提交添加到某些 b运行ch 时会发生什么。让我们从 git switch mastergit checkout master 开始,这样 current b运行ch namemaster当前提交 是提交G:

...--F--G   <-- master (HEAD)
         \
          H   <-- staging_kei20201211

这张图和上一张的区别是我们在名字master后面加上了特殊的名字HEAD,告诉我们哪个b运行ch名字是当前的b运行ch。 (git branch 命令现在将此名称打印为绿色,而不是白色,正如您在 staging_kei20201211 中看到的那样。)

我们现在可以创建一个也指向 G 的新名称,然后切换到它,使用:

git switch -C temp-branch

得到:

...--F--G   <-- master, temp-branch (HEAD)
         \
          H   <-- staging_kei20201211

如果我们现在以通常的方式进行 new 提交(修改文件、git addgit commit),我们将得到一个新的commit,使用一个新的、唯一的哈希 ID。这个又大又丑的哈希 ID 不在 任何其他 Git 任何地方的存储库 中(这就是为什么它们必须像现在一样又大又丑),但是我们将其称为提交 I,并像这样绘制它:

          I   <-- temp-branch (HEAD)
         /
...--F--G   <-- master
         \
          H   <-- staging_kei20201211

注意 name temp-branch 是如何变化的:它现在指向 new commit。旧的提交仍然存在,通过 G 的提交现在在所有三个 b运行 上。 name 已移动,但提交保留在原地。我们刚刚添加了一个 new 提交,现在是 b运行ch temp-branch.[=130 上的 last 提交=]

如果我们检查其他一些 b运行ch 名称,例如 staging_kei20201211,并且 删除 名称 temp-branch,我们得到:

          I   ???
         /
...--F--G   <-- master
         \
          H   <-- staging_kei20201211 (HEAD)

提交I 仍然存在,但如果你没有在任何地方保存它的提交哈希ID,将很难找到。 Git 将保留提交一段时间,以防您想要它回来,但您必须找到它的哈希 ID。如果你不以某种方式取回它,Git 最终将完全丢弃提交 I。 (如果我们想这样做,这就是我们做出然后放弃临时提交的方式。)

Git 的 fetchpush 处理 哈希 ID 到 t运行sfer 提交

虽然我们通过名称查找 提交,但实际提交本身由哈希 ID 标识。要查看我们是否已经有一些提交,当我们将两个 Git 相互挂钩时,它们只是交换原始哈希 ID。由于这些在 every Git 中是唯一的,因此一个 Git 可以通过它是否具有具有相同哈希 ID 的提交来判断另一个是否具有相同的提交。如果没有,发送 Git 就发送过来。所有 Git 的号码都以相同的方式提交,1 因此接收方 Git 将使用相同的 运行dom-looking 号码。


1为了完成这项工作,Git 使用了加密强度高的散列函数。 “加密强度”部分对 Git 本身不是必需的,但可用于其他目的。当前的算法 SHA-1 不再足够强大,Git 正在转向新的哈希算法,但这是一个长期的转变,可以预见到许多问题;随着 Git 开始进行转换,无法预料的问题将会出现。


获得后,receivingGit需要有一个name

在你的例子中,你 运行 git fetch 联系了一个 Git,他的联系人 URL 被记住在姓名 origin 下。您的 Git 调用了服务器 URL。该服务器调用了一个 Git 连接到一个存储库,其中有一个 b运行ch 名称 staging,其中包含哈希 ID c03c99691。为简单起见,我将此提交称为 K.

您的 Git 之前曾与另一个 Git 交谈过。事实上,给定名称 origin,你的 Git 可能 started 通过 copying all the commits that other Git 存储库已*进入您自己的新 Git 存储库。所以这个提交从那时起就被添加到 origin 中。他们移动了他们的名字运行频道staging。他们可能有:

...--G   <-- master
      \
       J   <-- staging

当你做你原来的 git clone 时,你在 你的 存储库中有,说:

       H   <-- staging_kei20201211 (HEAD)
      /
...--G   <-- origin/master
      \
       J   <-- staging, origin/staging

(或者可能是具有不同结构的不同图形,但是从你的 git branch 名称和你的 git fetch 输出,我怀疑你有一个 origin/master,我知道你有一个 origin/staging)。您的 origin/* 名称来自您的 Git 复制 他们的 Git 存储库的 b运行ch名字。

无论如何,他们现在有一些新的提交。我猜他们正好有一个新的提交,而你的 git fetch 带来了那个:

       H   <-- staging_kei20201211 (HEAD)
      /
...--G   <-- origin/master
      \
       J   <-- staging
        \
         K   <-- origin/staging

如果这张图是准确的,J 就是 c97e1dbb7K 就是 c03c99691

现在回答问题1

I go to visual studio to see the history of my branch staging_kei20201211, but I cannot see the commit c03c99691 as stated in the fetch output, why?

我不知道或使用 Visual Studio,但一般来说,要让任何 Git 查看器向您显示一些提交,您必须告诉他们要么最后一次这样的提交,或者给他们一个允许他们使用 Git 找到最后一次这样的提交的名称。

如您所知,根据定义,名称 origin/staging 将找到链中以该提交结尾的最后一个提交。那是因为你的 Git 更新了你的 origin/staging 以匹配另一个 Git 正在查看的 Git 存储库中的名称 staging

来自 bash 风格的命令行:

$ git log origin/staging

会向您显示一些提交,从 c03c99691 开始,由 origin/staging 找到。命令:

$ git show origin/staging

会找到提交 c03c99691,找到它的父级 — 可能是 c97e...,但如果您刚刚从 origin 获得两个或更多提交,也许还有其他提交 — 和 比较两次提交中的快照。对于完全相同的每个文件,git show 将不显示任何内容。对于每个不同的文件,git show 会告诉您发生了什么变化。所有这些都将以提交 c03c99691 中的 日志消息 为前缀,加上存储在提交 [=34= 中的姓名和电子邮件地址以及日期和时间戳信息].