2016-12-31 14:31:56 +02:00
#!/usr/bin/env bash
set -e
die( ) {
echo " $0 : error: $1 " >& 2
exit 1
}
2018-03-14 23:24:34 +09:00
# Usage: update-source-hash <attr> <version> [<new-source-hash>] [<new-source-url>]
2016-12-31 14:31:56 +02:00
attr = $1
newVersion = $2
newHash = $3
2018-03-14 23:24:34 +09:00
newUrl = $4
2016-12-31 14:31:56 +02:00
nixFile = $( nix-instantiate --eval --strict -A " $attr .meta.position " | sed -re 's/^"(.*):[0-9]+"$/\1/' )
if [ ! -f " $nixFile " ] ; then
die " Couldn't evaluate ' $attr .meta.position' to locate the .nix file! "
fi
oldHashAlgo = $( nix-instantiate --eval --strict -A " $attr .src.drvAttrs.outputHashAlgo " | tr -d '"' )
oldHash = $( nix-instantiate --eval --strict -A " $attr .src.drvAttrs.outputHash " | tr -d '"' )
if [ -z " $oldHashAlgo " -o -z " $oldHash " ] ; then
die " Couldn't evaluate old source hash from ' $attr .src'! "
fi
if [ $( grep -c " $oldHash " " $nixFile " ) != 1 ] ; then
die " Couldn't locate old source hash ' $oldHash ' (or it appeared more than once) in ' $nixFile '! "
fi
2018-03-14 23:24:34 +09:00
oldUrl = $( nix-instantiate --eval -E " with import ./. {}; builtins.elemAt $attr .src.drvAttrs.urls 0 " | tr -d '"' )
if [ -z " $oldUrl " ] ; then
die " Couldn't evaluate source url from ' $attr .name'! "
fi
2016-12-31 14:31:56 +02:00
drvName = $( nix-instantiate --eval -E " with import ./. {}; (builtins.parseDrvName $attr .name).name " | tr -d '"' )
oldVersion = $( nix-instantiate --eval -E " with import ./. {}; $attr .version or (builtins.parseDrvName $attr .name).version " | tr -d '"' )
if [ -z " $drvName " -o -z " $oldVersion " ] ; then
die " Couldn't evaluate name and version from ' $attr .name'! "
fi
if [ " $oldVersion " = " $newVersion " ] ; then
echo " $0 : New version same as old version, nothing to do. " >& 2
exit 0
fi
2017-11-19 03:33:06 +02:00
# Escape regex metacharacter that are allowed in store path names
oldVersion = $( echo " $oldVersion " | sed -re 's|[.+]|\\&|g' )
2018-03-14 23:24:34 +09:00
oldUrl = $( echo " $oldUrl " | sed -re 's|[${}.+]|\\&|g' )
2016-12-31 14:31:56 +02:00
2017-06-09 00:35:17 +03:00
if [ $( grep -c -E " ^\s*(let\b)?\s*version\s*=\s*\" $oldVersion \" " " $nixFile " ) = 1 ] ; then
2016-12-31 14:31:56 +02:00
pattern = " /\bversion\b\s*=/ s|\" $oldVersion \"|\" $newVersion \"| "
2017-11-06 01:55:56 +02:00
elif [ $( grep -c -E " ^\s*(let\b)?\s*name\s*=\s*\"[^\"]+- $oldVersion \" " " $nixFile " ) = 1 ] ; then
2017-11-19 03:36:03 +02:00
pattern = " /\bname\b\s*=/ s|- $oldVersion \"|- $newVersion \"| "
2016-12-31 14:31:56 +02:00
else
die " Couldn't figure out where out where to patch in new version in ' $attr '! "
fi
# Replace new version
sed -i.bak " $nixFile " -re " $pattern "
if cmp -s " $nixFile " " $nixFile .bak " ; then
die " Failed to replace version ' $oldVersion ' to ' $newVersion ' in ' $attr '! "
fi
2018-03-14 23:24:34 +09:00
# Replace new URL
if [ -n " $newUrl " ] ; then
sed -i " $nixFile " -re " s|\" $oldUrl \"|\" $newUrl \"| "
if cmp -s " $nixFile " " $nixFile .bak " ; then
die " Failed to replace source URL ' $oldUrl ' to ' $newUrl ' in ' $attr '! "
fi
fi
2016-12-31 14:31:56 +02:00
case " $oldHashAlgo " in
sha256) hashLength = 64 ; ;
sha512) hashLength = 128 ; ;
*) die " Unhandled hash algorithm ' $oldHashAlgo ' in ' $attr '! " ; ;
esac
# Make a temporary all-zeroes hash of $hashLength characters
tempHash = $( printf '%0*d' " $hashLength " 0)
sed -i " $nixFile " -re " s|\" $oldHash \"|\" $tempHash \"| "
if cmp -s " $nixFile " " $nixFile .bak " ; then
die " Failed to replace source hash of ' $attr ' to a temporary hash! "
fi
# If new hash not given on the command line, recalculate it ourselves.
if [ -z " $newHash " ] ; then
nix-build --no-out-link -A " $attr .src " 2>" $attr .fetchlog " >/dev/null || true
# FIXME: use nix-build --hash here once https://github.com/NixOS/nix/issues/1172 is fixed
2018-03-14 23:24:34 +09:00
newHash = $( egrep -v "killing process|dependencies couldn't be built" " $attr .fetchlog " | tail -n2 | sed "s~output path .* has .* hash ‘ \(.*\)’ when .* was expected\|fixed-output derivation produced path '.*' with .* hash '\(.*\)' instead of the expected hash '.*'~\1\2~" | head -n1)
2016-12-31 14:31:56 +02:00
fi
if [ -z " $newHash " ] ; then
cat " $attr .fetchlog " >& 2
die " Couldn't figure out new hash of ' $attr .src'! "
fi
2017-11-19 03:33:31 +02:00
if [ " $oldVersion " != " $newVersion " ] && [ " $oldHash " = " $newHash " ] ; then
mv " $nixFile .bak " " $nixFile "
die " Both the old and new source hashes of ' $attr .src' were equivalent. Please fix the package's source URL to be dependent on '\${version}'! "
fi
2016-12-31 14:31:56 +02:00
sed -i " $nixFile " -re " s|\" $tempHash \"|\" $newHash \"| "
if cmp -s " $nixFile " " $nixFile .bak " ; then
die " Failed to replace temporary source hash of ' $attr ' to the final source hash! "
fi
rm -f " $nixFile .bak "
rm -f " $attr .fetchlog "