“git pull”和“git fetch”有什么区别?

git version-control git-pull git-fetch

想要改进这篇文章?提供这个问题的详细答案,包括引文和解释为什么你的答案是正确的。没有足够细节的答案可能会被编辑或删除。

git pullgit fetch 有什么区别?

我发现这篇写得很好的关于 git fetch 和 git pull 的文章值得一读:longair.net/blog/2009/04/16/git-fetch-and-merge

我们的替代方法已成为 git fetch; git reset --hard origin/master 我们工作流程的一部分。它消除了本地更改,让您与 master 保持同步,但确保您不只是在当前更改的基础上引入新的更改并弄得一团糟。我们已经使用了一段时间,在实践中基本上感觉更安全。请务必先添加/提交/存储任何正在进行的工作!

确保您知道如何正确使用 git stash。如果您要询问“拉”和“取”,那么“藏匿”可能也需要解释......

许多来自 Mercurial 的人一直使用“git pull”,认为它相当于“hg pull”。它不是。 Git 相当于“hg pull”的是“git fetch”。

git pull 从远程分支中拉取并合并它。 git fetch 仅从远程分支获取,但不合并

M
Mateen Ulhaq

用最简单的术语来说,git pull 执行 git fetch 后跟 git merge

git fetch 更新 refs/remotes/<remote>/ 下的远程跟踪分支。此操作可随时安全运行,因为它不会更改您在 refs/heads 下的任何本地分支。

git pull 使用其远程版本更新本地分支,同时更新您的其他远程跟踪分支。

来自 git pull 的 Git 文档:

在其默认模式下,git pull 是 git fetch 后跟 git merge FETCH_HEAD 的简写。

““git pull”是您将存储库更新到最新的方法”<- 存储库更新不是已经通过 fetch 完成了吗?您不是说它使您的本地分支机构与远程分支机构保持同步吗?到合并:它将远程分支与这些分支的本地副本合并,或者它在这里合并了什么?

@Albert:是的,它的措辞很奇怪。 git pull 将始终合并到当前分支。因此,您选择要从 拉取的分支,并将其拉入当前分支。 from 分支可以是本地的或远程的;它甚至可以是一个未注册的远程分支 git remote(意味着您在 git pull 命令行上传递一个 URL)。

@espertus:不。推送永远不会自动进行合并。用户应该在本地拉取,解决任何合并冲突,然后推回远程。

如果我在 /home/alice/ 并执行 git fetch /home/bob,我应该将哪些参数传递给后续的 git merge

学习 Git 的人请注意:pull 实际上不能用 fetchmerge 来模拟。我刚刚获取了一个只有远程分支指针更改的更改,并且 merge 拒绝执行任何操作。另一方面,pull 快进我的跟踪分支。

M
Mateen Ulhaq

git pull 尝试在获取提交后自动合并。它是上下文敏感的,因此所有拉取的提交都将合并到您当前活动的分支中。 git pull 会自动合并提交,而无需您先查看它们。如果你不仔细管理你的分支,你可能会遇到频繁的冲突。

git fetch 从目标分支收集当前分支中不存在的所有提交,并将它们存储在本地存储库中。但是,它不会将它们与您当前的分支合并。如果您需要使存储库保持最新状态,但正在处理可能会因更新文件而中断的事情,这将特别有用。要将提交集成到您当前的分支中,您必须在之后使用 git merge 。

同意,很棒的评论。这就是我讨厌 git pull 的原因。什么时候让修订工具为您进行代码编辑才有意义?这不是合并两个文件的作用吗?如果这两个编辑在文件中物理上是分开的,但逻辑上不一致怎么办?

我不确定我是否理解正确。如果我是对的,请告诉我:假设我有两个分支,master 和 test。 test 是我正在研究的一个分支。如果我执行 git fetch,它会使用目标分支更新 master。如果我执行 git pull,它会尝试使用目标分支更新测试。这是正确的吗?如果不是,我想我不明白“本地存储库”是什么意思——我认为这意味着我的本地主人。

@elexhobby 简而言之,git fetch 仅更新您的 .git/ 目录(AKA:本地存储库),而在 .git/ 之外没有任何内容(AKA:工作树)。它不会更改您的本地分支,也不会触及 master。它触及 remotes/origin/master(见 git branch -avv)。如果您有更多遥控器,请尝试 git remote update。这是一个命令中所有遥控器的 git fetch

@Tino 你的确实是最重要的一点。人们可能不知道“远程”分支实际上存储为 .git/refs/remotes/origin/ 中的一堆哈希。

因此,fetch 命令类似于“从远程提交到本地”。正确的?

I
Ian Ringrose

将 git 的设计理念与更传统的源代码控制工具(如 SVN)的理念进行对比非常重要。

Subversion 是使用客户端/服务器模型设计和构建的。有一个存储库是服务器,多个客户端可以从服务器获取代码,对其进行处理,然后将其提交回服务器。假设客户端在需要执行操作时始终可以联系服务器。

Git 旨在支持更分布式的模型,而不需要中央存储库(尽管您当然可以根据需要使用一个)。 git 也被设计成客户端和“服务器”不需要同时在线。 Git 的设计目的是让不可靠链接上的人们甚至可以通过电子邮件交换代码。可以完全断开连接并刻录 CD 以通过 git 交换代码。

为了支持这个模型,git 使用你的代码维护一个本地存储库,以及一个反映远程存储库状态的附加本地存储库。通过在本地保存远程存储库的副本,即使远程存储库无法访问,git 也可以找出所需的更改。稍后当您需要将更改发送给其他人时,git 可以将它们作为一组更改从已知的时间点传输到远程存储库。

git fetch 是说“使我的远程存储库的本地副本保持最新”的命令。

git pull 说“将远程存储库中的更改带到我保存自己代码的地方。”

通常,git pull 通过执行 git fetch 来更新远程存储库的本地副本,然后将更改合并到您自己的代码存储库和可能是你的工作副本。

需要记住的是,您的工作站上通常至少有三个项目副本。一个副本是您自己的存储库,其中包含您自己的提交历史记录。第二个副本是您正在编辑和构建的工作副本。第三个副本是远程存储库的本地“缓存”副本。

从技术上讲,本地和远程存储库实际上是一回事。在 Git 中,存储库是指向其父级的提交的 DAG。从技术上讲,分支只不过是有意义的提交名称。本地分支和远程分支的唯一区别是远程分支以 remoteName/ 为前缀,Git from the ground up 非常好读。一旦你了解了 Git 的工作原理——它真的很简单——一切都变得有意义了。

错误的。存储库不包含工作树的副本。存储库是更改列表。因此,除非您明确 cp -R 它,否则工作站上只有一个项目实例。

M
Mateen Ulhaq

这是Oliver Steele's image of how all it all fits together

https://i.stack.imgur.com/XwVzT.png

带有 git clonegit merge 的更新图像会很有帮助!

是的,请添加 git merge - 它应该清楚地表明单独调用的 merge 与调用 pull 不同,因为 pull 仅从远程合并并忽略您在跟踪远程的本地分支中的本地提交被拉出的分支。

一张图片胜过千言万语!带有克隆和合并数据流的更新图像是否在某处准备就绪?除了图中已有的数据流之外,还有其他数据流吗?

M
Mateen Ulhaq

git fetch 的一个用例是,以下内容将告诉您自上次拉取以来远程分支中的任何更改......因此您可以在进行实际拉取之前进行检查,这可能会更改当前分支和工作副本中的文件。

git fetch
git diff ...origin

请参阅有关双 .. 和三点 ... 语法的 git diff 文档。

s
stites

我花了一点时间来理解有什么区别,但这是一个简单的解释。 master 在您的本地主机中是一个分支。

克隆存储库时,您会将整个存储库获取到本地主机。这意味着当时您有一个指向 HEAD 的 origin/master 指针和指向同一个 HEAD 的 master。

当您开始工作并提交时,您将主指针前进到 HEAD + 您的提交。但是原点/主指针仍然指向克隆时的位置。

所以区别将是:

如果您执行 git fetch,它只会获取远程存储库 (GitHub) 中的所有更改并将源/主指针移动到 HEAD。同时,您的本地分支主管将继续指向它所在的位置。

如果您执行 git pull,它基本上会执行 fetch(如前所述)并将任何新更改合并到您的 master 分支并将指针移动到 HEAD。

origin/master 是一个本地分支,它是原点上 master 的副本。当您获取时,您会更新 local:/origin/master。一旦你真正理解 git 中的所有东西都是一个分支,这很有意义,并且是一种非常强大的方式来维护不同的变更集,快速创建本地分支,合并和变基,并且通常从廉价的分支中获得很多价值模型。

M
Manoj

有时,视觉表示会有所帮助。

https://i.stack.imgur.com/ZYAVG.jpg

我认为这张照片必须表明它也影响了本地回购。也就是说,Git pull 是影响本地 repo 和工作副本的组合。现在它似乎只影响工作副本。

S
Snowcrash

更简短的

git fetch 获取更新但不合并它们。

git pull 在引擎盖下执行 git fetch,然后执行 merge

简要地

git fetchpull 类似,但不合并。即它获取远程更新(refsobjects)但您的本地保持不变(即 origin/master 得到更新但 master 保持不变)。

git pull 从远程下拉并立即合并。

更多的

git clone 克隆一个存储库。

git rebase 将当前分支中不在上游分支中的内容保存到临时区域。您的分支现在与开始更改之前相同。因此,git pull -rebase 将拉下远程更改,倒回您的本地分支,在当前分支的顶部一一重播您的更改,直到您是最新的。

此外,git branch -a 将准确地向您展示所有分支(本地和远程)的情况。

这篇博文很有用:

The difference between git pull, git fetch and git clone (and git rebase) - Mike Pearce

并涵盖 git pullgit fetchgit clonegit rebase

更新

我想我会更新这个来展示你在实践中是如何使用它的。

从远程更新您的本地仓库(但不要合并): git fetch 下载更新后,让我们看看差异: git diff master origin/master 如果您对这些更新感到满意,则合并: git pull

笔记:

第 2 步:有关本地和远程之间差异的更多信息,请参阅:How to compare a local Git branch with its remote branch

在第 3 步:在此处执行 git rebase origin 可能更准确(例如,在快速更改的仓库中)。请参阅另一个答案中的 @Justin Ohms comment

另请参阅:http://longair.net/blog/2009/04/16/git-fetch-and-merge/

另请注意:我在 pull 中提到了 merge,但是您可以将 pull 配置为使用 rebase

下面是一个非常重要的更新下载更新后,让我们看看差异:'git diff master origin/master'

V
Vinko Vrsalovic
git-pull - Fetch from and merge with another repository or a local branch
SYNOPSIS

git pull   …
DESCRIPTION

Runs git-fetch with the given parameters, and calls git-merge to merge the 
retrieved head(s) into the current branch. With --rebase, calls git-rebase 
instead of git-merge.

Note that you can use . (current directory) as the <repository> to pull 
from the local repository — this is useful when merging local branches 
into the current branch.

Also note that options meant for git-pull itself and underlying git-merge 
must be given before the options meant for git-fetch.

如果你想合并历史,你会拉,如果你只是“想要 codez”,你会提取,因为有人在这里标记了一些文章。

N
Noor A Shuvo

好的,这里有一些关于git pullgit fetch的信息,所以你可以了解实际的区别......简单的几句话,fetch获取最新数据,但不是代码更改,也不会弄乱您当前的本地分支代码,但 pull 获取代码更改并将其合并到您的本地分支,继续阅读以获取有关每个分支的更多详细信息:

获取

它将所有引用和对象以及任何新分支下载到您的本地存储库...

从一个或多个其他存储库中获取分支和/或标签(统称为“引用”),以及完成其历史所需的对象。远程跟踪分支已更新(有关控制此行为的方法,请参见下面的描述)。默认情况下,任何指向正在获取的历史的标签也会被获取;效果是获取指向您感兴趣的分支的标签。可以通过使用 --tags 或 --no-tags 选项或配置 remote..tagOpt 来更改此默认行为。通过使用显式获取标签的 refspec,您也可以获取不指向您感兴趣的分支的标签。 git fetch 可以从单个命名存储库或 URL 或从多个存储库中获取,如果给定并且有一个遥控器。配置文件中的条目。 (参见 git-config1)。如果未指定远程,默认情况下将使用原始远程,除非为当前分支配置了上游分支。获取的 ref 的名称以及它们指向的对象名称被写入 .git/FETCH_HEAD。脚本或其他 git 命令(例如 git-pull)可能会使用此信息。

git 拉

它会将远程的更改应用到本地的当前分支...

将来自远程存储库的更改合并到当前分支中。在其默认模式下,git pull 是 git fetch 后跟 git merge FETCH_HEAD 的简写。更准确地说, git pull 使用给定的参数运行 git fetch 并调用 git merge 以将检索到的分支头合并到当前分支中。使用 --rebase,它运行 git rebase 而不是 git merge。应该是传递给 git-fetch1 的远程存储库的名称。可以命名任意远程引用(例如,标签的名称),甚至是具有相应远程跟踪分支的引用集合(例如,refs/heads/:refs/remotes/origin/),但通常是名称远程存储库中的一个分支。和 的默认值是从 git-branch --track 设置的当前分支的“远程”和“合并”配置中读取的。

我还创建了下面的视觉效果,向您展示 git fetchgit pull 如何协同工作...

https://i.stack.imgur.com/nWYnQ.png

O
Olli

您可以从远程存储库中获取,查看差异,然后提取或合并。

这是一个名为 origin 的远程存储库和一个名为 master 的分支跟踪远程分支 origin/master 的示例:

git checkout master                                                  
git fetch                                        
git diff origin/master
git rebase origin master

由于您已经获取了更改,因此您可能希望跳过拉取并仅执行“git rebase origin”作为最后一步。原因是有人可能会在您进行 fetch 之后的时间内推送更改,而这些不会在您进行差异审查的 fetch 中。

j
jfmercer

简短而简单的答案是 git pull 只是 git fetch 后跟 git merge

请务必注意,git pull自动合并,无论您喜欢与否。当然,这可能会导致合并冲突。假设您的遥控器是 origin,而您的分支是 master。如果您在拉取之前git diff origin/master,您应该对潜在的合并冲突有所了解,并可以相应地准备您的本地分支。

除了拉和推之外,some workflows 还涉及 git rebase,例如这个,我从链接的文章中转述:

git pull origin master
git checkout foo-branch
git rebase master
git push origin foo-branch

如果您发现自己处于这种情况,您可能会想git pull --rebase。除非你真的,真的知道你在做什么,否则我建议不要这样做。此警告来自 git-pull 版本 2.3.5man 页面:

这是一种潜在的危险操作模式。它改写了历史,当您已经发布了该历史时,这并不是一个好兆头。除非您仔细阅读 git-rebase(1),否则不要使用此选项。

t
th3sly

https://i.stack.imgur.com/aiQDJ.png

这种交互式图形表示对于理解 git 非常有帮助:http://ndpsoftware.com/git-cheatsheet.html

git fetch 只需将更改从远程“下载”到本地存储库。 git pull 下载更改并将它们合并到您当前的分支中。 “在其默认模式下,git pullgit fetch 后跟 git merge FETCH_HEAD 的简写。”

人们,单击链接以与不同的列进行交互。这个备忘单是我见过的最好的资源,可以完全理解每个命令之间的差异。

图像需要更新,因为重置操作错误地连接到远程仓库,而应该连接到本地仓库。这在链接的网站上是固定的。

C
Community

奖金:

在谈到上述答案中的 pull & fetch 时,我想分享一个有趣的技巧,

git pull --rebase

上面这个命令是我 git 生活中最有用的命令,它节省了很多时间。

在将您的新提交推送到服务器之前,请尝试此命令,它会自动同步最新的服务器更改(使用 fetch + 合并)并将您的提交放在 git log 的顶部。无需担心手动拉/合并。

在以下位置查找详细信息:http://gitolite.com/git-pull--rebase

J
Justus Romijn

我喜欢对情况有一些直观的表示来掌握这些东西。也许其他开发人员也想看到它,所以这是我的补充。我不完全确定这一切都是正确的,所以如果您发现任何错误,请发表评论。

                                         LOCAL SYSTEM
                  . =====================================================    
================= . =================  ===================  =============
REMOTE REPOSITORY . REMOTE REPOSITORY  LOCAL REPOSITORY     WORKING COPY
(ORIGIN)          . (CACHED)           
for example,      . mirror of the      
a github repo.    . remote repo
Can also be       .
multiple repo's   .
                  .
                  .
FETCH  *------------------>*
Your local cache of the remote is updated with the origin (or multiple
external sources, that is git's distributed nature)
                  .
PULL   *-------------------------------------------------------->*
changes are merged directly into your local copy. when conflicts occur, 
you are asked for decisions.
                  .
COMMIT            .                             *<---------------*
When coming from, for example, subversion, you might think that a commit
will update the origin. In git, a commit is only done to your local repo.
                  .
PUSH   *<---------------------------------------*
Synchronizes your changes back into the origin.

获取遥控器镜像的一些主要优点是:

性能(滚动浏览所有提交和消息,而不试图通过网络挤压它)

关于本地 repo 状态的反馈(例如,我使用 Atlassian 的 SourceTree,它会给我一个灯泡,指示与原点相比我是提前还是落后提交。可以使用 GIT FETCH 更新此信息)。

A
Anupama Karunarathna

GIT Fetch 和 GIT Pull 之间的区别可以用以下场景来解释:(请记住,图片胜于雄辩!,我提供了图片表示)

让我们举一个例子,您正在与您的团队成员一起处理一个项目。所以项目会有一个主分支,所有贡献者必须将它分叉到他们自己的本地存储库,然后在这个本地分支上修改/添加模块,然后推回主分支。

因此,当您在本地存储库上分叉主项目时,两个分支的初始状态将如下所示 - (ABC 是项目已完成的模块)

https://i.stack.imgur.com/SPky3.png

现在,您已经开始开发新模块(假设 D),当您完成 D 模块后,您希望将其推送到主分支,但同时发生的情况是您的一位队友开发了新模块EF 和修改的 C
现在发生的情况是,您的本地存储库落后于项目的原始进度,因此将您的更改推送到主分支可能会导致冲突和可能会导致您的模块 D 发生故障。

https://i.stack.imgur.com/SpIlX.png

为避免此类问题并与项目的原始进度并行工作,有两种方法:

1. Git Fetch - 这将下载对 origin/main 分支项目所做的所有更改,这些更改不存在于您的本地分支中。并将等待 Git Merge 命令将已获取的更改应用到您的存储库或分支。

https://i.stack.imgur.com/8qhgH.png

所以现在您可以在将文件合并到您的存储库之前仔细监控文件。由于修改了 C,您还可以根据需要修改 D

https://i.stack.imgur.com/JYA7S.png

2. Git Pull-这将使用原始/主分支更新您的本地分支,即实际上它所做的是Git Fetch 和Git 一个接一个合并的组合。但这可能会导致发生冲突,因此建议使用带有干净副本的 Git Pull。

https://i.stack.imgur.com/O1vk0.png

更清楚地说,如果同一文件被另一位同事更改并上传到远程仓库中,然后那些丢失的更改将使用“git pull”拉到本地仓库中,则“可能会发生冲突”。

J
JohnAllen

我也为此苦苦挣扎。事实上,我通过谷歌搜索完全相同的问题来到这里。阅读所有这些答案最终在我的脑海中描绘了一幅画面,我决定尝试通过查看 2 个存储库和 1 个沙箱的状态以及在查看它们的版本时随时间执行的操作来了解这一点。所以这就是我想出的。如果我在任何地方搞砸了,请纠正我。

三个带有 fetch 的 repos:

---------------------     -----------------------     -----------------------
- Remote Repo       -     - Remote Repo         -     - Remote Repo         -
-                   -     - gets pushed         -     -                     -
- @ R01             -     - @ R02               -     - @ R02               -
---------------------     -----------------------     -----------------------

---------------------     -----------------------     -----------------------
- Local Repo        -     - Local Repo          -     - Local Repo          -
- pull              -     -                     -     - fetch               -
- @ R01             -     - @ R01               -     - @ R02               -
---------------------     -----------------------     -----------------------

---------------------     -----------------------     -----------------------
- Local Sandbox     -     - Local Sandbox       -     - Local Sandbox       -
- Checkout          -     - new work done       -     -                     -
- @ R01             -     - @ R01+              -     - @R01+               -
---------------------     -----------------------     -----------------------

拉动的三个回购

---------------------     -----------------------     -----------------------
- Remote Repo       -     - Remote Repo         -     - Remote Repo         -
-                   -     - gets pushed         -     -                     -
- @ R01             -     - @ R02               -     - @ R02               -
---------------------     -----------------------     -----------------------

---------------------     -----------------------     -----------------------
- Local Repo        -     - Local Repo          -     - Local Repo          -
- pull              -     -                     -     - pull                -
- @ R01             -     - @ R01               -     - @ R02               -
---------------------     -----------------------     -----------------------

---------------------     -----------------------     -----------------------
- Local Sandbox     -     - Local Sandbox       -     - Local Sandbox       -
- Checkout          -     - new work done       -     - merged with R02     -
- @ R01             -     - @ R01+              -     - @R02+               -
---------------------     -----------------------     -----------------------

这帮助我理解了为什么 fetch 非常重要。

S
Selvamani

我们简单地说:

git pull == git fetch + git merge

如果您运行 git pull,则不需要将数据合并到本地。如果您运行 git fetch,则意味着您必须运行 git merge 才能将最新代码下载到本地计算机。否则,不合并就不会更改本地机器代码。

所以在 Git Gui 中,当你获取数据时,你必须合并数据。 Fetch 本身不会在您的本地进行代码更改。您可以通过获取一次获取并查看来检查更新代码时;它不会改变的代码。然后合并...您将看到更改后的代码。

t
tagurit

简单来说,如果您要在没有任何 Internet 连接的情况下跳上飞机……在起飞之前,您只需执行 git fetch origin <branch>。它会将所有更改提取到您的计算机中,但将其与您的本地开发/工作区分开。

在飞机上,您可以对本地工作区进行更改,然后将其与您之前获取的内容合并,然后解决潜在的合并冲突,所有这些都无需连接到 Internet。除非有人对远程存储库进行了 更改,否则一旦您到达目的地,您将执行 git push origin <branch> 并去喝咖啡。

从这个很棒的 Atlassian tutorial

git fetch 命令将提交、文件和引用从远程存储库下载到本地存储库。当您想查看其他人一直在做什么时,您会执行获取操作。它类似于 SVN 更新,因为它可以让您查看中央历史记录的进展情况,但它不会强制您将更改实际合并到您的存储库中。 Git 将获取的内容与现有的本地内容隔离开来,它对您的本地开发工作绝对没有影响。必须使用 git checkout 命令明确签出获取的内容。这使得在将提交与本地存储库集成之前,获取一种安全的方式来审查提交。从远程存储库下载内容时,可以使用 git pull 和 git fetch 命令来完成任务。您可以考虑 git fetch 这两个命令的“安全”版本。它将下载远程内容,但不会更新本地存储库的工作状态,从而使您当前的工作保持不变。 git pull 是更激进的选择,它将下载活动本地分支的远程内容并立即执行 git merge 为新的远程内容创建合并提交。如果您有正在进行的未决更改,这将导致冲突并启动合并冲突解决流程。

使用 git pull

你没有得到任何孤立。

它不需要显式检出。因为它隐式地做了一个 git 合并。

合并步骤会影响你本地的发展,可能会造成冲突

这基本上是不安全的。这是侵略性的。

与 git fetch 只影响你的 .git/refs/remotes 不同,git pull 会影响你的 .git/refs/remotes 和 .git/refs/heads/

嗯...所以如果我不使用 git fetch 更新工作副本,那么我在哪里进行更改? Git fetch 将新提交存储在哪里?

好问题。首先,headsremotes 不存储新提交。他们只需 pointers 即可提交。因此,您可以使用 git fetch 下载最新的 git objects(blob、树、提交。要完全理解对象请观看 this video on git internals),但只需更新您的 remotes 指针以指向该分支的最新提交。它仍然与您的工作副本隔离,因为您在 heads 目录中的分支指针尚未更新。它只会在 merge/pull 时更新。但又在哪里?让我们来了解一下。

在您的项目目录(即您执行 git 命令的位置)中,执行以下操作:

ls。这将显示文件和目录。没什么酷的,我知道。现在执行 ls -a。这将显示点文件,即以 . 开头的文件。然后,您将能够看到一个名为:.git 的目录。执行 cd .git。这显然会改变你的目录。有趣的来了;做 ls。您将看到目录列表。我们正在寻找裁判。做 cd 参考。查看所有目录中的内容很有趣,但让我们关注其中的两个。头和遥控器。也可以使用 cd 检查它们的内部。您执行的任何 git fetch 操作都会更新 /.git/refs/remotes 目录中的指针。它不会更新 /.git/refs/heads 目录中的任何内容。任何 git pull 都会首先执行 git fetch,更新 /.git/refs/remotes 目录中的项目,然后与本地合并,然后更改 /.git/refs/heads 目录中的头。

Where does 'git fetch' place itself? 中也可以找到一个非常好的相关答案。

另外,从 Git branch naming conventions 帖子中查找“斜线符号”。它可以帮助你更好地理解 Git 如何将东西放在不同的目录中。

查看实际差异

做就是了:

git fetch origin master
git checkout master

如果远程主机已更新,您将收到如下消息:

Your branch is behind 'origin/master' by 2 commits, and can be fast-forwarded.
  (use "git pull" to update your local branch)

如果您没有 fetch 而只是做了 git checkout master,那么您的本地 git 不会知道添加了 2 个提交。它只会说:

Already on 'master'
Your branch is up to date with 'origin/master'.

但这是过时和不正确的。这是因为 git 只会根据它所知道的信息给你反馈。它忘记了它尚未撤消的新提交......

在本地处理分支时,有什么方法可以查看远程所做的新更改?

一些 IDE(例如 Xcode)非常智能,并且使用 git fetch 的结果,并且可以注释在当前工作分支的远程分支中已更改的代码行。如果该行已被本地更改和远程分支更改,则该行将被标记为红色。这不是合并冲突。这是一个潜在的合并冲突。在从远程分支执行 git pull 之前,您可以使用它来解决未来的合并冲突。

https://i.stack.imgur.com/OEl72.png

有趣的提示:

如果您获取远程分支,例如:

git fetch origin feature/123

然后这将进入您的远程目录。您的本地目录仍然无法使用它。但是,它通过 DWIM 简化了您对该远程分支的结帐(按我的意思做):

git checkout feature/123

你不再需要做:

git checkout -b feature/123 origin/feature/123

有关该内容的更多信息,请阅读 here

M
Michael Durrant

git fetch 将代码从远程服务器下载到本地存储库中的跟踪分支。如果您的遥控器名为 origin(默认),那么这些分支将位于 origin/ 内,例如 origin/masterorigin/mybranch-123 等。这些不是您当前的分支,它们是本地 来自服务器的这些分支的副本。

git pull 执行 git fetch,然后将跟踪分支中的代码合并到该分支的当前本地版本中。如果您还没有准备好进行更改,请先git fetch

P
Peter Mortensen

git fetch 将检索远程分支,以便您可以使用当前分支git diffgit merge 它们。 git pull 将在当前分支跟踪的远程分支上运行 fetch,然后合并结果。您可以使用 git fetch 查看远程分支是否有任何更新,而无需将它们与本地分支合并。

P
Pinkesh Sharma

Git 获取

您通过 fetch 将更改从 origin 下载到本地分支。 Fetch 向远程存储库询问其他人已提交但您在本地存储库中没有的所有提交。 Fetch 下载这些提交并将它们添加到本地存储库。

Git 合并

您可以使用 merge 命令应用通过 fetch 下载的更改。 Merge 将获取从 fetch 中检索到的提交,并尝试将它们添加到您的本地分支。合并将保留您本地更改的提交历史,以便当您通过推送共享您的分支时,Git 将知道其他人如何合并您的更改。

Git 拉取

fetch 和 merge 经常一起运行,以至于创建了一个将两者结合在一起的命令 pull。拉取然后合并以将下载的提交添加到您的本地分支。

b
bcr

git pullgit fetch 之间的唯一区别是:

git pull 从远程分支中提取并合并它。

git fetch 仅从远程分支获取但不合并

即 git pull = git fetch + git merge ...

P
Pawel Furmaniak

Git 允许在较新的提交之后应用按时间顺序较旧的提交。因此,在存储库之间传输提交的行为分为两个步骤:

将远程分支的新提交复制到本地仓库中此远程分支的副本。 (repo 到 repo 操作)master@remote >> remote/origin/master@local 将新提交集成到本地分支(inside-repo 操作)remote/origin/master@local >> master@local

第 2 步有两种方法。您可以:

在最后一个共同祖先之后分叉本地分支,并添加与本地存储库唯一的提交并行的新提交,通过合并提交完成,关闭分叉。在最后一个共同祖先之后插入新提交并重新应用本地存储库独有的提交。

git 术语中,步骤 1 是 git fetch,步骤 2 是 git mergegit rebase

git pullgit fetchgit merge

i
ishant kaushik

git pull 命令实际上是 git fetchshortcut,后跟 git mergegit rebase命令取决于您的配置。您可以配置您的 Git 存储库,以便 git pull 是一个提取,然后是一个变基。

M
Marcus Thornton

Git 使用两条命令从远程获取最新版本的分支到本地:

git fetch:Git 会从远程获取最新版本到本地,但不会自动合并。 git fetch origin master git log -p master..origin/master git merge origin/master 上面的命令意味着从远程下载主分支的最新版本到源主分支。然后比较本地master分支和origin master分支。最后,合并。 git pull:Git 将从远程获取最新版本并合并到本地。 git pull origin master 上面的命令相当于 git fetch 和 git merge 。在实践中, git fetch 可能更安全,因为在合并之前我们可以看到更改并决定是否合并。

D
Donal

git pull 和 git fetch 有什么区别?

要理解这一点,您首先需要了解您的本地 git 不仅维护您的本地存储库,而且还维护远程存储库的本地副本。

git fetch 使远程存储库的本地副本保持最新。例如,如果您的远程存储库是 GitHub - 您可能希望将远程存储库中所做的任何更改提取到远程存储库的本地副本。这将允许您执行比较或合并等操作。

另一方面,git pull 会将远程存储库中的更改带到您保留自己代码的位置。通常,git pull 将首先执行 git fetch 以使远程存储库的本地副本保持最新,然后它将更改合并到您自己的代码存储库和可能的工作副本中。

M
Mohideen bin Mohammed

初学者的简单图形表示,

https://i.stack.imgur.com/fEvk2.jpg

这里,

git pull  

将从存储库中获取代码并使用您的本地重新设置...在 git pull 中,有可能创建新的提交。

但在 ,

获取

将从存储库中获取代码,我们需要使用 git rebase 手动对其进行变基

例如:我将从服务器主服务器获取并在我的本地主服务器中重新设置它。

1) git pull ( rebase 会自动完成):

git pull origin master

这里 origin 是你的远程仓库 master 是你的分支

2)git fetch(需要手动变基):

git fetch origin master

它将从原点获取服务器更改。它将在您的本地,直到您自己重新设置它。我们需要通过检查代码手动修复冲突。

git rebase origin/master

这会将代码变基为本地代码。在此之前确保您在正确的分支中。

I
Iggy

git pull == ( git fetch + git 合并)

git fetch 不会更改本地分支。

如果您已经有一个为所需项目设置了远程的本地存储库,则可以使用 git fetch 获取现有远程的所有分支和标签。 ... Fetch 不会对本地分支进行任何更改,因此您需要将远程分支与配对的本地分支合并以合并新的 fetch 更改。 from github

y
youpilat13

实际上,Git 维护您自己的代码和远程存储库的副本。

命令 git fetch 通过从远程存储库获取数据使您的本地副本保持最新。我们需要这个的原因是因为其他人可能对代码进行了一些更改,而您希望自己保持更新。

命令 git pull 将远程存储库中的更改带到您保存自己代码的位置。通常,git pull 首先执行“git fetch”以使远程存储库的本地副本保持最新,然后将更改合并到您自己的代码存储库和可能的工作副本中。