tests: "wc -c" portability for *BSDs
[rainbows.git] / t / test-lib.sh
blob26709bc74b18fbd7ec0bb3a3d519b0ccf0f192c2
1 #!/bin/sh
2 # Copyright (c) 2009 Rainbows! developers
3 . ./my-tap-lib.sh
5 set +u
7 # sometimes we rely on http_proxy to avoid wasting bandwidth with Isolate
8 # and multiple Ruby versions
9 NO_PROXY=${UNICORN_TEST_ADDR-127.0.0.1}
10 export NO_PROXY
12 if test -z "$model"
13 then
14 # defaulting to Base would unfortunately fail some concurrency tests
15 model=ThreadSpawn
16 t_info "model undefined, defaulting to $model"
19 set -e
20 RUBY="${RUBY-ruby}"
21 RUBY_VERSION=${RUBY_VERSION-$($RUBY -e 'puts RUBY_VERSION')}
22 t_pfx=$PWD/trash/$model.$T-$RUBY_ENGINE-$RUBY_VERSION
23 set -u
25 PATH=$PWD/bin:$PATH
26 export PATH
28 test -x $PWD/bin/unused_listen || die "must be run in 't' directory"
30 # requires $1 and prints out the value of $2
31 require_check () {
32 lib=$1
33 const=$2
34 if ! $RUBY -r$lib -e "puts $const" >/dev/null 2>&1
35 then
36 t_info "skipping $T since we don't have $lib"
37 exit 0
41 # "date +%s" is not in POSIX, but in GNU, and FreeBSD 9.0 (possibly earlier)
42 unix_time () {
43 $RUBY -e 'puts Time.now.to_i'
46 # "wc -c" outputs leading whitespace on *BSDs, filter it out for portability
47 count_bytes () {
48 wc -c | tr -d '[:space:]'
51 skip_models () {
52 for i in "$@"
54 if test x"$model" != x"$i"
55 then
56 continue
58 t_info "skipping $T since it is not compatible with $model"
59 exit 0
60 done
64 # given a list of variable names, create temporary files and assign
65 # the pathnames to those variables
66 rtmpfiles () {
67 for id in "$@"
69 name=$id
70 _tmp=$t_pfx.$id
71 eval "$id=$_tmp"
73 case $name in
74 *fifo)
75 rm -f $_tmp
76 mkfifo $_tmp
77 T_RM_LIST="$T_RM_LIST $_tmp"
79 *socket)
80 rm -f $_tmp
81 T_RM_LIST="$T_RM_LIST $_tmp"
84 > $_tmp
85 T_OK_RM_LIST="$T_OK_RM_LIST $_tmp"
87 esac
88 done
91 dbgcat () {
92 id=$1
93 eval '_file=$'$id
94 echo "==> $id <=="
95 sed -e "s/^/$id:/" < $_file
98 check_stderr () {
99 set +u
100 _r_err=${1-${r_err}}
101 set -u
102 if grep -i Error $_r_err
103 then
104 die "Errors found in $_r_err"
105 elif grep SIGKILL $_r_err
106 then
107 die "SIGKILL found in $_r_err"
111 # rainbows_setup [ MODEL [ WORKER_CONNECTIONS ] ]
112 rainbows_setup () {
113 eval $(unused_listen)
114 rtmpfiles unicorn_config pid r_err r_out fifo tmp ok
115 cat > $unicorn_config <<EOF
116 listen "$listen"
117 pid "$pid"
118 stderr_path "$r_err"
119 stdout_path "$r_out"
121 after_fork do |server, worker|
122 # test script will block while reading from $fifo,
123 # so notify the script on the first worker we spawn
124 # by opening the FIFO
125 if worker.nr == 0
126 File.open("$fifo", "wb") { |fp| fp.syswrite "START" }
131 # set a higher default for tests since we run heavily-loaded
132 # boxes and sometimes sleep 1s in tests
133 kato=5
134 echo 'Rainbows! do'
135 echo " client_max_body_size nil"
136 if test $# -ge 1
137 then
138 echo " use :$1"
139 test $# -ge 2 && echo " worker_connections $2"
140 if test $# -eq 3
141 then
142 echo " keepalive_timeout $3"
143 else
144 echo " keepalive_timeout $kato"
146 else
147 echo " use :$model"
148 echo " keepalive_timeout $kato"
150 echo end
151 } >> $unicorn_config
154 rainbows_wait_start () {
155 # "cat $fifo" will block until the before_fork hook is called in
156 # the Unicorn config file
157 test xSTART = x"$(cat $fifo)"
158 rainbows_pid=$(cat $pid)
161 wait_for_reload () {
162 case $# in
163 0) err_log=$r_err status=done ;;
164 1) err_log=$1 status=done ;;
165 2) err_log=$1 status=$2 ;;
166 esac
167 while ! egrep '(done|error) reloading' < $err_log >/dev/null
169 sleep 1
170 done
171 grep "$status reloading" $err_log >/dev/null
174 wait_for_reap () {
175 case $# in
176 0) err_log=$r_err ;;
177 1) err_log=$1 ;;
178 esac
180 while ! grep reaped < $err_log >/dev/null
182 sleep 1
183 done
186 rsha1 () {
187 _cmd="$(which sha1sum 2>/dev/null || :)"
188 test -n "$_cmd" || _cmd="$(which openssl 2>/dev/null || :) sha1"
189 test "$_cmd" != " sha1" || _cmd="$(which gsha1sum 2>/dev/null || :)"
191 # last resort, see comments in sha1sum.rb for reasoning
192 test -n "$_cmd" || _cmd=sha1sum.rb
193 expr "$($_cmd)" : '\([a-f0-9]\{40\}\)'
196 req_curl_chunked_upload_err_check () {
197 set +e
198 curl --version 2>/dev/null | awk '$1 == "curl" {
199 split($2, v, /\./)
200 if ((v[1] < 7) || (v[1] == 7 && v[2] < 18))
201 code = 1
203 END { exit(code) }'
204 if test $? -ne 0
205 then
206 t_info "curl >= 7.18.0 required for $T"
207 exit 0
211 check_splice () {
212 case $(uname -s) in
213 Linux) ;;
215 t_info "skipping $T since it's not Linux"
216 exit 0
218 esac
220 # we only allow splice on 2.6.32+
221 min=32 uname_r=$(uname -r)
222 case $uname_r in
223 2.6.*)
224 sub=$(expr "$uname_r" : '2\.6\.\(.*\)$')
225 if test $sub -lt $min
226 then
227 t_info "skipping $T (Linux $(uname_r < 2.6.$min)"
228 exit 0
231 [3-9].*)
232 # OK
235 t_info "skipping $T (Linux $uname_r < 2.6.$min)"
236 exit 0
238 esac
241 check_threaded_app_dispatch () {
242 case $model in
243 ThreadSpawn|ThreadPool) ;;
244 RevThreadSpawn|RevThreadPool) ;;
245 CoolioThreadSpawn|CoolioThreadPool) ;;
246 XEpollThreadSpawn|XEpollThreadPool) ;;
248 t_info "$0 is only compatible with threaded app dispatch"
249 exit 0 ;;
250 esac
253 check_copy_stream () {
254 case $RUBY_VERSION in
255 1.9.*) ;;
257 t_info "skipping $T since it can't IO.copy_stream"
258 exit 0
260 esac
262 case $model in
263 ThreadSpawn|WriterThreadSpawn|ThreadPool|WriterThreadPool|Base) ;;
264 XEpollThreadSpawn|XEpollThreadPool) ;;
266 t_info "skipping $T since it doesn't use copy_stream"
267 exit 0
269 esac
272 case $model in
273 Rev) require_check rev Rev::VERSION ;;
274 Coolio) require_check coolio Coolio::VERSION ;;
275 Revactor) require_check revactor Revactor::VERSION ;;
276 EventMachine) require_check eventmachine EventMachine::VERSION ;;
277 esac