1

I wanted to clone just a folder from a repo on Github, am not sure if am using the sparse checkout correctly, but the docs here isn't giving any examples so am fiddling through blog posts to try to understand how to use it.

First I ran
git clone --no-checkout https://github.com/reponame

then
cd reponame

then

git sparse-checkout init --cone
git sparse-checkout set folder1/folder2

But that doesn't populate anything in my folder. When I go there in my windows explorer, I only see the .git folder. I try with fetch and pull, nothing.

So do I need to clone the repo 1 time, THEN I can start using sparse-checkout? Does sparse-checkout work only on existing repos that have been already cloned? If not, what am I doing wrong?

Thanks for any help, am still new to git.

akane
  • 429
  • 1
  • 3
  • 10
B1B
  • 193
  • 5
  • 16
  • What's the content of `.git/info/sparse-checkout`? Has `master` of the repo originally been empty? How about switching to another branch? – ElpieKay Sep 12 '20 at 02:59
  • 2
    This may be teething pains. `--no-checkout` leaves the index (where the flags sparse checkout manipulates are stored) empty, so when sparse checkout applies its patterns there's nothing to apply them to yet, and when it then tries to update the work tree, there's nothing to update. Try `git checkout @` or `git reset --hard` or `git reset -q` followed by `git checkout`, some variation on that should get you what you want. p.s. by teething pains I mean the new sparse-checkout command, the process of setting it up has been completely manual until very recently. – jthill Sep 12 '20 at 03:04
  • hi, git checkout @ did the trick. Now it populated the folder for me. Now let's say I want to get another folder, do I repeat the same steps? @jthill – B1B Sep 12 '20 at 03:43
  • 1
    No, once the index is populated just the sparse-checkout should do it. – jthill Sep 12 '20 at 04:37

2 Answers2

3

Sparse checkout affects your current and all subsequent checkouts, but with a --no-checkout clone you haven't done your first one yet. Do git checkout @ to do that initial checkout, since you've got the sparse patterns set up it'll govern what parts show up.

jthill
  • 55,082
  • 5
  • 77
  • 137
1

The sequence I usually recommend is, with sparse cone:

git clone --filter=blob:none --no-checkout https://github.com/git/git
cd git
git sparse-checkout init --cone
# that sets git config core.sparseCheckoutCone true
git sparse-checkout set folder1/folder2
git read-tree -mu HEAD

Note that, with With Git 2.34 (Q4 2021), "git add"(man), "git mv"(man), and "git rm"(man) have been adjusted to avoid updating paths outside of the sparse-checkout definition unless the user specifies a --sparse option.

See commit 6579e78, commit 93d2c16, commit d7c4415, commit f9786f9, commit 61d450f, commit 63b60b3, commit 0299a69, commit 49fdd51, commit 105e8b0, commit ed49584, commit f652672, commit edd2cd3, commit ca267ae (24 Sep 2021) by Derrick Stolee (derrickstolee).
(Merged by Junio C Hamano -- gitster -- in commit 2d498a7, 13 Oct 2021)

add: implement the --sparse option

Signed-off-by: Derrick Stolee

We previously modified 'git add'(man) to refuse updating index entries outside of the sparse-checkout cone.
This is justified to prevent users from accidentally getting into a confusing state when Git removes those files from the working tree at some later point.

Unfortunately, this caused some workflows that were previously possible to become impossible, especially around merge conflicts outside of the sparse-checkout cone.

We now re-enable these workflows using a new '--sparse' option to 'git add'.
This allows users to signal "Yes, I do know what I'm doing with these files," and accept the consequences of the files leaving the worktree later.

git add now includes in its man page:

[--edit | -e] [--[no-]all | --[no-]ignore-removal | [--update | -u]] [--sparse]

git add now includes in its man page:

--sparse

Allow updating index entries outside of the sparse-checkout cone. Normally, git add refuses to update index entries whose paths do not fit within the sparse-checkout cone, since those files might be removed from the working tree without warning. See git sparse-checkout for more details.

And:

rm: add --sparse option

Signed-off-by: Derrick Stolee

As we did previously in 'git add'(man), add a '--sparse' option to 'git rm'(man) that allows modifying paths outside of the sparse-checkout definition.
The existing checks in 'git rm' are restricted to tracked files that have the SKIP_WORKTREE bit in the current index.
Future changes will cause 'git rm' to reject removing paths outside of the sparse-checkout definition, even if they are untracked or do not have the SKIP_WORKTREE bit.

git rm now includes in its man page:

--sparse

Allow updating index entries outside of the sparse-checkout cone. Normally, git rm refuses to update index entries whose paths do not fit within the sparse-checkout cone. See git sparse-checkout for more.


With Git 2.38 (Q3 2022), "git mv A B"(man)in a sparsely populated working tree can be asked to move a path between directories that are in cone (i.e. expected to be materialized in the working tree) and "out of cone" (i.e. expected to be hidden).

The handling of such cases has been improved.

See commit b91a2b6, commit 24ea81d, commit 8a26a39, commit 6645b03, commit 7889755, commit 707fa2f, commit 1143cc0, commit 367844e (30 Jun 2022) by Shaoxuan Yuan (ffyuanda).
(Merged by Junio C Hamano -- gitster -- in commit 0455aad, 14 Jul 2022)

mv: update sparsity after moving from out-of-cone to in-cone

Helped-by: Victoria Dye
Signed-off-by: Shaoxuan Yuan
Acked-by: Derrick Stolee

Originally, "git mv"(man) a sparse file from out-of-cone to in-cone does not update the moved files sparsity (remove its SKIP_WORKTREE bit).
And the corresponding cache entry is, unexpectedly, not checked out in the working tree.

Update the behavior so that:

  1. Moving from out-of-cone to in-cone removes the SKIP_WORKTREE bit from corresponding cache entry.
  2. The moved cache entry is checked out in the working tree to reflect the updated sparsity.

mv: check if out-of-cone file exists in index with SKIP_WORKTREE bit

Signed-off-by: Shaoxuan Yuan
Acked-by: Derrick Stolee

Originally, moving a <source> file which is not on-disk but exists in index as a SKIP_WORKTREE enabled cache entry, "giv mv" command errors out with "bad source".

Change the checking logic, so that such <source> file makes "giv mv" command warns with "advise_on_updating_sparse_paths()" instead of "bad source".

The following paths and/or pathspecs matched paths that exist
outside of your sparse-checkout definition, so will not be
updated in the index:
...
If you intend to update such entries, try one of the following:"
* Use the --sparse option."
* Disable or modify the sparsity rules.

Also user now can supply a "--sparse" flag so this operation can be carried out successfully.

mv: check if <destination> exists in index to handle overwriting

Signed-off-by: Shaoxuan Yuan
Acked-by: Derrick Stolee

Originally, moving a sparse file into cone can result in unwarned overwrite of existing entry.
The expected behavior is that if the <destination> exists in the entry, user should be prompted to supply a [-f|--force] to carry out the operation, or the operation should fail.

VonC
  • 1,262,500
  • 529
  • 4,410
  • 5,250