Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
43 changes: 40 additions & 3 deletions pkgs/build-support/fetchgit/nix-prefetch-git
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,43 @@ clone(){
cd $top
}

# Remove all remote branches, remove tags not reachable from HEAD, do a full
# repack and then garbage collect unreferenced objects.
make_deterministic_repo(){
local repo="$1"

# run in sub-shell to not touch current working directory
(
cd "$repo"
# Remove files that contain timestamps or otherwise have non-deterministic
# properties.
rm -rf .git/logs/ .git/hooks/ .git/index .git/FETCH_HEAD .git/ORIG_HEAD \
.git/refs/remotes/origin/HEAD .git/config

# Remove all remote branches.
git branch -r | while read branch; do
git branch -rD "$branch" >&2
done

# Remove tags not reachable from HEAD. If we're exactly on a tag, don't
# delete it.
maybe_tag=$(git tag --points-at HEAD)
git tag --contains HEAD | while read tag; do
if [ "$tag" != "$maybe_tag" ]; then
git tag -d "$tag" >&2
fi
done

# Do a full repack, for determinism.
# Repack does not add unreferenced objects to a pack file.
git repack -A -d -f

# Garbage collect unreferenced objects.
git gc --prune=all
)
}


clone_user_rev() {
local dir="$1"
local url="$2"
Expand Down Expand Up @@ -227,9 +264,9 @@ clone_user_rev() {
echo "removing \`.git'..." >&2
find $dir -name .git\* | xargs rm -rf
else
# The logs and index contain timestamps, and the hooks contain
# the nix path of git's bash
find $dir -name .git | xargs -I {} rm -rf {}/logs {}/index {}/hooks
find $dir -name .git | while read gitdir; do
make_deterministic_repo "$(readlink -f "$gitdir/..")"
done
fi
}

Expand Down