#! /bin/sh
# PCP QA Test No. 660
# checks basic pmwebd functionality
#
# Copyright (c) 2013-2014 Red Hat, Inc.  All Rights Reserved.
#
seq=`basename $0`
echo "QA output created by $seq"

# get standard environment, filters and checks
. ./common.product
. ./common.filter
. ./common.check

which curl >/dev/null 2>&1 || _notrun "No curl binary installed"
echo curl ok
# nb: wget dispreferred because of its processing of .. relative links,
# so it's harder to stress pmwebd's base-directory-escaping logic

pyscript=src/test_webapi.python
python $pyscript --version 2>/dev/null || _notrun "python/modules missing"
echo python ok

$sudo rm -fr $tmp.dir
$sudo rm -f $tmp.*
rm -f $seq.full

signal=$PCP_BINADM_DIR/pmsignal
status=1	# failure is the default!
username=`id -u -n`
trap "_cleanup" 0 1 2 3 15

_cleanup()
{
    $sudo rm -fr $tmp.dir
    $sudo rm -f $tmp.*
    $sudo $signal -a pmwebd >/dev/null 2>&1
    $sudo $PCP_RC_DIR/pmwebd restart >/dev/null 2>&1
    exit $status
}

_filter()
{
    tee -a $seq.full \
        | sed -e 's,#[0-9]*,####,g' \
        | sed -e 's/PMWEBD error, .*/PMWEBD error, XXX/g'
}


unset http_proxy
unset HTTP_PROXY

$sudo $PCP_RC_DIR/pmwebd stop >/dev/null 2>&1
$sudo $signal -a pmwebd >/dev/null 2>&1

webargs="-U $username"

echo | tee -a $seq.full
echo "=== 1. pmwebd default startup  ===" | tee -a $seq.full
$PCP_BINADM_DIR/pmwebd $webargs -l $tmp.out -v -t10 &
echo "pid=$!" >>$seq.full
sleep 2		# let it start up

if [ -f $tmp.out ]
then
    cat $tmp.out >>$seq.full
else
    echo "Arrgh ... pmwebd failed to start, $tmp.out not created"
    $PCP_PS_PROG $PCP_PS_ALL_FLAGS | egrep '[P]ID|[p]mwebd'
    exit
fi
curl -s -S "http://localhost:44323/pmapi/context?local=ANYTHING" \
| tee -a $seq.full \
| awk '{print $2}'
echo >>$seq.full

if [ ! -f /etc/hosts ]
then
    echo "Arrgh ... cannot find /etc/hosts to determine IPv6 localhost name"
    exit
fi
ipv6local=''
for sniff in localhost6 ip6-localhost
do
    if sed -e '/^#/d' -e 's/$/ /' /etc/hosts | grep -q "[ 	]$sniff "
    then
	ipv6local=$sniff
	break
    fi
done
if [ -z "$ipv6local" ]
then
    echo "Arrgh ... cannot determine IPv6 localhost name from /etc/hosts"
    exit
fi
echo "ipv6local=$ipv6local" >>$seq.full

rm -f $seq.out
if grep -q IPv6 $tmp.out; then
    curl -s -S "http://$ipv6local:44323/pmapi/context?local=ANYTHING" \
    | tee -a $seq.full \
    | awk '{print $2}'
    echo >>$seq.full
    # ipv6 + ipv4
    ln $seq.out.46 $seq.out
else
    # ipv4 only
    ln $seq.out.4 $seq.out
fi
# NB: we don't anticipate an ipv6-only host

echo | tee -a $seq.full
echo "=== 2. pmwebd exercise via python ===" | tee -a $seq.full
# pmwebd still running in default mode
if grep -q IPv4 $tmp.out; then
    python $pyscript --host localhost | _filter
fi
if grep -q IPv6 $tmp.out; then
    python $pyscript --host "$ipv6local" | _filter
fi

echo | tee -a $seq.full
echo "=== 3. pmwebd security constraints, file service ===" | tee -a $seq.full
$sudo $signal -a pmwebd >/dev/null 2>&1
sleep 2		# let it shutdown

cat $tmp.out >> $seq.full
$PCP_BINADM_DIR/pmwebd $webargs -R `pwd` -c 2222 -L -h localhost -N -vv -l $tmp.out &
sleep 2		# let it start up

# should fail due to -N
curl -s -S "http://localhost:44323/pmapi/context?local=anything" | _filter
echo
# should fail due to nonexistent context#
curl -s -S "http://localhost:44323/pmapi/2225/_fetch" | _filter
echo
# should fail with a different error (insufficient elements; ie pmFetch failed) 
curl -s -S "http://localhost:44323/pmapi/2222/_fetch?names=" | _filter
echo
# should fail with a different error (insufficient elements; ie pmFetch failed) 
curl -s -S "http://localhost:44323/pmapi/2223/_fetch?pmids=" | _filter
echo
# should fail due to suspicious pmresapi path name
curl -s -S "http://localhost:44323/../../etc/passwd" | _filter
echo
# should fail due to non-enablement of graphite
curl -s -S "http://localhost:44323/graphite/render?target=*" | _filter
echo
# should pass, feed this very script
curl -s -S "http://localhost:44323/$seq" > $tmp.out2
diff $tmp.out2 $0 && echo file service ok

echo | tee -a $seq.full
echo "=== 4. pmwebd graphite capabilities ===" | tee -a $seq.full
$sudo $signal -a pmwebd >/dev/null 2>&1
sleep 2		# let it shut down

cat $tmp.out >> $seq.full
$PCP_BINADM_DIR/pmwebd $webargs -G -R $PCP_SHARE_DIR/jsdemos -A `pwd` -N -M0 -x/dev/tty -d1 -vvv -l $tmp.out &
sleep 2		# let it start up

function python_json_pretty() {
  # python 2.6+:  python -mjson.tool
  # python 2.5-:
  python -c 'from simplejson.tool import main; main()'
}

function python_img_pretty() {
  python -c "
import sys
from PIL import Image
from StringIO import StringIO
data = sys.stdin.read()
img = Image.open(StringIO(data))
print 'size=%dx%d\n' % (img.size[0], img.size[1])
"
}

echo "the catalog"
curl -s -i "http://localhost:44323/?zoo=poo&phantasm" | sed -e 's,^Date:.*$,Date: XXX,'  # test forwarding
curl -s -i "http://localhost:44323/blinkenlights" | sed -e 's,^Date:.*$,Date: XXX,'  # test forwarding
curl -s -i "http://localhost:44323/blinkenlights/" | sed -e 's,^Date:.*$,Date: XXX,'  # test forwarding
curl -s -S "http://localhost:44323/index.html?foo=bar&ectoplasm=egon"

echo
echo "metric name breakage" 
curl -s -S "http://localhost:44323/graphite/render?format=json&target=.." | python_json_pretty
curl -s -S "http://localhost:44323/graphite/render?format=json&target=foo-XX-bar" | python_json_pretty

echo
echo "metric tree iteration" 
curl -s -S "http://localhost:44323/graphite/metrics/find?query=src*naslog*meta.*" | python_json_pretty
curl -s -S "http://localhost:44323/graphite/metrics/find?format=completer&query=src*naslog*meta.*" | python_json_pretty

echo
echo "metric regex grep 1" 
curl -s -S "http://localhost:44323/graphite/graphlot/findmetric?q=.*960624.*disk.*dks131.*"
echo
echo "metric regex grep 2" 
curl -s -S "http://localhost:44323/graphite/browser/search?query=2013+hinv+n.*"
echo # not \n terminated

echo
echo "metric value dump 1" 
curl -s -S "http://localhost:44323/graphite/render?format=json&target=*-2F-node_archive-2E-meta.proc.psinfo.pid.*&from=15:50_20131127&until=1385585880&maxDataPoints=100" | python_json_pretty
echo
echo "metric value dump 2" 
curl -s -S "http://localhost:44323/graphite/rawdata?target=*-2F-node_archive-2E-meta.proc.psinfo.pid.*&from=15:50_20131127&until=20131129&maxDataPoints=300" | python_json_pretty

echo
echo "metric gfx rendering" 
curl -s -S "http://localhost:44323/graphite/render?width=999&height=999&hideLegend=false&bgcolor=%23FF0&title=hello&format=png&target=*-chartqa1-2E-meta.sample.*byte*&target=*-chartqa1-2E-meta.*NOSUCH*&target=*-chartqa1-2E-meta.sample.dodgey.value.NOSUCH&from=22:31_20071010&until=22:36_20071010" | tee 660.png | python_img_pretty


# tidy up
cat $tmp.out >> $seq.full
_cleanup

status=0
sleep 2
exit
