我正在使用一个存储库,其中有大量的文件,需要几个小时才能签出。我正在研究Git是否能很好地使用这种存储库的可能性,因为它支持稀疏签出,但我能找到的每个例子都是这样的:

git clone <path>
git config core.sparsecheckout true
echo <dir> > .git/info/sparse-checkout
git read-tree -m -u HEAD

这个命令序列的问题是原来的克隆也做一个签出。如果在原来的clone命令中添加了-n,则read-tree命令将导致以下错误:

错误:稀疏签出在工作目录上没有留下条目

如何在不先签出所有文件的情况下进行稀疏签出?


当前回答

我从TypeScript定义库@types中获取了这个:

让我们说回购有这样的结构:

types/
|_ identity/
|_ etc...

您的目标:仅签出标识/文件夹。包括子文件夹在内的所有内容。

⚠️这需要最低git版本2.27.0,这可能比大多数机器上的默认版本更新。更复杂的过程可以在旧版本中使用,但本指南没有涉及。

git clone --sparse --filter=blob:none --depth=1 <source-repo-url>
git sparse-checkout add types/identity types/identity ...

这将检出类型/标识文件夹到您的本地机器。

——sparse初始化稀疏签出文件,以便工作目录只从存储库根目录中的文件开始。

——filter=blob:none将排除文件,只在需要时获取它们。

——depth=1将通过截断提交历史来进一步提高克隆速度,但它可能会导致以下总结的问题。

其他回答

根据apenwarr的回答和Miral的评论,我提出了以下解决方案,在本地克隆linux git存储库时节省了近94%的磁盘空间,同时只需要一个文档子目录:

$ cd linux
$ du -sh .git .
2.1G    .git
894M    .
$ du -sh 
2.9G    .
$ mkdir ../linux-sparse-test
$ cd ../linux-sparse-test
$ git init
Initialized empty Git repository in /…/linux-sparse-test/.git/
$ git config core.sparseCheckout true
$ git remote add origin ../linux
# Parameter "origin master" saves a tiny bit if there are other branches
$ git fetch --depth=1 origin master
remote: Enumerating objects: 65839, done.
remote: Counting objects: 100% (65839/65839), done.
remote: Compressing objects: 100% (61140/61140), done.
remote: Total 65839 (delta 6202), reused 22590 (delta 3703)
Receiving objects: 100% (65839/65839), 173.09 MiB | 10.05 MiB/s, done.
Resolving deltas: 100% (6202/6202), done.
From ../linux
 * branch              master     -> FETCH_HEAD
 * [new branch]        master     -> origin/master
$ echo "Documentation/hid/*" > .git/info/sparse-checkout
$ git checkout master
Branch 'master' set up to track remote branch 'master' from 'origin'.
Already on 'master'
$ ls -l
total 4
drwxr-xr-x 3 abe abe 4096 May  3 14:12 Documentation/
$  du -sh .git .
181M    .git
100K    .
$  du -sh
182M    .

所以我从2.9GB降到了182MB,这已经很不错了。

我虽然没有得到这个工作与git克隆-深度1 -no-checkout -filter=blob:none file:///…/linux linux-稀疏-测试(这里暗示)然后丢失的文件都作为删除文件添加到索引。因此,如果有人知道等价于git clone——filter=blob:none用于git读取,我们可能可以节省更多兆字节。(阅读git-rev-list的手册页还提示有像——filter=sparse:path=…这样的东西,但我也没有让它工作。

(都是用Debian Buster的git 2.20.1尝试过的。)

步骤稀疏签出只特定的文件夹:

1) git clone --no-checkout  <project clone url>  
2) cd <project folder>
3) git config core.sparsecheckout true   [You must do this]
4) echo "<path you want to sparce>/*" > .git/info/sparse-checkout
    [You must enter /* at the end of the path such that it will take all contents of that folder]
5) git checkout <branch name> [Ex: master]

是的,可以下载一个文件夹,而不是下载整个存储库。甚至任何/最后一次提交

这样做不错

D:\Lab>git svn clone https://github.com/Qamar4P/LolAdapter.git/trunk/lol-adapter -r HEAD

-r HEAD将只下载最近的版本,忽略所有历史。 注意trunk和/specific文件夹

复制并更改URL在/trunk/之前和之后。我希望这能帮助到一些人。享受:)

2019年9月26日更新

在2020年,有一种更简单的方法来处理稀疏签出,而不必担心.git文件。以下是我的做法:

git clone <URL> --no-checkout <directory>
cd <directory>
git sparse-checkout init --cone # to fetch only root files
git sparse-checkout set apps/my_app libs/my_lib # etc, to list sub-folders to checkout
git checkout # or git switch

注意,它需要安装git 2.25版本。更多信息请点击:https://github.blog/2020-01-17-bring-your-monorepo-down-to-size-with-sparse-checkout/

更新:

上面的git clone命令仍然会克隆出完整的历史记录,尽管没有检出文件。如果你不需要完整的历史,你可以在命令中添加——depth参数,如下所示:

# create a shallow clone,
# with only 1 (since depth equals 1) latest commit in history
git clone <URL> --no-checkout <directory> --depth 1

我是新的git,但似乎如果我做每个目录的git签出,然后它工作。同样,稀疏签出文件需要在每个目录后面都有一个斜杠。有人更有经验,请确认这将工作。

有趣的是,如果签出不在稀疏签出文件中的目录,似乎没有什么区别。它们不会显示在git状态中,git read-tree -m -u HEAD不会导致它被删除。Git reset -hard也不会导致目录被删除。有没有更有经验的人愿意评论一下git对签出但不在稀疏签出文件中的目录的看法?