如何更新git浅层克隆?

时间:2016-12-10 13:16:35

标签: git git-clone

背景

(对于tl; dr,请参阅下面的#questions)

我有多个git存储库浅克隆。我使用的是浅克隆,因为它与脏克隆相比要小得多。每个都是克隆做约git clone --single-branch --depth 1 <git-repo-url> <dir-name>

这个工作正常,但我没有看到如何更新它。

当我用标签克隆时,更新没有意义,因为标签是冻结的时间点(据我所知)。在这种情况下,如果我想要更新,这意味着我想要通过另一个标签克隆,所以我只是rm -rf <dir-name>并再次克隆。

当我克隆了主分支的HEAD然后想要更新它时,事情变得更加复杂。

我试过git pull --depth 1但是我不想把任何东西推到远程存储库,它抱怨它不知道我是谁。

我尝试了git fetch --depth 1,但是虽然它似乎更新了一些东西,但我检查它是不是最新的(远程存储库上的某些文件的内容与我克隆上的文件不同)。

https://stackoverflow.com/a/20508591/279335之后,我尝试了git fetch --depth 1; git reset --hard origin/master,但有两件事:首先我不明白为什么需要git reset,其次,虽然文件似乎是最新的,但有些旧文件仍然存在,git clean -df不会删除这些文件。

问题

使用git clone --single-branch --depth 1 <git-repo-url> <dir-name>创建克隆。如何更新它以获得与rm -rf <dir-name>; git clone --single-branch --depth 1 <git-repo-url> <dir-name>相同的结果?或者是rm -rf <dir-name>并以唯一的方式再次克隆?

注意

这不是How to update a shallow cloned submodule without increasing main repo size的重复,因为答案不符合我的期望,我使用的是简单的存储库,而不是子模块(我不知道)。

2 个答案:

答案 0 :(得分:3)

在浅层克隆更新过程中,请参阅commit 649b0c3表格Git 2.12(2017年第1季度) 该提交是以下内容的一部分:

Commit 649b0c3commit f2386c6commit 6bc3d8ccommit 0afd307(2016年12月6日)Nguyễn Thái Ngọc Duy (pclouds)。 请commit 1127b3c查看commit 381aa8eRasmus Villemoes (ravi-prevas)(2016年12月6日)。 Junio C Hamano -- gitster --合并于commit 3c9979b,2016年12月21日)

  

shallow.c

     

paint_down()58babff (shallow.c: the 8 steps to select new commits for .git/shallow - 2013-12-05)第6步的一部分   当我们从浅存储库中获取时,我们需要知道其中一个新的/更新的引用是否需要.git/shallow中的新“浅提交”(因为我们没有足够的这些引用的历史记录)以及哪一个。 / p>      

第6步的问题是,需要什么(新的)浅提交   另一个是在没有的情况下维护整个存储库的可达性   缩短我们的历史?   要回答,我们使用UNINTERESTING(“rev-list --not --all”)标记从现有引用可到达的所有提交,使用BOTTOM标记浅提交,然后对于每个新的/更新的引用,遍历提交图,直到我们点击UNINTERESTING或BOTTOM,在我们走路的时候在提交上标记引用。

     

完成所有步行后,我们检查新的浅提交。要是我们   我们都知道,在新的浅层提交中没有看到任何新的引用   只需使用我们的历史记录.git/shallow即可访问新/更新的参考号   不需要浅层提交,可以丢弃。

     

所以,代码。

     

这里的循环(遍历提交)基本上是:

     
      
  1. 从队列中获取一个提交
  2.   
  3. 忽略,如果它是SEEN或UNINTERESTING
  4.   
  5. 标记
  6.   
  7. 通过所有的父母和..
  8.   
    •   
    • 5.a如果它之前从未标记过,则标记
    •   
    • 5.b将其放回队列
    •   
  9.         

    我们在这个补丁中做的是丢弃步骤5a,因为它不是   必要的。
      在5a标记的提交被放回队列中,并且   将在下一次迭代的第3步标记。它唯一的情况   不标记的是提交已经标记为UNINTERESTING(5a   不检查这个),在步骤2中将被忽略。

答案 1 :(得分:0)

如果目标是在不获取整个历史记录的情况下更新浅表克隆(但允许获取简短的历史记录),那么使用git(> = 2.11.1)的现代版本的替代方法可以使用:

  • --shallow-since=...仅获取早于给定日期的提交
  • --shallow-exclude=...来获取而不获取作为给定提交祖先的提交