summaryrefslogtreecommitdiffstats
path: root/cucumber/bin/run_test_suite
diff options
context:
space:
mode:
Diffstat (limited to 'cucumber/bin/run_test_suite')
-rwxr-xr-xcucumber/bin/run_test_suite276
1 files changed, 276 insertions, 0 deletions
diff --git a/cucumber/bin/run_test_suite b/cucumber/bin/run_test_suite
new file mode 100755
index 00000000..5b40c389
--- /dev/null
+++ b/cucumber/bin/run_test_suite
@@ -0,0 +1,276 @@
+#!/bin/bash
+
+set -e
+set -u
+set -o pipefail
+
+NAME=$(basename ${0})
+
+GENERAL_DEPENDENCIES="
+cucumber
+devscripts
+dnsmasq-base
+gawk
+git
+i18nspector
+libav-tools
+libcap2-bin
+libsikuli-script-java
+libvirt-clients
+libvirt-daemon-system
+libvirt-dev
+libvirt0
+openjdk-7-jre
+openssh-server
+ovmf
+python-jabberbot
+python-potr
+qemu-kvm
+qemu-system-x86
+ruby-guestfs
+ruby-json
+ruby-libvirt
+ruby-net-irc
+ruby-packetfu
+ruby-rb-inotify
+ruby-rjb
+ruby-rspec
+ruby-test-unit
+seabios
+tcpdump
+unclutter
+virt-viewer
+xvfb
+"
+
+usage() {
+ echo "Usage: $NAME [OPTION]... [--] [CUCUMBER_ARGS]...
+Sets up an appropriate environment and invokes cucumber. Note that this script
+must be run from the Tails source directory root.
+
+Options for '@product' features:
+ --artifacts-base-uri URI
+ Pretend that the artifact is located at URI when printing
+ its location during a scenario failure. This is useful if
+ you intend to serve the artifacts via the web, for
+ instance.
+ --capture Captures failed scenarios into videos stored in the
+ temporary directory (see --tmpdir below) using x264
+ encoding. Requires x264.
+ --capture-all Keep videos for all scenarios, including those that
+ succeed (implies --capture).
+ --pause-on-fail On failure, pause test suite until pressing Enter. This is
+ useful for investigating the state of the VM guest to see
+ exactly why a test failed.
+ --keep-snapshots Don't ever delete any snapshots (including ones marked as
+ temporary). This can be a big time saver when debugging new
+ features.
+ --retry-find Print a warning whenever Sikuli fails to find an image
+ and allow *one* retry after pressing ENTER. This is useful
+ for updating outdated images.
+ --tmpdir Directory where various temporary files are written
+ during a test, e.g. VM snapshots and memory dumps,
+ failure screenshots, pcap files and disk images
+ (default is TMPDIR in the environment, and if unset,
+ /tmp/DebianToaster).
+ --view Shows the test session in a windows. Requires x11vnc
+ and xtightvncviewer.
+ --vnc-server-only Starts a VNC server for the test session. Requires x11vnc.
+ --iso IMAGE Test '@product' features using IMAGE.
+ --old-iso IMAGE For some '@product' features (e.g. usb_install) we need
+ an older version of Tails, which this options sets to
+ IMAGE. If none is given, it defaults to the same IMAGE
+ given by --iso, which will be good enough for most testing
+ purposes.
+
+Note that '@source' features has no relevant options.
+
+CUCUMBER_ARGS can be used to specify which features to be run, but also any
+cucumber option, although then you must pass \`--\` first to let this wrapper
+script know that we're done with *its* options. For debugging purposes, a
+'debug' formatter has been added so pretty debugging can be enabled with
+\`--format debug\`. You could even combine the default (pretty) formatter with
+pretty debugging printed to a file with \`--format pretty --format debug
+--out debug.log\`.
+"
+}
+
+error() {
+ echo "${NAME}: error: ${*}" >&2
+ usage
+ exit 1
+}
+
+package_installed() {
+ local ret
+ set +o pipefail
+ if dpkg -s "${1}" 2>/dev/null | grep -q "^Status:.*installed"; then
+ ret=0
+ else
+ ret=1
+ fi
+ set -o pipefail
+ return ${ret}
+}
+
+check_dependencies() {
+ while [ -n "${1:-}" ]; do
+ if ! which "${1}" >/dev/null && ! package_installed "${1}" ; then
+ error "'${1}' is missing, please install it and run again."
+ fi
+ shift
+ done
+}
+
+display_in_use() {
+ [ -e "/tmp/.X${1#:}-lock" ] || [ -e "/tmp/.X11-unix/X${1#:}" ]
+}
+
+next_free_display() {
+ display_nr=0
+ while display_in_use ":${display_nr}"; do
+ display_nr=$((display_nr+1))
+ done
+ echo ":${display_nr}"
+}
+
+test_suite_cleanup() {
+ (kill -0 ${XVFB_PID} 2>/dev/null && kill ${XVFB_PID}) || /bin/true
+}
+
+start_xvfb() {
+ Xvfb $TARGET_DISPLAY -screen 0 1024x768x24+32 >/dev/null 2>&1 &
+ XVFB_PID=$!
+ # Wait for Xvfb to run on TARGET_DISPLAY
+ until display_in_use $TARGET_DISPLAY; do
+ sleep 1
+ done
+ echo "Virtual X framebuffer started on display ${TARGET_DISPLAY}"
+ # Hide the mouse cursor so it won't mess up Sikuli's screen scanning
+ unclutter -display $TARGET_DISPLAY -root -idle 0 >/dev/null 2>&1 &
+}
+
+start_vnc_server() {
+ check_dependencies x11vnc
+ VNC_SERVER_PORT="$(x11vnc -listen localhost -display ${TARGET_DISPLAY} \
+ -bg -nopw -forever 2>&1 | \
+ grep -m 1 "^PORT=[0-9]\+" | sed 's/^PORT=//')"
+ echo "VNC server running on: localhost:${VNC_SERVER_PORT}"
+}
+
+start_vnc_viewer() {
+ check_dependencies xtightvncviewer
+ xtightvncviewer -viewonly localhost:${VNC_SERVER_PORT} 1>/dev/null 2>&1 &
+}
+
+capture_session() {
+ check_dependencies libvpx1
+ echo "Capturing guest display into ${CAPTURE_FILE}"
+ avconv -f x11grab -s 1024x768 -r 15 -i ${TARGET_DISPLAY}.0 -an \
+ -vcodec libvpx -y "${CAPTURE_FILE}" >/dev/null 2>&1 &
+}
+
+# main script
+
+# Unset all environment variables used by this script to pass options
+# to cucumber, except TMPDIR since we explicitly want to support
+# setting it that way.
+ARTIFACTS_BASE_URI=
+CAPTURE=
+CAPTURE_ALL=
+LOG_FILE=
+VNC_VIEWER=
+VNC_SERVER=
+PAUSE_ON_FAIL=
+KEEP_SNAPSHOTS=
+SIKULI_RETRY_FINDFAILED=
+ISO=
+OLD_ISO=
+
+LONGOPTS="artifacts-base-uri:,view,vnc-server-only,capture,capture-all,help,tmpdir:,keep-snapshots,retry-find,iso:,old-iso:,pause-on-fail"
+OPTS=$(getopt -o "" --longoptions $LONGOPTS -n "${NAME}" -- "$@")
+eval set -- "$OPTS"
+while [ $# -gt 0 ]; do
+ case $1 in
+ --artifacts-base-uri)
+ shift
+ export ARTIFACTS_BASE_URI="${1}"
+ ;;
+ --view)
+ VNC_VIEWER=yes
+ VNC_SERVER=yes
+ ;;
+ --vnc-server-only)
+ VNC_VIEWER=
+ VNC_SERVER=yes
+ ;;
+ --capture)
+ check_dependencies x264
+ export CAPTURE="yes"
+ ;;
+ --capture-all)
+ check_dependencies x264
+ export CAPTURE="yes"
+ export CAPTURE_ALL="yes"
+ ;;
+ --pause-on-fail)
+ export PAUSE_ON_FAIL="yes"
+ ;;
+ --keep-snapshots)
+ export KEEP_SNAPSHOTS="yes"
+ ;;
+ --retry-find)
+ export SIKULI_RETRY_FINDFAILED="yes"
+ ;;
+ --tmpdir)
+ shift
+ export TMPDIR="$(readlink -f $1)"
+ ;;
+ --iso)
+ shift
+ export ISO="$(readlink -f $1)"
+ ;;
+ --old-iso)
+ shift
+ export OLD_ISO="$(readlink -f $1)"
+ ;;
+ --help)
+ usage
+ exit 0
+ ;;
+ --)
+ shift
+ break
+ ;;
+ esac
+ shift
+done
+
+trap "test_suite_cleanup" EXIT HUP INT QUIT TERM
+
+check_dependencies ${GENERAL_DEPENDENCIES}
+
+TARGET_DISPLAY=$(next_free_display)
+
+start_xvfb
+
+if [ -n "${VNC_SERVER:-}" ]; then
+ start_vnc_server
+fi
+if [ -n "${VNC_VIEWER:-}" ]; then
+ start_vnc_viewer
+fi
+
+export SIKULI_HOME="/usr/share/java"
+export SIKULI_IMAGE_PATH="/srv/jenkins/features/images/"
+export RUBYLIB="/srv/jenkins"
+export VM_XML_PATH="/srv/jenkins/features/domains"
+export DISPLAY=${TARGET_DISPLAY}
+check_dependencies cucumber
+
+# cludge ruby to stop buffering output
+RUBY_STDOUT_SYNC=$TMPDIR/.stdout-sync.rb
+echo STDOUT.sync = true > $RUBY_STDOUT_SYNC
+export RUBYOPT="-r $RUBY_STDOUT_SYNC"
+
+cucumber ${@}