I'm experimenting with git shallow clones and wonder if there is any possibility to "ungraft" a commit if I happen to fetch the parent of an already existing commit.
Let's say I have a full repo with three commits looking like this (letters indicating their checksums):
A--B--C
I then want a shallow clone of only commit C, and perform the following actions:
git init
git remote add origin url_to_my_repo
git fetch --depth=1 C
git checkout FETCH_HEAD
This leaves me with a shallow clone of the origin repo, where only commit C is
available. The commit is marked as grafted
, indicating the broken history.
Let's say I now also fetch commit B in the same way:
git fetch --depth=1 B
git checkout FETCH_HEAD
Now it is getting interesting. I have two commits that are both marked
grafted
. Recalling that each commit records its parent checksum, which can be
successfully verified using e.g. git cat-file -p C
, Git actually has all
necessary information to replace the grafted mark of commit C with the
real history which in fact is available.
In essence, I want the same outcome as if I would checkout commit C with a depth of 2 in the first place.
I've read this excellent explanation regarding grafted commits, however it
requires me to do a manual intervention. I'm sure there must be a command to
tell git to check all grafted commits if the grafted mark can be removed, e.g.
with git fsck
.
Any ideas?
After reading up a bit on the documentation of shallow concept, I started to play around with the shallow
-file located in the .git
-folder. Essentially it is a list of all commits that are grafted. Removing a commit hash in the file successfully "ungrafts" that very commit (i.e. the graft marker is removed, and history viewed correctly in git log
).
One should be somewhat careful when directly editing anything within the .git-folder, but this at least points in the right direction on how to ungraft commits without perform git fetch --unshallow
.
Edit:
I created a python script for this very purpose and recently published it on GitHub, should anyone be interested: https://github.com/chrillof/git-ungraft