Small sh "framework" to test some server responses
sh
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

check.sh 8.7KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502
  1. #!/bin/sh
  2. alias echo="/bin/echo -e"
  3. color=1
  4. verbose=2
  5. exit_on_fail=0
  6. col_reset() {
  7. if [ "$color" -gt 0 ]
  8. then
  9. tput sgr0
  10. fi
  11. }
  12. col_set() {
  13. if [ -z "$1" ]
  14. then
  15. return
  16. fi
  17. if [ "$color" -gt 0 ]
  18. then
  19. tput setaf $1
  20. fi
  21. }
  22. log() {
  23. echo "$(col_set $3)[$(printf "%7s" "$1")]$(col_reset) $2"
  24. }
  25. datetime() {
  26. date -Iseconds
  27. }
  28. logdate() {
  29. echo "$(date -Iseconds) $(col_set $3)[$(printf "%7s" "$1")]$(col_reset) $2"
  30. }
  31. fail() {
  32. if [ "$verbose" -lt 2 ]
  33. then
  34. echo "" #for the dot printed with -n
  35. fi
  36. test_msg="$1"
  37. test_status=1
  38. }
  39. err() {
  40. msg="$(log ERR "$1" 1)"
  41. test_msg="$1"
  42. test_status=-1
  43. }
  44. success() {
  45. msg="$(log OK "$1" 2)"
  46. test_msg="$1"
  47. test_status=0
  48. }
  49. #
  50. # Tests & testcase functions
  51. #
  52. tc_name=""
  53. tc_infos=""
  54. tc_fail=0
  55. tc_run=0
  56. total_fail=0
  57. total_run=0
  58. test_msg=""
  59. test_status=0
  60. _test_setup() {
  61. test_status=0
  62. test_msg=""
  63. }
  64. TC_INIT() {
  65. tc_name=$1
  66. tc_infos=$2
  67. tc_fail=0
  68. tc_run=0
  69. msg="Running testcase '$tc_name'"
  70. if [ -n "$tc_infos" ]
  71. then
  72. msg="${msg} ($tc_infos)"
  73. fi
  74. if [ "$verbose" -gt 0 ]
  75. then
  76. logdate TESTCASE "$msg" 4
  77. fi
  78. }
  79. TC_END() {
  80. if [ "$tc_fail" -gt 0 ]
  81. then
  82. if [ "$verbose" -gt 1 ]
  83. then
  84. logdate TESTCASE "-------------$tc_name END------------" 1
  85. fi
  86. logdate FAIL "Testcase '$tc_name' tests: ${tc_run} fails: $(col_set 1)${tc_fail}$(col_reset)" 1
  87. if [ "$exit_on_fail" -ne 0 ]
  88. then
  89. CHECK_REPORT
  90. fi
  91. elif [ "$verbose" -eq 1 ]
  92. then
  93. echo "" #for the dot printed with -n
  94. logdate TESTCASE "Testcase '$tc_name' tests:${tc_run} fails: $tc_fail" 2
  95. elif [ "$verbose" -gt 1 ]
  96. then
  97. logdate TESTCASE "-------------$tc_name END------------" 4
  98. fi
  99. tc_name=""
  100. tc_infos=""
  101. tc_fail=0
  102. tc_run=0
  103. }
  104. TC_RUN() {
  105. _test_setup
  106. cmd=$1
  107. shift
  108. args=""
  109. case $#
  110. in
  111. 1)$cmd "$1";;
  112. 2)$cmd "$1" "$2";;
  113. 3)$cmd "$1" "$2" "$3";;
  114. 4)$cmd "$1" "$2" "$3" "$4";;
  115. *)fail "To many arguments for $cmd"
  116. esac
  117. #$cmd $args
  118. tc_run=$(expr $tc_run + 1)
  119. total_run=$(expr $total_run + 1)
  120. if [ "$test_status" -ne 0 ]
  121. then
  122. err_type="FAIL"
  123. if [ "$test_status" -lt 0 ]
  124. then
  125. err_type="ERR"
  126. fi
  127. tc_fail=$(expr $tc_fail + 1)
  128. total_fail=$(expr $total_fail + 1)
  129. logdate $err_type "$tc_name: $test_msg" 1 >&2
  130. elif [ "$verbose" -gt 1 ]
  131. then
  132. logdate OK "$tc_name: $test_msg" 2
  133. else
  134. echo -n '.'
  135. fi
  136. }
  137. CHECK_START() {
  138. logdate STATUS "Starting tests" 3
  139. }
  140. CHECK_REPORT() {
  141. if [ "$verbose" -eq 0 -a "$tc_fail" -eq "0" ]
  142. then
  143. echo "" # for dot printed with -n
  144. fi
  145. if [ "$verbose" -gt 0 ]
  146. then
  147. logdate STATUS "All tests done" 3
  148. fi
  149. if [ "$total_fail" -gt 0 ]
  150. then
  151. logdate FAIL "Summary : tests: ${total_run} fails: $(col_set 1)${total_fail}$(col_reset)" 1
  152. exit 1
  153. else
  154. logdate OK "Summary : tests:${total_run} fails: $total_fail" 2
  155. exit 0
  156. fi
  157. }
  158. #
  159. # HTTP/HTTPS tests
  160. #
  161. _check_http_status() {
  162. # $1 url
  163. # $2 status
  164. # $* curl options
  165. url=$1
  166. shift 1
  167. expt=$1
  168. if [ -z "$1" ]
  169. then
  170. expt=200
  171. fi
  172. shift 1
  173. status=$(curl -s -o /dev/null -w "%{http_code}" $* $url)
  174. if [ "$status" -ne "$expt" ]
  175. then
  176. fail "Check http status $expt for $url : $status returned"
  177. elif [ "$verbose" -gt 0 ]
  178. then
  179. success "Check http status $status for $url"
  180. fi
  181. }
  182. check_http_status() {
  183. # $1 url
  184. # $2 status
  185. _check_http_status http://$1 $2
  186. }
  187. check_http_200() {
  188. _check_http_status http://$1 200
  189. }
  190. check_https_status() {
  191. # $1 url
  192. # $2 status
  193. _check_http_status https://$1 $2
  194. }
  195. check_https_200() {
  196. _check_http_status https://$1 200
  197. }
  198. check_https_cert() {
  199. # Check that SSL Cert is valid
  200. # $1 URL
  201. status=$(curl -s -o /dev/null -w "%{http_code}" https://$1)
  202. rep=$?
  203. if [ "$rep" -eq 0 ]
  204. then
  205. success "https://$1 cert verified"
  206. return
  207. fi
  208. status=$(curl -k -s -o /dev/null -q "%{http_code}" https://$1)
  209. rep=$?
  210. if [ "$rep" -eq 0 ]
  211. then
  212. fail "https://$1 cert invalid"
  213. else
  214. err "Unable to curl https://$1"
  215. fi
  216. }
  217. check_html_title() {
  218. url="$1"
  219. expt="$2"
  220. tmpxsl=$(mktemp -t XSL.XXXXXXXXXXX)
  221. echo '<?xml version="1.0"?>
  222. <xsl:stylesheet version="1.0"
  223. xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  224. <xsl:output method = "text"/>
  225. <xsl:template match="/">
  226. <xsl:value-of select="/html/head/title"/>
  227. </xsl:template>
  228. </xsl:stylesheet>' > $tmpxsl
  229. tmphtml=$(mktemp -t html.XXXXXXXXX)
  230. curl --silent $url > $tmphtml
  231. title=$(xsltproc --html --novalid $tmpxsl $tmphtml 2>/dev/null)
  232. if [ "$?" -ne "0" ]
  233. then
  234. title=$(xsltproc --novalid $tmpxsl $tmphtml 2>/dev/null)
  235. fi
  236. if [ "$title" = "$expt" ]
  237. then
  238. success "$url HTML title is '$expt'"
  239. else
  240. fail "$url HTML title is '$title' but '$expt' expected"
  241. fi
  242. rm $tmpxsl $tmphtml 2>/dev/null
  243. }
  244. check_audiostream() {
  245. # Uses mplayer to fetch 128Kb of stream
  246. # $1 Stream URL
  247. tmpfile=$(mktemp -t check_audiostream.XXXXXXXXX)
  248. sz="128kb"
  249. if [ "$verbose" -gt 1 ]
  250. then
  251. logdate INFO "$tc_name: Running mplayer on '$1' for $sz" 3
  252. fi
  253. mplayer -endpos $sz -ao pcm:file=$tmpfile "$1" 1>/dev/null 2>/dev/null
  254. res=$?
  255. bytes=$(du $tmpfile | cut -f1)
  256. rm $tmpfile 2>/dev/null
  257. if [ "$bytes" -lt 1024 ]
  258. then
  259. fail "mplayer retrieved ${bytes}B of stream instead of expected $sz"
  260. return
  261. fi
  262. if [ "$res" -eq 0 ]
  263. then
  264. success "mplayer retrieved $sz of stream on $1"
  265. else
  266. fail "mplayer failed to retrieve stream on $1"
  267. fi
  268. }
  269. check_ping() {
  270. ns=$1
  271. count=$2
  272. if [ -z "$count" ]
  273. then
  274. count=5
  275. fi
  276. ping -i 0.2 -c $count $ns 2>/dev/null >/dev/null
  277. res=$?
  278. if [ "$res" -ne 0 ]
  279. then
  280. fail "unable to ping '$ns'"
  281. else
  282. success "successfully send $count ping to '$ns'"
  283. fi
  284. }
  285. check_git_repo() {
  286. tmpdir=$(mktemp -d -t check_git.XXXXXXXXX)
  287. git clone $1 $tmpdir 2>/dev/null 1>/dev/null
  288. res=$?
  289. rm -Rf $tmpdir
  290. if [ "$res" -ne 0 ]
  291. then
  292. fail "unable to clone git repo '$1'"
  293. else
  294. success "git repo '$1' cloned'"
  295. fi
  296. }
  297. #
  298. # Jabber XMPP checks
  299. #
  300. __xmpp_probe() {
  301. serv=$1
  302. timeout=$2
  303. type=$3
  304. payload="<?xml version=\"1.0\"?>\n<stream:stream xmlns:stream=\"http://etherx.jabber.org/streams\" version=\"1.0\" xmlns=\"jabber:$type\" to=\"${1}\" xml:lang=\"en\" xmlns:xml=\"http://www.w3.org/XML/1998/namespace\">\n"
  305. if [ "$verbose" -gt 2 ]
  306. then
  307. echo -e $payload | sed -e "s/^/$(datetime) [ DEBUG] Sent : /" >&2
  308. fi
  309. echo -e $payload
  310. sleep $timeout
  311. }
  312. _xmpp_probe() {
  313. serv=$1
  314. port=$2
  315. timeout=$3
  316. type=$4
  317. tmpres=$(mktemp -t xmpp_probe.XXXXXXXXX)
  318. echo "$(__xmpp_probe $serv $timeout $type| nc -q2 $serv $port)</stream:stream>" | xmllint --format - > $tmpres
  319. if [ "$verbose" -gt 2 ]
  320. then
  321. cat $tmpres | sed -e "s/^/$(datetime) [ DEBUG] Recv : /" >&2
  322. fi
  323. cat $tmpres
  324. rm $tmpres
  325. }
  326. _check_xmpp_ns() {
  327. ns1=$1
  328. expt_ns=$2
  329. expt_port=$3
  330. dnsq="_xmpp-${4}._tcp.$1"
  331. rep="$(dig $dnsq srv +short | cut -d" " -f3,4)"
  332. if [ "$rep" = "$expt_port ${expt_ns}." ]
  333. then
  334. success "$dnsq = '$rep'"
  335. else
  336. fail "$dnsq = '$rep' but '$expt_port ${expt_ns}.' expected"
  337. fi
  338. }
  339. check_xmpp_serv_ns() {
  340. _check_xmpp_ns "$1" "$2" "$3" "server"
  341. }
  342. check_xmpp_client_ns() {
  343. _check_xmpp_ns "$1" "$2" "$3" "client"
  344. }
  345. _check_xmpp_server() {
  346. serv=$1
  347. port=$2
  348. timeout=$3
  349. type=$4
  350. if [ -z "$port" ]
  351. then
  352. port=5222
  353. fi
  354. if [ -z "$timeout" ]
  355. then
  356. timeout=2
  357. fi
  358. if [ "$verbose" -gt 1 ]
  359. then
  360. tpe="client"
  361. if [ "$type" = "server" ]
  362. then
  363. tpe="S2S"
  364. fi
  365. logdate INFO "$tc_name: Connecting to XMPP $serv $tpe port $port (timeout=${timeout}s)" 3
  366. fi
  367. stream=$(_xmpp_probe $serv $port $timeout $type| head -n2 | tail -n1)
  368. if [ -z "$stream" ]
  369. then
  370. fail "Empty reply from $serv:$port"
  371. return
  372. fi
  373. if [ "$type" = "client" ]
  374. then
  375. infos=$(echo $stream | sed -E 's/^<([^ ]+).* xmlns="([^"]+)".* from="([^"]+)" .*$/\1 \2 \3/')
  376. else
  377. infos="$(echo $stream | sed -E 's/^<([^ ]+).* xmlns="([^"]+)" .*$/\1 \2/') $serv"
  378. fi
  379. if [ "$(echo $infos | cut -d ' ' -f1,2)" = "stream:stream jabber:$type" ]
  380. then
  381. if [ "$(echo $infos | cut -d ' ' -f3)" = "$serv" ]
  382. then
  383. success "Successfully connected to XMPP $type $serv:$port"
  384. else
  385. fail "Server $serv:$port announce itself as $(echo $infos | cut -f3)"
  386. fi
  387. else
  388. fail "Unexpected reply from $serv:$port : $infos"
  389. fi
  390. }
  391. check_xmpp_server_client() {
  392. _check_xmpp_server "$1" "$2" "$3" "client"
  393. }
  394. check_xmpp_server_s2s() {
  395. _check_xmpp_server "$1" "$2" "$3" "server"
  396. }
  397. check_xmpp_ssl() {
  398. serv=$1
  399. port=$2
  400. if [ -z "$port" ]
  401. then
  402. port=5222
  403. fi
  404. openssl s_client -connect $serv:$port </dev/null -starttls xmpp >/dev/null 2>/dev/null
  405. rep=$?
  406. if [ "$rep" -eq 0 ]
  407. then
  408. success "Openssl successfully negociating XMPP ssl with $serv:$port"
  409. else
  410. fail "Openssl failed negociating XMPP ssl with $serv:$port"
  411. fi
  412. }
  413. #
  414. # SSH checks
  415. #
  416. check_ssh_nc() {
  417. host=$1
  418. port=$2
  419. if [ -z "$port" ]
  420. then
  421. port=22
  422. fi
  423. rep="$(nc -q1 z3.zered.net $port </dev/null)"
  424. res=$?
  425. if [ "$res" -ne "0" ]
  426. then
  427. fail "Netcat unable to connect to $host:$port"
  428. return
  429. fi
  430. if echo $rep | grep "^SSH-2.0-OpenSSH" >/dev/null
  431. then
  432. success "OpenSSH replied on $host:$port"
  433. else
  434. fail "Bad replie from $host:$port : '$rep'"
  435. fi
  436. }