2015-07-30 02:37:31 +00:00
#!/usr/bin/env bash
2015-05-18 19:44:22 +00:00
2015-05-19 22:54:15 +00:00
# assert_pointer confirms that the pointer in the repository for $path in the
# given $ref matches the given $oid and $size.
#
# $ assert_pointer "master" "path/to/file" "some-oid" 123
2015-05-18 22:49:21 +00:00
assert_pointer( ) {
2015-05-22 22:16:47 +00:00
local ref = " $1 "
local path = " $2 "
local oid = " $3 "
local size = " $4 "
2015-05-18 22:49:21 +00:00
2016-02-21 18:10:36 +00:00
gitblob = $( git ls-tree -lrz " $ref " |
while read -r -d $'\0' x; do
echo $x
done |
grep " $path " | cut -f 3 -d " " )
2015-05-18 22:49:21 +00:00
actual = $( git cat-file -p $gitblob )
expected = $( pointer $oid $size )
if [ " $expected " != " $actual " ] ; then
exit 1
2015-05-18 19:44:22 +00:00
fi
}
2015-08-06 10:44:38 +00:00
# assert_local_object confirms that an object file is stored for the given oid &
# has the correct size
# $ assert_local_object "some-oid" size
assert_local_object( ) {
local oid = " $1 "
local size = " $2 "
local cfg = ` git lfs env | grep LocalMediaDir`
local f = " ${ cfg : 14 } / ${ oid : 0 : 2 } / ${ oid : 2 : 2 } / $oid "
actualsize = $( wc -c <" $f " | tr -d '[[:space:]]' )
if [ " $size " != " $actualsize " ] ; then
exit 1
fi
}
# refute_local_object confirms that an object file is NOT stored for an oid
# $ refute_local_object "some-oid"
refute_local_object( ) {
local oid = " $1 "
local cfg = ` git lfs env | grep LocalMediaDir`
local regex = "LocalMediaDir=(\S+)"
local f = " ${ cfg : 14 } / ${ oid : 0 : 2 } / ${ oid : 2 : 2 } / $oid "
if [ -e $f ] ; then
exit 1
fi
}
2015-10-15 15:35:26 +00:00
# delete_local_object deletes the local storage for an oid
# $ delete_local_object "some-oid"
delete_local_object( ) {
local oid = " $1 "
local cfg = ` git lfs env | grep LocalMediaDir`
local f = " ${ cfg : 14 } / ${ oid : 0 : 2 } / ${ oid : 2 : 2 } / $oid "
rm " $f "
}
2015-07-06 18:19:18 +00:00
# check that the object does not exist in the git lfs server. HTTP log is
# written to http.log. JSON output is written to http.json.
#
# $ refute_server_object "reponame" "oid"
2015-05-18 22:49:21 +00:00
refute_server_object( ) {
2015-07-06 18:19:18 +00:00
local reponame = " $1 "
local oid = " $2 "
curl -v " $GITSERVER / $reponame .git/info/lfs/objects/ $oid " \
-u "user:pass" \
-o http.json \
-H "Accept: application/vnd.git-lfs+json" 2>& 1 |
tee http.log
grep "404 Not Found" http.log
2015-05-18 22:49:21 +00:00
}
2015-10-13 14:29:25 +00:00
# Delete an object on the lfs server. HTTP log is
# written to http.log. JSON output is written to http.json.
#
# $ delete_server_object "reponame" "oid"
delete_server_object( ) {
local reponame = " $1 "
local oid = " $2 "
curl -v " $GITSERVER / $reponame .git/info/lfs/delete/ $oid " \
-u "user:pass" \
-o http.json \
-H "Accept: application/vnd.git-lfs+json" 2>& 1 |
tee http.log
grep "200 OK" http.log
}
2015-07-06 18:19:18 +00:00
# check that the object does exist in the git lfs server. HTTP log is written
# to http.log. JSON output is written to http.json.
2015-05-18 22:49:21 +00:00
assert_server_object( ) {
2015-07-06 18:19:18 +00:00
local reponame = " $1 "
local oid = " $2 "
curl -v " $GITSERVER / $reponame .git/info/lfs/objects/ $oid " \
-u "user:pass" \
-o http.json \
-H "Accept: application/vnd.git-lfs+json" 2>& 1 |
tee http.log
grep "200 OK" http.log
grep "download" http.json || {
cat http.json
exit 1
}
2015-05-18 22:49:21 +00:00
}
2016-06-03 16:36:13 +00:00
# assert that a lock with the given ID exists on the test server
assert_server_lock( ) {
local id = " $1 "
curl -v " $GITSERVER /locks/ " \
-u "user:pass" \
-o http.json \
-H "Accept:application/vnd.git-lfs+json" 2>& 1 |
tee http.log
grep "200 OK" http.log
grep " $id " http.json || {
cat http.json
exit 1
}
}
# refute that a lock with the given ID exists on the test server
refute_server_lock( ) {
2016-06-03 21:00:36 +00:00
local id = " $1 "
2016-06-03 16:36:13 +00:00
curl -v " $GITSERVER /locks/ " \
-u "user:pass" \
-o http.json \
2016-06-03 21:00:36 +00:00
-H "Accept:application/vnd.git-lfs+json" 2>& 1 | tee http.log
2016-06-03 16:36:13 +00:00
grep "200 OK" http.log
2016-06-03 21:00:36 +00:00
[ $( grep -c " $id " http.json) -eq 0 ]
2016-06-03 16:36:13 +00:00
}
2015-05-19 22:54:15 +00:00
# pointer returns a string Git LFS pointer file.
#
# $ pointer abc-some-oid 123
# > version ...
2015-05-18 22:49:21 +00:00
pointer( ) {
local oid = $1
local size = $2
printf " version https://git-lfs.github.com/spec/v1
oid sha256:%s
size %s
" " $oid " " $size "
}
2015-05-19 22:54:15 +00:00
# wait_for_file simply sleeps until a file exists.
#
# $ wait_for_file "path/to/upcoming/file"
2015-05-18 19:44:22 +00:00
wait_for_file( ) {
2015-05-22 22:16:47 +00:00
local filename = " $1 "
2015-05-18 19:58:58 +00:00
n = 0
while [ $n -lt 10 ] ; do
2015-05-18 19:44:22 +00:00
if [ -s $filename ] ; then
return 0
fi
sleep 0.5
2015-05-18 19:58:58 +00:00
n = ` expr $n + 1`
2015-05-18 19:44:22 +00:00
done
return 1
}
2015-05-19 22:54:15 +00:00
# setup_remote_repo intializes a bare Git repository that is accessible through
# the test Git server. The `pwd` is set to the repository's directory, in case
# further commands need to be run. This server is running for every test in a
# script/integration run, so every test file should setup its own remote
# repository to avoid conflicts.
#
# $ setup_remote_repo "some-name"
#
2015-05-18 19:44:22 +00:00
setup_remote_repo( ) {
2015-05-22 22:16:47 +00:00
local reponame = " $1 "
2015-05-18 22:49:21 +00:00
echo " set up remote git repository: $reponame "
2015-05-18 19:44:22 +00:00
repodir = " $REMOTEDIR / $reponame .git "
2015-05-18 22:49:21 +00:00
mkdir -p " $repodir "
cd " $repodir "
2015-05-18 19:44:22 +00:00
git init --bare
git config http.receivepack true
git config receive.denyCurrentBranch ignore
2015-05-18 22:49:21 +00:00
}
2015-09-09 20:18:51 +00:00
# creates a bare remote repository for a local clone. Useful to test pushing to
# a fresh remote server.
#
# $ setup_alternate_remote "$reponame-whatever"
# $ setup_alternate_remote "$reponame-whatever" "other-remote-name"
#
setup_alternate_remote( ) {
local newRemoteName = $1
local remote = ${ 2 :- origin }
wd = ` pwd `
setup_remote_repo " $newRemoteName "
cd $wd
git remote rm " $remote "
git remote add " $remote " " $GITSERVER / $newRemoteName "
}
2015-05-19 22:54:15 +00:00
# clone_repo clones a repository from the test Git server to the subdirectory
2015-09-23 19:30:10 +00:00
# $dir under $TRASHDIR. setup_remote_repo() needs to be run first. Output is
# written to clone.log.
2015-05-18 22:49:21 +00:00
clone_repo( ) {
cd " $TRASHDIR "
2015-05-22 22:16:47 +00:00
local reponame = " $1 "
local dir = " $2 "
2015-05-18 22:49:21 +00:00
echo " clone local git repository $reponame to $dir "
2015-05-26 15:39:04 +00:00
out = $( git clone " $GITSERVER / $reponame " " $dir " 2>& 1)
2015-05-18 22:49:21 +00:00
cd " $dir "
2015-05-21 17:04:59 +00:00
git config credential.helper lfstest
2015-09-23 19:30:10 +00:00
echo " $out " > clone.log
2015-05-18 22:49:21 +00:00
echo " $out "
2015-05-18 19:44:22 +00:00
}
2016-03-09 17:31:04 +00:00
# clone_repo_ssl clones a repository from the test Git server to the subdirectory
2016-05-23 21:03:25 +00:00
# $dir under $TRASHDIR, using the SSL endpoint.
2016-03-09 17:31:04 +00:00
# setup_remote_repo() needs to be run first. Output is written to clone_ssl.log.
clone_repo_ssl( ) {
cd " $TRASHDIR "
local reponame = " $1 "
local dir = " $2 "
echo " clone local git repository $reponame to $dir "
2016-03-09 18:03:15 +00:00
out = $( git clone " $SSLGITSERVER / $reponame " " $dir " 2>& 1)
2016-03-09 17:31:04 +00:00
cd " $dir "
git config credential.helper lfstest
2016-03-09 18:03:15 +00:00
2016-03-09 17:31:04 +00:00
echo " $out " > clone_ssl.log
echo " $out "
}
2016-06-03 16:36:13 +00:00
# setup_remote_repo_with_file creates a remote repo, clones it locally, commits
# a file tracked by LFS, and pushes it to the remote:
#
# setup_remote_repo_with_file "reponame" "filename"
setup_remote_repo_with_file( ) {
local reponame = " $1 "
local filename = " $2 "
setup_remote_repo " remote_ $reponame "
clone_repo " remote_ $reponame " " clone_ $reponame "
git lfs track " $filename "
echo " $filename " > " $filename "
git add .gitattributes $filename
git commit -m " add $filename " | tee commit.log
grep "master (root-commit)" commit.log
grep "2 files changed" commit.log
grep " create mode 100644 $filename " commit.log
grep "create mode 100644 .gitattributes" commit.log
2016-06-03 21:09:02 +00:00
git push origin master 2>& 1 | tee push.log
2016-06-03 16:36:13 +00:00
grep "master -> master" push.log
}
2015-05-20 17:25:20 +00:00
# setup initializes the clean, isolated environment for integration tests.
2015-05-18 19:44:22 +00:00
setup( ) {
2015-05-18 22:49:21 +00:00
cd " $ROOTDIR "
2015-05-21 20:48:02 +00:00
rm -rf " $REMOTEDIR "
mkdir " $REMOTEDIR "
2015-05-18 22:49:21 +00:00
2015-06-19 16:58:30 +00:00
if [ -z " $SKIPCOMPILE " ] && [ -z " $LFS_BIN " ] ; then
2015-05-21 17:51:40 +00:00
echo " compile git-lfs for $0 "
2015-06-07 15:40:35 +00:00
script/bootstrap || {
return $?
}
2015-05-21 17:51:40 +00:00
fi
2015-07-06 17:21:50 +00:00
echo " Git LFS: ${ LFS_BIN :- $( which git-lfs) } "
2015-05-26 15:39:04 +00:00
git lfs version
2015-06-19 16:59:45 +00:00
git version
2015-05-18 19:44:22 +00:00
2015-05-21 17:51:40 +00:00
if [ -z " $SKIPCOMPILE " ] ; then
2016-09-16 21:53:47 +00:00
[ $IS_WINDOWS = = "1" ] && EXT = ".exe"
2015-05-21 17:51:40 +00:00
for go in test/cmd/*.go; do
2016-09-16 21:53:47 +00:00
GO15VENDOREXPERIMENT = 1 go build -o " $BINPATH / $( basename $go .go) $EXT " " $go "
2015-05-21 17:51:40 +00:00
done
2016-07-27 13:48:23 +00:00
if [ -z " $SKIPAPITESTCOMPILE " ] ; then
# Ensure API test util is built during tests to ensure it stays in sync
2016-09-16 21:53:47 +00:00
GO15VENDOREXPERIMENT = 1 go build -o " $BINPATH /git-lfs-test-server-api $EXT " "test/git-lfs-test-server-api/main.go" "test/git-lfs-test-server-api/testdownload.go" "test/git-lfs-test-server-api/testupload.go"
2016-07-27 13:48:23 +00:00
fi
2015-05-21 17:51:40 +00:00
fi
2015-05-18 19:44:22 +00:00
2016-03-09 17:31:04 +00:00
LFSTEST_URL = " $LFS_URL_FILE " LFSTEST_SSL_URL = " $LFS_SSL_URL_FILE " LFSTEST_DIR = " $REMOTEDIR " LFSTEST_CERT = " $LFS_CERT_FILE " lfstest-gitserver > " $REMOTEDIR /gitserver.log " 2>& 1 &
2015-05-26 15:39:04 +00:00
2015-07-30 02:03:57 +00:00
# Set up the initial git config and osx keychain if applicable
HOME = " $TESTHOME "
mkdir " $HOME "
2015-11-18 18:27:00 +00:00
git lfs install
2016-07-15 21:05:06 +00:00
git config --global credential.usehttppath true
2015-06-28 12:48:59 +00:00
git config --global credential.helper lfstest
git config --global user.name "Git LFS Tests"
git config --global user.email "git-lfs@example.com"
2016-03-09 18:03:15 +00:00
git config --global http.sslcainfo " $LFS_CERT_FILE "
2015-06-28 12:48:59 +00:00
grep "git-lfs clean" " $REMOTEDIR /home/.gitconfig " > /dev/null || {
echo " global git config should be set in $REMOTEDIR /home "
ls -al " $REMOTEDIR /home "
exit 1
}
2015-05-26 15:39:04 +00:00
2015-08-04 16:06:30 +00:00
# setup the git credential password storage
mkdir -p " $CREDSDIR "
printf "user:pass" > " $CREDSDIR /127.0.0.1 "
2015-07-30 02:03:57 +00:00
echo
2015-07-28 15:38:41 +00:00
echo " HOME: $HOME "
echo " TMP: $TMPDIR "
2015-10-26 22:25:31 +00:00
echo " CREDS: $CREDSDIR "
2015-07-28 15:38:41 +00:00
echo "lfstest-gitserver:"
echo " LFSTEST_URL= $LFS_URL_FILE "
2016-03-09 17:31:04 +00:00
echo " LFSTEST_SSL_URL= $LFS_SSL_URL_FILE "
echo " LFSTEST_CERT= $LFS_CERT_FILE "
2015-07-28 15:38:41 +00:00
echo " LFSTEST_DIR= $REMOTEDIR "
echo "GIT:"
git config --global --get-regexp "lfs|credential|user"
2015-05-18 22:49:21 +00:00
wait_for_file " $LFS_URL_FILE "
2016-03-09 17:31:04 +00:00
wait_for_file " $LFS_SSL_URL_FILE "
2016-03-14 16:46:51 +00:00
wait_for_file " $LFS_CERT_FILE "
2015-07-30 02:03:57 +00:00
echo
2015-05-18 22:49:21 +00:00
}
2015-05-19 22:54:15 +00:00
# shutdown cleans the $TRASHDIR and shuts the test Git server down.
2015-05-18 22:49:21 +00:00
shutdown( ) {
2015-05-21 16:27:40 +00:00
# every test/test-*.sh file should cleanup its trashdir
[ -z " $KEEPTRASH " ] && rm -rf " $TRASHDIR "
2015-05-18 23:15:32 +00:00
2015-05-19 21:13:21 +00:00
if [ " $SHUTDOWN_LFS " != "no" ] ; then
2015-05-21 16:27:40 +00:00
# only cleanup test/remote after script/integration done OR a single
# test/test-*.sh file is run manually.
2015-05-19 21:13:21 +00:00
if [ -s " $LFS_URL_FILE " ] ; then
curl " $( cat " $LFS_URL_FILE " ) /shutdown "
fi
2015-07-24 11:54:43 +00:00
2015-06-24 20:38:10 +00:00
[ -z " $KEEPTRASH " ] && rm -rf " $REMOTEDIR "
2016-03-18 15:04:49 +00:00
# delete entire lfs test root if we created it (double check pattern)
if [ -z " $KEEPTRASH " ] && [ " $RM_GIT_LFS_TEST_DIR " = "yes" ] && [ [ $GIT_LFS_TEST_DIR = = *" $TEMPDIR_PREFIX " * ] ] ; then
rm -rf " $GIT_LFS_TEST_DIR "
fi
fi
2015-05-18 19:44:22 +00:00
}
2015-07-31 13:45:42 +00:00
2015-07-31 16:31:26 +00:00
ensure_git_version_isnt( ) {
local expectedComparison = $1
local version = $2
local gitVersion = $( git version | cut -d" " -f3)
set +e
compare_version $gitVersion $version
result = $?
set -e
if [ [ $result = = $expectedComparison ] ] ; then
echo " skip: $0 (git version $( comparison_to_operator $expectedComparison ) $version ) "
exit
fi
}
2015-07-31 13:45:42 +00:00
VERSION_EQUAL = 0
VERSION_HIGHER = 1
VERSION_LOWER = 2
2015-07-31 16:31:26 +00:00
2015-07-31 13:45:42 +00:00
# Compare $1 and $2 and return VERSION_EQUAL / VERSION_LOWER / VERSION_HIGHER
compare_version( ) {
if [ [ $1 = = $2 ] ]
then
return $VERSION_EQUAL
fi
local IFS = .
local i ver1 = ( $1 ) ver2 = ( $2 )
# fill empty fields in ver1 with zeros
for ( ( i = ${# ver1 [@] } ; i<${# ver2 [@] } ; i++) )
do
ver1[ i] = 0
done
for ( ( i = 0; i<${# ver1 [@] } ; i++) )
do
if [ [ -z ${ ver2 [i] } ] ]
then
# fill empty fields in ver2 with zeros
ver2[ i] = 0
fi
if ( ( 10#${ ver1 [i] } > 10#${ ver2 [i] } ) )
then
return $VERSION_HIGHER
fi
if ( ( 10#${ ver1 [i] } < 10#${ ver2 [i] } ) )
then
return $VERSION_LOWER
fi
done
return $VERSION_EQUAL
2015-07-31 16:31:26 +00:00
}
comparison_to_operator( ) {
local comparison = $1
if [ [ $1 = = $VERSION_EQUAL ] ] ; then
echo "=="
elif [ [ $1 = = $VERSION_HIGHER ] ] ; then
echo ">"
elif [ [ $1 = = $VERSION_LOWER ] ] ; then
echo "<"
else
echo "???"
fi
}
2015-08-25 16:39:33 +00:00
2015-09-21 17:50:22 +00:00
calc_oid( ) {
printf " $1 " | shasum -a 256 | cut -f 1 -d " "
}
2015-08-25 16:39:33 +00:00
# Get a date string with an offset
# Args: One or more date offsets of the form (regex) "[+-]\d+[dmyHM]"
# e.g. +1d = 1 day forward from today
# -5y = 5 years before today
# Example call:
# D=$(get_date +1y +1m -5H)
# returns date as string in RFC3339 format ccyy-mm-ddThh:MM:ssZ
# note returns in UTC time not local time hence Z and not +/-
get_date( ) {
# Wrapped because BSD (inc OSX) & GNU 'date' functions are different
# on Windows under Git Bash it's GNU
if date --version >/dev/null 2>& 1 ; then # GNU
ARGS = ""
for var in " $@ "
do
# GNU offsets are more verbose
unit = ${ var : -1 }
val = ${ var : 0 : ${# var } -1 }
case " $unit " in
d) unit = "days" ; ;
m) unit = "months" ; ;
y) unit = "years" ; ;
H) unit = "hours" ; ;
M) unit = "minutes" ; ;
esac
ARGS = " $ARGS $val $unit "
done
date -d " $ARGS " -u +%Y-%m-%dT%TZ
else # BSD
ARGS = ""
for var in " $@ "
do
ARGS = " $ARGS -v $var "
done
date $ARGS -u +%Y-%m-%dT%TZ
fi
2015-09-09 20:18:51 +00:00
}
2015-10-16 12:28:34 +00:00
# Convert potentially MinGW bash paths to native Windows paths
# Needed to match generic built paths in test scripts to native paths generated from Go
native_path( ) {
2015-10-16 13:26:56 +00:00
local arg = $1
2015-10-20 14:27:47 +00:00
if [ $IS_WINDOWS = = "1" ] ; then
2015-10-16 12:28:34 +00:00
# Use params form to avoid interpreting any '\' characters
2015-10-16 13:26:56 +00:00
printf '%s' " $( cygpath -w $arg ) "
2015-10-16 12:28:34 +00:00
else
2015-10-16 13:26:56 +00:00
printf '%s' " $arg "
2015-10-16 12:28:34 +00:00
fi
}
2015-10-21 09:58:18 +00:00
2015-10-23 08:21:49 +00:00
# escape any instance of '\' with '\\' on Windows
escape_path( ) {
local unescaped = " $1 "
2015-10-22 13:34:44 +00:00
if [ $IS_WINDOWS = = "1" ] ; then
printf '%s' " ${ unescaped // \\ / \\ \\ } "
else
printf '%s' " $unescaped "
fi
2015-10-23 08:21:49 +00:00
}
# As native_path but escape all backslash characters to "\\"
native_path_escaped( ) {
local unescaped = $( native_path " $1 " )
2015-10-26 22:25:31 +00:00
escape_path " $unescaped "
2015-10-22 13:34:44 +00:00
}
2015-10-21 09:58:18 +00:00
# Compare 2 lists which are newline-delimited in a string, ignoring ordering and blank lines
contains_same_elements( ) {
# Remove blank lines then sort
2015-10-23 08:13:55 +00:00
printf '%s' " $1 " | grep -v '^$' | sort > a.txt
printf '%s' " $2 " | grep -v '^$' | sort > b.txt
2015-10-21 09:58:18 +00:00
2015-10-23 08:13:55 +00:00
set +e
diff -u a.txt b.txt 1>& 2
res = $?
set -e
rm a.txt b.txt
exit $res
2015-10-21 09:58:18 +00:00
}
2015-10-22 11:49:48 +00:00
is_stdin_attached( ) {
test -t0
echo $?
2015-10-26 22:25:31 +00:00
}
2015-10-26 23:12:15 +00:00
has_test_dir( ) {
if [ -z " $GIT_LFS_TEST_DIR " ] ; then
echo "No GIT_LFS_TEST_DIR. Skipping..."
exit 0
fi
}