]> git.notmuchmail.org Git - notmuch/blobdiff - test/test-lib.sh
test: Don't return the result of checking for running emacs to the tester.
[notmuch] / test / test-lib.sh
index 0996a7426442cca7ab4c1913fa7612a88e6ce767..82c686ca074030e86397693775512c764751b690 100644 (file)
@@ -1,4 +1,3 @@
-#!/usr/bin/env bash
 #
 # Copyright (c) 2005 Junio C Hamano
 #
@@ -50,6 +49,7 @@ TZ=UTC
 TERM=dumb
 export LANG LC_ALL PAGER TERM TZ
 GIT_TEST_CMP=${GIT_TEST_CMP:-diff -u}
+TEST_EMACS=${TEST_EMACS:-${EMACS:-emacs}}
 
 # Protect ourselves from common misconfiguration to export
 # CDPATH into the environment
@@ -116,6 +116,16 @@ do
        esac
 done
 
+if test -n "$debug"; then
+    print_subtest () {
+       printf " %-4s" "[$((test_count - 1))]"
+    }
+else
+    print_subtest () {
+       true
+    }
+fi
+
 if test -n "$color"; then
        say_color () {
                (
@@ -130,8 +140,9 @@ if test -n "$color"; then
                esac
                shift
                printf " "
-                printf "$@"
+               printf "$@"
                tput sgr0
+               print_subtest
                )
        }
 else
@@ -139,7 +150,8 @@ else
                test -z "$1" && test -n "$quiet" && return
                shift
                printf " "
-                printf "$@"
+               printf "$@"
+               print_subtest
        }
 fi
 
@@ -237,7 +249,7 @@ remove_cr () {
 #      Store the message in file 'name'. The default is to store it
 #      in 'msg-<count>', where <count> is three-digit number of the
 #      message.
-#      
+#
 #  [body]=text
 #
 #      Text to use as the body of the email message
@@ -310,7 +322,7 @@ generate_message ()
     fi
 
     if [ -z "${template[date]}" ]; then
-       template[date]="Tue, 05 Jan 2001 15:43:57 -0000"
+       template[date]="Fri, 05 Jan 2001 15:43:57 +0000"
     fi
 
     additional_headers=""
@@ -554,13 +566,27 @@ test_declare_external_prereq () {
        test "$#" = 2 && name=$2 || name="$binary(1)"
 
        hash $binary 2>/dev/null || eval "
+       test_missing_external_prereq_${binary}_=t
 $binary () {
-       echo -n \"\$test_subtest_missing_external_prereqs_\" | grep -e \" $name \" ||
-       test_subtest_missing_external_prereqs_=\"$test_subtest_missing_external_prereqs_ $name\"
+       echo -n \"\$test_subtest_missing_external_prereqs_ \" | grep -qe \" $name \" ||
+       test_subtest_missing_external_prereqs_=\"\$test_subtest_missing_external_prereqs_ $name\"
        false
 }"
 }
 
+# Explicitly require external prerequisite.  Useful when binary is
+# called indirectly (e.g. from emacs).
+# Returns success if dependency is available, failure otherwise.
+test_require_external_prereq () {
+       binary="$1"
+       if [ "$(eval echo -n \$test_missing_external_prereq_${binary}_)" = t ]; then
+               # dependency is missing, call the replacement function to note it
+               eval "$binary"
+       else
+               true
+       fi
+}
+
 # You are not expected to call test_ok_ and test_failure_ directly, use
 # the text_expect_* functions instead.
 
@@ -657,7 +683,8 @@ test_check_missing_external_prereqs_ () {
 
 test_report_skip_ () {
        test_reset_state_
-       say_color skip >&3 "skipping test: $@"
+       say_color skip >&3 "skipping test:"
+       echo " $@" >&3
        say_color skip "%-6s" "SKIP"
        echo " $1"
 }
@@ -842,7 +869,7 @@ test_done () {
        [ -n "$EMACS_SERVER" ] && test_emacs '(kill-emacs)'
 
        if [ "$test_failure" = "0" ]; then
-           if [ "$test_broken" = "0" ]; then       
+           if [ "$test_broken" = "0" ]; then
                rm -rf "$remove_tmp"
            fi
            exit 0
@@ -854,7 +881,7 @@ test_done () {
 emacs_generate_script () {
        # Construct a little test script here for the benefit of the user,
        # (who can easily run "run_emacs" to get the same emacs environment
-       # for investigating any failures).    
+       # for investigating any failures).
        cat <<EOF >"$TMP_DIRECTORY/run_emacs"
 #!/bin/sh
 export PATH=$PATH
@@ -870,7 +897,7 @@ export NOTMUCH_CONFIG=$NOTMUCH_CONFIG
 #
 # --load               Force loading of notmuch.el and test-lib.el
 
-exec emacs --no-init-file --no-site-file \
+exec ${TEST_EMACS} --no-init-file --no-site-file \
        --directory "$TEST_DIRECTORY/../emacs" --load notmuch.el \
        --directory "$TEST_DIRECTORY" --load test-lib.el \
        "\$@"
@@ -879,6 +906,13 @@ EOF
 }
 
 test_emacs () {
+       # test dependencies beforehand to avoid the waiting loop below
+       missing_dependencies=
+       test_require_external_prereq dtach || missing_dependencies=1
+       test_require_external_prereq emacs || missing_dependencies=1
+       test_require_external_prereq emacsclient || missing_dependencies=1
+       test -z "$missing_dependencies" || return
+
        if [ -z "$EMACS_SERVER" ]; then
                server_name="notmuch-test-suite-$$"
                # start a detached session with an emacs server
@@ -892,7 +926,7 @@ test_emacs () {
                                --eval '(orphan-watchdog $$)'" || return
                EMACS_SERVER="$server_name"
                # wait until the emacs server is up
-               until test_emacs '()' 2>/dev/null; do
+               until test_emacs '()' >/dev/null 2>/dev/null; do
                        sleep 1
                done
        fi
@@ -900,11 +934,67 @@ test_emacs () {
        emacsclient --socket-name="$EMACS_SERVER" --eval "(progn $@)"
 }
 
+test_python() {
+       export LD_LIBRARY_PATH=$TEST_DIRECTORY/../lib
+       export PYTHONPATH=$TEST_DIRECTORY/../bindings/python
+
+       # Some distros (e.g. Arch Linux) ship Python 2.* as /usr/bin/python2,
+       # most others as /usr/bin/python. So first try python2, and fallback to
+       # python if python2 doesn't exist.
+       cmd=python2
+       [[ "$test_missing_external_prereq_python2_" = t ]] && cmd=python
+
+       (echo "import sys; _orig_stdout=sys.stdout; sys.stdout=open('OUTPUT', 'w')"; cat) \
+               | $cmd -
+}
+
+# Creates a script that counts how much time it is executed and calls
+# notmuch.  $notmuch_counter_command is set to the path to the
+# generated script.  Use notmuch_counter_value() function to get the
+# current counter value.
+notmuch_counter_reset () {
+       notmuch_counter_command="$TMP_DIRECTORY/notmuch_counter"
+       if [ ! -x "$notmuch_counter_command" ]; then
+               notmuch_counter_state_path="$TMP_DIRECTORY/notmuch_counter.state"
+               cat >"$notmuch_counter_command" <<EOF || return
+#!/bin/sh
+
+read count < "$notmuch_counter_state_path"
+echo \$((count + 1)) > "$notmuch_counter_state_path"
+
+exec notmuch "\$@"
+EOF
+               chmod +x "$notmuch_counter_command" || return
+       fi
+
+       echo 0 > "$notmuch_counter_state_path"
+}
+
+# Returns the current notmuch counter value.
+notmuch_counter_value () {
+       if [ -r "$notmuch_counter_state_path" ]; then
+               read count < "$notmuch_counter_state_path"
+       else
+               count=0
+       fi
+       echo $count
+}
+
 test_reset_state_ () {
+       test -z "$test_init_done_" && test_init_
+
        test_subtest_known_broken_=
        test_subtest_missing_external_prereqs_=
 }
 
+# called once before the first subtest
+test_init_ () {
+       test_init_done_=t
+
+       # skip all tests if there were external prerequisites missing during init
+       test_check_missing_external_prereqs_ "all tests in $this_test" && test_done
+}
+
 
 find_notmuch_path ()
 {
@@ -1112,3 +1202,12 @@ test -z "$NO_PYTHON" && test_set_prereq PYTHON
 # test whether the filesystem supports symbolic links
 ln -s x y 2>/dev/null && test -h y 2>/dev/null && test_set_prereq SYMLINKS
 rm -f y
+
+# declare prerequisites for external binaries used in tests
+test_declare_external_prereq dtach
+test_declare_external_prereq emacs
+test_declare_external_prereq emacsclient
+test_declare_external_prereq gdb
+test_declare_external_prereq gpg
+test_declare_external_prereq python
+test_declare_external_prereq python2