1#!/bin/sh 2# 3# Copyright (c) 2005 Junio C Hamano 4# 5 6# Keep the original TERM for say_color 7ORIGINAL_TERM=$TERM 8 9# For repeatability, reset the environment to known value. 10LANG=C 11LC_ALL=C 12PAGER=cat 13TZ=UTC 14TERM=dumb 15export LANG LC_ALL PAGER TERM TZ 16EDITOR=: 17VISUAL=: 18unset GIT_EDITOR 19unset AUTHOR_DATE 20unset AUTHOR_EMAIL 21unset AUTHOR_NAME 22unset COMMIT_AUTHOR_EMAIL 23unset COMMIT_AUTHOR_NAME 24unset EMAIL 25unset GIT_ALTERNATE_OBJECT_DIRECTORIES 26unset GIT_AUTHOR_DATE 27GIT_AUTHOR_EMAIL=author@example.com 28GIT_AUTHOR_NAME='A U Thor' 29unset GIT_COMMITTER_DATE 30GIT_COMMITTER_EMAIL=committer@example.com 31GIT_COMMITTER_NAME='C O Mitter' 32unset GIT_DIFF_OPTS 33unset GIT_DIR 34unset GIT_WORK_TREE 35unset GIT_EXTERNAL_DIFF 36unset GIT_INDEX_FILE 37unset GIT_OBJECT_DIRECTORY 38unset SHA1_FILE_DIRECTORIES 39unset SHA1_FILE_DIRECTORY 40GIT_MERGE_VERBOSITY=5 41export GIT_MERGE_VERBOSITY 42export GIT_AUTHOR_EMAIL GIT_AUTHOR_NAME 43export GIT_COMMITTER_EMAIL GIT_COMMITTER_NAME 44export EDITOR VISUAL 45GIT_TEST_CMP=${GIT_TEST_CMP:-diff -u} 46 47# Protect ourselves from common misconfiguration to export 48# CDPATH into the environment 49unset CDPATH 50 51case$(echo $GIT_TRACE |tr "[A-Z]" "[a-z]")in 521|2|true) 53echo"* warning: Some tests will not work if GIT_TRACE" \ 54"is set as to trace on STDERR ! *" 55echo"* warning: Please set GIT_TRACE to something" \ 56"other than 1, 2 or true ! *" 57;; 58esac 59 60# Each test should start with something like this, after copyright notices: 61# 62# test_description='Description of this test... 63# This test checks if command xyzzy does the right thing... 64# ' 65# . ./test-lib.sh 66["x$ORIGINAL_TERM"!="xdumb"] && ( 67 TERM=$ORIGINAL_TERM&& 68export TERM && 69[-t1] && 70tput bold >/dev/null 2>&1&& 71tput setaf 1>/dev/null 2>&1&& 72tput sgr0 >/dev/null 2>&1 73) && 74 color=t 75 76whiletest"$#"-ne0 77do 78case"$1"in 79-d|--d|--de|--deb|--debu|--debug) 80 debug=t;shift;; 81-i|--i|--im|--imm|--imme|--immed|--immedi|--immedia|--immediat|--immediate) 82 immediate=t;shift;; 83-l|--l|--lo|--lon|--long|--long-|--long-t|--long-te|--long-tes|--long-test|--long-tests) 84export GIT_TEST_LONG=t;shift;; 85-h|--h|--he|--hel|--help) 86help=t;shift;; 87-v|--v|--ve|--ver|--verb|--verbo|--verbos|--verbose) 88 verbose=t;shift;; 89-q|--q|--qu|--qui|--quie|--quiet) 90 quiet=t;shift;; 91--no-color) 92 color=;shift;; 93--no-python) 94# noop now... 95shift;; 96*) 97break;; 98esac 99done 100 101iftest -n"$color";then 102 say_color () { 103( 104 TERM=$ORIGINAL_TERM 105export TERM 106case"$1"in 107 error)tput bold;tput setaf 1;;# bold red 108 skip)tput bold;tput setaf 2;;# bold green 109 pass)tput setaf 2;;# green 110 info)tput setaf 3;;# brown 111*)test -n"$quiet"&&return;; 112esac 113shift 114echo"* $*" 115tput sgr0 116) 117} 118else 119 say_color() { 120test -z"$1"&&test -n"$quiet"&&return 121shift 122echo"* $*" 123} 124fi 125 126error () { 127 say_color error "error: $*" 128trap-exit 129exit1 130} 131 132say () { 133 say_color info "$*" 134} 135 136test"${test_description}"!=""|| 137error "Test script did not set test_description." 138 139iftest"$help"="t" 140then 141echo"$test_description" 142exit0 143fi 144 145exec5>&1 146iftest"$verbose"="t" 147then 148exec4>&2 3>&1 149else 150exec4>/dev/null 3>/dev/null 151fi 152 153test_failure=0 154test_count=0 155test_fixed=0 156test_broken=0 157 158die () { 159echo>&5"FATAL: Unexpected exit with code $?" 160exit1 161} 162 163trap'die'exit 164 165# The semantics of the editor variables are that of invoking 166# sh -c "$EDITOR \"$@\"" files ... 167# 168# If our trash directory contains shell metacharacters, they will be 169# interpreted if we just set $EDITOR directly, so do a little dance with 170# environment variables to work around this. 171# 172# In particular, quoting isn't enough, as the path may contain the same quote 173# that we're using. 174test_set_editor () { 175 FAKE_EDITOR="$1" 176export FAKE_EDITOR 177 VISUAL='"$FAKE_EDITOR"' 178export VISUAL 179} 180 181test_tick () { 182iftest -z"${test_tick+set}" 183then 184 test_tick=1112911993 185else 186 test_tick=$(($test_tick + 60)) 187fi 188 GIT_COMMITTER_DATE="$test_tick-0700" 189 GIT_AUTHOR_DATE="$test_tick-0700" 190export GIT_COMMITTER_DATE GIT_AUTHOR_DATE 191} 192 193# You are not expected to call test_ok_ and test_failure_ directly, use 194# the text_expect_* functions instead. 195 196test_ok_ () { 197 test_count=$(expr "$test_count" + 1) 198 say_color """ ok$test_count: $@" 199} 200 201test_failure_ () { 202 test_count=$(expr "$test_count" + 1) 203 test_failure=$(expr "$test_failure" + 1); 204 say_color error "FAIL$test_count:$1" 205shift 206echo"$@"|sed-e's/^/ /' 207test"$immediate"=""|| {trap-exit;exit1; } 208} 209 210test_known_broken_ok_ () { 211 test_count=$(expr "$test_count" + 1) 212 test_fixed=$(($test_fixed+1)) 213 say_color """ FIXED$test_count: $@" 214} 215 216test_known_broken_failure_ () { 217 test_count=$(expr "$test_count" + 1) 218 test_broken=$(($test_broken+1)) 219 say_color skip " still broken$test_count: $@" 220} 221 222test_debug () { 223test"$debug"=""||eval"$1" 224} 225 226test_run_ () { 227eval>&3 2>&4"$1" 228 eval_ret="$?" 229return0 230} 231 232test_skip () { 233 this_test=$(expr "./$0" : '.*/\(t[0-9]*\)-[^/]*$') 234 this_test="$this_test.$(expr "$test_count" + 1)" 235 to_skip= 236 for skp in$GIT_SKIP_TESTS 237 do 238 case "$this_test" in 239$skp) 240 to_skip=t 241 esac 242 done 243 case "$to_skip" in 244 t) 245 say_color skip >&3 "skipping test: $@" 246 test_count=$(expr "$test_count" + 1) 247 say_color skip "skip$test_count:$1" 248 : true 249 ;; 250 *) 251 false 252 ;; 253 esac 254} 255 256test_expect_failure () { 257 test "$#" = 2 || 258 error "bug in the test script: not 2 parameters to test-expect-failure" 259 if ! test_skip "$@" 260 then 261 say >&3 "checking known breakage:$2" 262 test_run_ "$2" 263 if [ "$?" = 0 -a "$eval_ret" = 0 ] 264 then 265 test_known_broken_ok_ "$1" 266 else 267 test_known_broken_failure_ "$1" 268 fi 269 fi 270 echo >&3 "" 271} 272 273test_expect_success () { 274 test "$#" = 2 || 275 error "bug in the test script: not 2 parameters to test-expect-success" 276 if ! test_skip "$@" 277 then 278 say >&3 "expecting success:$2" 279 test_run_ "$2" 280 if [ "$?" = 0 -a "$eval_ret" = 0 ] 281 then 282 test_ok_ "$1" 283 else 284 test_failure_ "$@" 285 fi 286 fi 287 echo >&3 "" 288} 289 290test_expect_code () { 291 test "$#" = 3 || 292 error "bug in the test script: not 3 parameters to test-expect-code" 293 if ! test_skip "$@" 294 then 295 say >&3 "expecting exit code$1:$3" 296 test_run_ "$3" 297 if [ "$?" = 0 -a "$eval_ret" = "$1" ] 298 then 299 test_ok_ "$2" 300 else 301 test_failure_ "$@" 302 fi 303 fi 304 echo >&3 "" 305} 306 307# test_external runs external test scripts that provide continuous 308# test output about their progress, and succeeds/fails on 309# zero/non-zero exit code. It outputs the test output on stdout even 310# in non-verbose mode, and announces the external script with "* run 311# <n>: ..." before running it. When providing relative paths, keep in 312# mind that all scripts run in "trash directory". 313# Usage: test_external description command arguments... 314# Example: test_external 'Perl API' perl ../path/to/test.pl 315test_external () { 316 test "$#" -eq 3 || 317 error >&5 "bug in the test script: not 3 parameters to test_external" 318 descr="$1" 319 shift 320 if ! test_skip "$descr" "$@" 321 then 322 # Announce the script to reduce confusion about the 323 # test output that follows. 324 say_color "" " run$(expr "$test_count" + 1):$descr($*)" 325 # Run command; redirect its stderr to &4 as in 326 # test_run_, but keep its stdout on our stdout even in 327 # non-verbose mode. 328 "$@" 2>&4 329 if [ "$?" = 0 ] 330 then 331 test_ok_ "$descr" 332 else 333 test_failure_ "$descr" "$@" 334 fi 335 fi 336} 337 338# Like test_external, but in addition tests that the command generated 339# no output on stderr. 340test_external_without_stderr () { 341 # The temporary file has no (and must have no) security 342 # implications. 343 tmp="$TMPDIR"; if [ -z "$tmp" ]; then tmp=/tmp; fi 344 stderr="$tmp/git-external-stderr.$$.tmp" 345 test_external "$@" 4> "$stderr" 346 [ -f "$stderr" ] || error "Internal error:$stderrdisappeared." 347 descr="no stderr:$1" 348 shift 349 say >&3 "expecting no stderr from previous command" 350 if [ ! -s "$stderr" ]; then 351 rm "$stderr" 352 test_ok_ "$descr" 353 else 354 if [ "$verbose" = t ]; then 355 output=`echo; echo Stderr is:; cat "$stderr"` 356 else 357 output= 358 fi 359 # rm first in case test_failure exits. 360 rm "$stderr" 361 test_failure_ "$descr" "$@" "$output" 362 fi 363} 364 365# This is not among top-level (test_expect_success | test_expect_failure) 366# but is a prefix that can be used in the test script, like: 367# 368# test_expect_success 'complain and die' ' 369# do something && 370# do something else && 371# test_must_fail git checkout ../outerspace 372# ' 373# 374# Writing this as "! git checkout ../outerspace" is wrong, because 375# the failure could be due to a segv. We want a controlled failure. 376 377test_must_fail () { 378"$@" 379test $? -gt0-a $? -le129 380} 381 382# test_cmp is a helper function to compare actual and expected output. 383# You can use it like: 384# 385# test_expect_success 'foo works' ' 386# echo expected >expected && 387# foo >actual && 388# test_cmp expected actual 389# ' 390# 391# This could be written as either "cmp" or "diff -u", but: 392# - cmp's output is not nearly as easy to read as diff -u 393# - not all diff versions understand "-u" 394 395test_cmp() { 396$GIT_TEST_CMP"$@" 397} 398 399# Most tests can use the created repository, but some may need to create more. 400# Usage: test_create_repo <directory> 401test_create_repo () { 402test"$#"=1|| 403 error "bug in the test script: not 1 parameter to test-create-repo" 404 owd=`pwd` 405 repo="$1" 406mkdir"$repo" 407cd"$repo"|| error "Cannot setup test environment" 408"$GIT_EXEC_PATH/git" init "--template=$GIT_EXEC_PATH/templates/blt/">/dev/null 2>&1|| 409 error "cannot run git init -- have you built things yet?" 410mv .git/hooks .git/hooks-disabled 411cd"$owd" 412} 413 414test_done () { 415trap-exit 416 417iftest"$test_fixed"!=0 418then 419 say_color pass "fixed$test_fixedknown breakage(s)" 420fi 421iftest"$test_broken"!=0 422then 423 say_color error "still have$test_brokenknown breakage(s)" 424 msg="remaining$(($test_count-$test_broken)) test(s)" 425else 426 msg="$test_counttest(s)" 427fi 428case"$test_failure"in 4290) 430# We could: 431# cd .. && rm -fr 'trash directory' 432# but that means we forbid any tests that use their own 433# subdirectory from calling test_done without coming back 434# to where they started from. 435# The Makefile provided will clean this test area so 436# we will leave things as they are. 437 438 say_color pass "passed all$msg" 439exit0;; 440 441*) 442 say_color error "failed$test_failureamong$msg" 443exit1;; 444 445esac 446} 447 448# Test the binaries we have just built. The tests are kept in 449# t/ subdirectory and are run in 'trash directory' subdirectory. 450PATH=$(pwd)/..:$PATH 451GIT_EXEC_PATH=$(pwd)/.. 452GIT_TEMPLATE_DIR=$(pwd)/../templates/blt 453unset GIT_CONFIG 454unset GIT_CONFIG_LOCAL 455GIT_CONFIG_NOSYSTEM=1 456GIT_CONFIG_NOGLOBAL=1 457export PATH GIT_EXEC_PATH GIT_TEMPLATE_DIR GIT_CONFIG_NOSYSTEM GIT_CONFIG_NOGLOBAL 458 459GITPERLLIB=$(pwd)/../perl/blib/lib:$(pwd)/../perl/blib/arch/auto/Git 460export GITPERLLIB 461test -d ../templates/blt || { 462 error "You haven't built things yet, have you?" 463} 464 465if!test -x ../test-chmtime;then 466echo>&2'You need to build test-chmtime:' 467echo>&2'Run "make test-chmtime" in the source (toplevel) directory' 468exit1 469fi 470 471. ../GIT-BUILD-OPTIONS 472 473# Test repository 474test="trash directory" 475rm-fr"$test"|| { 476trap-exit 477echo>&5"FATAL: Cannot prepare test area" 478exit1 479} 480 481test_create_repo "$test" 482# Use -P to resolve symlinks in our working directory so that the cwd 483# in subprocesses like git equals our $PWD (for pathname comparisons). 484cd -P"$test"||exit1 485 486this_test=$(expr "./$0" : '.*/\(t[0-9]*\)-[^/]*$') 487for skp in$GIT_SKIP_TESTS 488do 489 to_skip= 490 for skp in$GIT_SKIP_TESTS 491 do 492 case "$this_test" in 493$skp) 494 to_skip=t 495 esac 496 done 497 case "$to_skip" in 498 t) 499 say_color skip >&3 "skipping test$this_testaltogether" 500 say_color skip "skip all tests in$this_test" 501 test_done 502 esac 503done