如何使用git提取特定目录

blu*_*oot 174 git directory pull

我有一个带git的项目,我只想克隆或拉出一个特定的目录,就像myproject/javascript一样,就像subversion一样.
进行一些更改,提交并再次推回.
这是可能的?

ver*_*hon 189

  1. cd进入repo副本的顶部
  2. git fetch
  3. git checkout HEAD path/to/your/dir/or/file

    • 其中" path/..."()中的" .../file"从包含" " 的repo根目录正下方的目录开始

  • 这仍然得到整个回购.对于2GB大小的项目,这不会节省太多时间.. (15认同)
  • 对于那些阅读这些评论但不知道如何回答这个问题的人来说,这个解决方案所做的只是给你一个文件夹的副本,但它不是一个工作副本,这意味着你无法修改和重新-承诺.所以@Morgon说,它解决了问题的标题(你只能拉一个目录),但没有回答问题的主体("做出一些改变,提交并再次推回"). (4认同)
  • 刚刚意识到我误解了这个问题。相反,我的回复解决了如何签出单个文件,然后可以修改和提交该文件。 (2认同)

小智 89

在一个空目录中:

git init
git remote add [REMOTE_NAME] [GIT_URL]
git fetch REMOTE_NAME
git checkout REMOTE_NAME/BRANCH -- path/to/directory
Run Code Online (Sandbox Code Playgroud)

  • 当接受的答案没有时,这对我有用. (5认同)
  • 这是对OP的正确答案. (4认同)
  • 正如 Pithkos 在接受的答案中指出的那样,该答案还将整个远程存储库下载到您的本地计算机。shingara 的答案是最明确的——没有办法远程拉取仓库的一部分。但是,对于那些不介意整个提取的带宽,并且有兴趣制作本地缓存的一部分的工作副本的人,那么接受的答案将向您展示如何操作。但我只是想澄清一下,必须将存储库的整个历史记录(以压缩格式)下载到您的计算机上。 (2认同)

msb*_*msb 30

经过多次寻找答案,没有找到,放弃,再次尝试等等,我终于在另一个SO线程中找到了解决方案:

如何git-pull除了一个文件夹

复制粘贴那里的东西:

git init
git remote add -f origin <url>
git config core.sparsecheckout true
echo <dir1>/ >> .git/info/sparse-checkout
echo <dir2>/ >> .git/info/sparse-checkout
echo <dir3>/ >> .git/info/sparse-checkout
git pull origin master
Run Code Online (Sandbox Code Playgroud)

为了做OP想要的(仅在一个目录上工作),只需.git/info/sparse-checkout在执行上述步骤时添加一个目录.

非常感谢@cforbish!

  • 这是唯一一种干净的解决方案。尝试了上面的答案。在我用其他答案检查我的分支后,我无法拉取,并且有几个需要提交的新文件。有了这个解决方案,一切看起来都不错。但是注意:无论签出哪个分支,git 都会认为您在“master”中。只需确保您执行 `git branch --set-upstream-to=origin/&lt;branch&gt;` 以正确拉取 (3认同)
  • 我在这里发布它主要是因为每当我尝试用谷歌搜索如何做到这一点时,这是一个最佳结果,并且该线程甚至还没有接近显示。:(我觉得复制粘贴不好,但我认为这是最佳实践? (2认同)

fer*_*llo 19

如果您想在不输入目录的情况下获取目录中的最新更改,您可以执行以下操作:

$ git -C <Path to directory> pull
Run Code Online (Sandbox Code Playgroud)


shi*_*ara 13

这是不可能的.您需要拉动所有存储库或什么都不需

  • 只是为了补充一点,你不能只拉一个目录的原因是因为git使用数据语义跟踪,而不是文件语义跟踪,所以你可以无缝地将代码(或其他数据)移入和移出文件而不必告诉源代码跟踪系统(直到你更新当然.)因此,代码可以无缝地移入和移出目录,所以抓住一个目录并没有多大意义.希望这可以帮助. (10认同)
  • @OmnipotentEntity抱歉,恕我直言_does_有意义.实施不应限制使用.Git确实知道目录是什么(至少在创建本地工作副本时),因此没有理由不能在服务器上执行某些类似的操作并只发送相关的输出.当然,目前尚未实施,但这是由于缺乏功能,而不是基本的不可能性.我个人认为这是一个非常重要的功能,但嘿,这是我尽可能避免使用git的原因之一. (10认同)

小智 9

也许这个命令可能会有所帮助:

git archive --remote=MyRemoteGitRepo --format=tar BranchName_or_commit  path/to/your/dir/or/file > files.tar
Run Code Online (Sandbox Code Playgroud)

"Etvoilà"

  • 很酷。作为OP的解决方案可能不可接受,但这实际上是*我*所追求的,因为我只需要在更大的存储库中搜索大文件夹的内容,我绝对不想获取,而且我不需要修改/推送。 (4认同)
  • 这会下载文件的特定目录以进行存档,这不会提取您可以修改和推回的副本. (2认同)

Cir*_*四事件 8

git clone --filter 从 git 2.19 现在在 GitHub 上工作(测试 2020-09-18,git 2.25.1)

我不确定拉/取,但至少对于初始克隆,此选项与远程协议的更新一起添加,它确实阻止了从服务器下载对象。

例如,仅克隆d1此存储库所需的对象:https : //github.com/cirosantilli/test-git-partial-clone我可以这样做:

git clone \
  --depth 1 \
  --filter=blob:none \
  --no-checkout \
  https://github.com/cirosantilli/test-git-partial-clone \
;
cd test-git-partial-clone
git checkout master -- d1
Run Code Online (Sandbox Code Playgroud)

我在以下位置更详细地介绍了这一点:Git:如何仅克隆 Git 存储库的子目录?

很可能git clone在那个领域实施的任何东西也有git pull类似物,但我还不能很容易地找到它。


小智 6

尝试并测试了这个作品!

mkdir <directory name> ;  //Same directory name as the one you want to pull
cd <directory name>;
git remote add origin <GIT_URL>;
git checkout -b '<branch name>';
git config core.sparsecheckout true;
echo <directory name>/ >> .git/info/sparse-checkout;
git pull origin <pull branch name>
Run Code Online (Sandbox Code Playgroud)

希望这有帮助!