2013-04-04 03:32:26 +02:00

145 lines
3.2 KiB
Bash
Executable File

#!/usr/bin/env bash
# Usage: script/test [file] [adapter]... -- [test/unit options]
# Runs the test suite against a local server spawned automatically in a
# thread. After tests are done, the server is shut down.
#
# If filename arguments are given, only those files are run. If arguments given
# are not filenames, they are taken as words that filter the list of files to run.
#
# Examples:
#
# $ script/test
# $ script/test test/env_test.rb
# $ script/test excon typhoeus
#
# # Run only tests matching /ssl/ for the net_http adapter, with SSL enabled.
# $ SSL=yes script/test net_http -- -n /ssl/
#
# # Run against multiple rbenv versions
# $ RBENV_VERSIONS="1.9.3-p194 ree-1.8.7-2012.02" script/test
set -e
if [[ "$RUBYOPT" != *"bundler/setup"* ]]; then
export RUBYOPT="-rbundler/setup $RUBYOPT"
fi
port=3999
scheme=http
if [ "$SSL" = "yes" ]; then
scheme=https
if [ -z "$SSL_KEY" ] || [ -z "$SSL_FILE" ]; then
eval "$(script/generate_certs -s)"
fi
fi
find_test_files() {
find "$1" -name '*_test.rb'
}
filter_matching() {
pattern="$1"
shift
for line in "$@"; do
[[ $line == *"$pattern"* ]] && echo "$line"
done
}
start_server() {
mkdir -p log
script/server -p $port >log/server.log 2>&1 &
echo $!
}
server_started() {
lsof -i :$port >/dev/null
}
timestamp() {
date +%s
}
wait_for_server() {
timeout=$(( `timestamp` + $1 ))
while true; do
if server_started; then
break
elif [ `timestamp` -gt "$timeout" ]; then
echo "timed out after $1 seconds" >&2
return 1
fi
done
}
filtered=
IFS=$'\n' test_files=($(find_test_files "test"))
declare -a explicit_files
# Process filter arguments:
# - test filenames as taken as-is
# - other words are taken as pattern to match the list of known files against
# - arguments after "--" are forwarded to the ruby process
while [ $# -gt 0 ]; do
arg="$1"
shift
if [ "$arg" = "--" ]; then
break
elif [ -f "$arg" ]; then
filtered=true
explicit_files[${#explicit_files[@]}+1]="$arg"
else
filtered=true
IFS=$'\n' explicit_files=(
${explicit_files[@]}
$(filter_matching "$arg" "${test_files[@]}" || true)
)
fi
done
# If there were filter args, replace test files list with the results
if [ -n "$filtered" ]; then
if [ ${#explicit_files[@]} -eq 0 ]; then
echo "Error: no test files match" >&2
exit 1
else
test_files=(${explicit_files[@]})
echo running "${test_files[@]}"
fi
fi
# If there are any adapter tests, spin up the HTTP server
if [ -n "$(filter_matching "adapters" "${test_files[@]}")" ]; then
if server_started; then
echo "aborted: another instance of server running on $port" >&2
exit 1
fi
server_pid=$(start_server)
wait_for_server 15 || {
cat log/server.log
exit 1
}
cleanup() {
if [ $? -ne 0 ] && [ -n "$TRAVIS" ]; then
cat log/test.log
fi
kill "$server_pid"
}
trap cleanup INT EXIT
export LIVE="${scheme}://localhost:${port}"
fi
run_test_files() {
ruby -e 'while f=ARGV.shift and f!="--"; load f; end' "${test_files[@]}" -- "$@"
}
if [ -n "$RBENV_VERSIONS" ]; then
IFS=' ' versions=($RBENV_VERSIONS)
for version in "${versions[@]}"; do
echo "[${version}]"
RBENV_VERSION="$version" run_test_files "$@"
done
else
run_test_files "$@"
fi