* Restconf native http/1, first working version
* Renamed files clixon_http -> restconf_http * Split main file into restconf_native.c * Remove all evhtp code and libevhtp/libevent dependency
This commit is contained in:
parent
dadf4a778a
commit
4aa74fa1d8
27 changed files with 1291 additions and 789 deletions
|
|
@ -40,7 +40,11 @@
|
|||
# --with-restconf=native Integration with embedded web server
|
||||
WITH_RESTCONF=@with_restconf@ # native, fcgi or ""
|
||||
|
||||
HAVE_LIBNGHTTP2=@HAVE_LIBNGHTTP2@
|
||||
# HTTP/2?
|
||||
# If set, curl options are set to use --http2 which may not be what you want, ie
|
||||
# you may want to force it to http/1 for example
|
||||
# If so, override before test
|
||||
: ${HAVE_LIBNGHTTP2:=@HAVE_LIBNGHTTP2@}o
|
||||
HAVE_HTTP1=@HAVE_HTTP1@
|
||||
|
||||
# This is for libxml2 XSD regex engine
|
||||
|
|
@ -85,4 +89,6 @@ LIBSTATIC_SUFFIX=@LIBSTATIC_SUFFIX@
|
|||
LIBS="@LIBS@"
|
||||
CLIXON_YANG_PATCH=@CLIXON_YANG_PATCH@
|
||||
YANG_STANDARD_DIR=@YANG_STANDARD_DIR@
|
||||
|
||||
YANG_INSTALLDIR=@YANG_INSTALLDIR@
|
||||
|
||||
|
|
|
|||
|
|
@ -110,6 +110,7 @@ if ${HAVE_LIBNGHTTP2}; then
|
|||
CURLOPTS="${CURLOPTS} --http2-prior-knowledge"
|
||||
fi
|
||||
else
|
||||
CURLOPTS="${CURLOPTS} --http1.1"
|
||||
HVER=1.1
|
||||
fi
|
||||
|
||||
|
|
|
|||
|
|
@ -454,7 +454,7 @@ function testrun()
|
|||
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" -d '{"ietf-interfaces:description":"The-first-interface"}' $proto://$addr/restconf/data/ietf-interfaces:interfaces/interface=eth%2f0%2f0)" 0 "HTTP/$HVER 201"
|
||||
|
||||
new "Add nothing using POST (expect fail)"
|
||||
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" $proto://$addr/restconf/data/ietf-interfaces:interfaces/interface=eth%2f0%2f0)" 0 "HTTP/$HVER 400" '{"ietf-restconf:errors":{"error":{"error-type":"rpc","error-tag":"malformed-message","error-severity":"error","error-message":"The message-body MUST contain exactly one instance of the expected data resource"}}}'
|
||||
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" $proto://$addr/restconf/data/ietf-interfaces:interfaces/interface=eth%2f0%2f0)" 0 "HTTP/$HVER 400" '{"ietf-restconf:errors":{"error":{"error-type":"rpc","error-tag":"malformed-message","error-severity":"error","error-message":"The message-body of POST MUST contain exactly one instance of the expected data resource"}}}'
|
||||
|
||||
new "restconf Check description added"
|
||||
expectpart "$(curl $CURLOPTS -X GET $proto://$addr/restconf/data/ietf-interfaces:interfaces)" 0 "HTTP/$HVER 200" '{"ietf-interfaces:interfaces":{"interface":\[{"name":"eth/0/0","description":"The-first-interface","type":"clixon-example:eth","enabled":true,"oper-status":"up","clixon-example:my-status":{"int":42,"str":"foo"}}\]}}'
|
||||
|
|
|
|||
131
test/test_restconf_continue.sh
Executable file
131
test/test_restconf_continue.sh
Executable file
|
|
@ -0,0 +1,131 @@
|
|||
#!/usr/bin/env bash
|
||||
# Restconf HTTP/1.1 Expect/Continue functionality
|
||||
# Trigger Expect by curl -H. Some curls seem to trigger one on large PUTs but not all
|
||||
|
||||
# Override default to use http/1.1
|
||||
HAVE_LIBNGHTTP2=false
|
||||
|
||||
# Magic line must be first in script (see README.md)
|
||||
s="$_" ; . ./lib.sh || if [ "$s" = $0 ]; then exit 0; else return 0; fi
|
||||
|
||||
APPNAME=example
|
||||
|
||||
cfg=$dir/conf.xml
|
||||
fyang=$dir/restconf.yang
|
||||
fjson=$dir/large.json
|
||||
|
||||
# Define default restconfig config: RESTCONFIG
|
||||
RESTCONFIG=$(restconf_config none false)
|
||||
|
||||
# <CLICON_YANG_MODULE_MAIN>example</CLICON_YANG_MODULE_MAIN>
|
||||
cat <<EOF > $cfg
|
||||
<clixon-config xmlns="http://clicon.org/config">
|
||||
<CLICON_FEATURE>clixon-restconf:allow-auth-none</CLICON_FEATURE> <!-- Use auth-type=none -->
|
||||
<CLICON_CONFIGFILE>$cfg</CLICON_CONFIGFILE>
|
||||
<CLICON_YANG_DIR>/usr/local/share/clixon</CLICON_YANG_DIR>
|
||||
<CLICON_YANG_MAIN_FILE>$fyang</CLICON_YANG_MAIN_FILE>
|
||||
<CLICON_SOCK>/usr/local/var/$APPNAME/$APPNAME.sock</CLICON_SOCK>
|
||||
<CLICON_BACKEND_PIDFILE>$dir/restconf.pidfile</CLICON_BACKEND_PIDFILE>
|
||||
<CLICON_XMLDB_DIR>/usr/local/var/$APPNAME</CLICON_XMLDB_DIR>
|
||||
$RESTCONFIG
|
||||
</clixon-config>
|
||||
EOF
|
||||
|
||||
cat <<EOF > $fyang
|
||||
module example{
|
||||
yang-version 1.1;
|
||||
namespace "urn:example:clixon";
|
||||
prefix ex;
|
||||
/* Generic config data */
|
||||
container table{
|
||||
list parameter{
|
||||
key name;
|
||||
leaf name{
|
||||
type string;
|
||||
}
|
||||
leaf value{
|
||||
type string;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
EOF
|
||||
|
||||
new "test params: -f $cfg"
|
||||
|
||||
if [ $BE -ne 0 ]; then
|
||||
new "kill old backend"
|
||||
sudo clixon_backend -zf $cfg
|
||||
if [ $? -ne 0 ]; then
|
||||
err
|
||||
fi
|
||||
sudo pkill -f clixon_backend # to be sure
|
||||
|
||||
new "start backend -s init -f $cfg"
|
||||
start_backend -s init -f $cfg
|
||||
fi
|
||||
|
||||
new "wait backend"
|
||||
wait_backend
|
||||
|
||||
if [ $RC -ne 0 ]; then
|
||||
new "kill old restconf daemon"
|
||||
stop_restconf_pre
|
||||
|
||||
new "start restconf daemon"
|
||||
start_restconf -f $cfg
|
||||
fi
|
||||
|
||||
new "wait restconf"
|
||||
wait_restconf
|
||||
|
||||
|
||||
new "generate large request"
|
||||
# Add large put, curl seems to create a Expect:100-continue after 1024 bytes
|
||||
# Alt: add in file if nr=5000 reacts with "Argument list too long"
|
||||
echo -n '{"example:table":{"parameter":[' > $fjson
|
||||
|
||||
nr=10000
|
||||
for (( i=0; i<$nr; i++ )); do
|
||||
if [ $i -ne 0 ]; then
|
||||
echo -n ",
|
||||
" >> $fjson
|
||||
fi
|
||||
echo -n "{\"name\":\"A$i\",\"value\":\"$i\"}" >> $fjson
|
||||
done
|
||||
echo -n "]}}" >> $fjson
|
||||
|
||||
new "restconf large PUT"
|
||||
expectpart "$(curl $CURLOPTS -X POST -H "Content-Type: application/yang-data+json" -H "Expect: 100-continue" -d @$fjson $RCPROTO://localhost/restconf/data)" 0 "HTTP/$HVER 100 Continue" "HTTP/$HVER 201"
|
||||
|
||||
new "restconf PUT with expect"
|
||||
expectpart "$(curl $CURLOPTS -H "Expect: 100-continue" -X POST -H "Content-Type: application/yang-data+json" -d '{"example:parameter":[{"name":"A","value":"42"}]}' $RCPROTO://localhost/restconf/data/example:table)" 0 "HTTP/$HVER 100 Continue" "HTTP/$HVER 201"
|
||||
|
||||
new "restconf GET"
|
||||
expectpart "$(curl $CURLOPTS -X GET $RCPROTO://localhost/restconf/data/example:table/parameter=A)" 0 "HTTP/$HVER 200" '{"example:parameter":\[{"name":"A","value":"42"}\]}'
|
||||
|
||||
if [ $RC -ne 0 ]; then
|
||||
new "Kill restconf daemon"
|
||||
stop_restconf
|
||||
fi
|
||||
|
||||
if [ $BE -ne 0 ]; then
|
||||
new "Kill backend"
|
||||
# Check if premature kill
|
||||
pid=$(pgrep -u root -f clixon_backend)
|
||||
if [ -z "$pid" ]; then
|
||||
err "backend already dead"
|
||||
fi
|
||||
# kill backend
|
||||
stop_backend -f $cfg
|
||||
fi
|
||||
|
||||
# Set by restconf_config
|
||||
unset RESTCONFIG
|
||||
unset nr
|
||||
unset HAVE_LIBNGHTTP2
|
||||
|
||||
rm -rf $dir
|
||||
|
||||
new "endtest"
|
||||
endtest
|
||||
|
|
@ -20,6 +20,11 @@
|
|||
# plugin should be visible in the error message.
|
||||
# XXX does not test rpc-error from backend in api_return_err?
|
||||
|
||||
# Override default to use http/1.1
|
||||
# Force to HTTP 1.1 no SSL due to netcat
|
||||
RCPROTO=http
|
||||
HAVE_LIBNGHTTP2=false
|
||||
|
||||
# Magic line must be first in script (see README.md)
|
||||
s="$_" ; . ./lib.sh || if [ "$s" = $0 ]; then exit 0; else return 0; fi
|
||||
|
||||
|
|
@ -37,9 +42,6 @@ fyang2=$dir/augment.yang
|
|||
fxml=$dir/initial.xml
|
||||
fstate=$dir/state.xml
|
||||
|
||||
RCPROTO=http # Force to http due to netcat
|
||||
HVER=1.1
|
||||
|
||||
# Define default restconfig config: RESTCONFIG
|
||||
RESTCONFIG=$(restconf_config none false)
|
||||
|
||||
|
|
@ -203,15 +205,15 @@ expectpart "$(curl $CURLOPTS -X GET -H 'Accept: application/yang-data+xml' $RCPR
|
|||
# But leave it here for debugging where netcat works properly
|
||||
# Alt try something like:
|
||||
# printf "Hello World!" | (exec 3<>/dev/tcp/127.0.0.1/80; cat >&3; cat <&3; exec 3<&-)
|
||||
if [ false -a ! ${HAVE_LIBNGHTTP2} ] ; then
|
||||
# Look for netcat or nc for direct socket http calls
|
||||
if [ -n "$(type netcat 2> /dev/null)" ]; then
|
||||
netcat="netcat -w 1" # -N does not work on fcgi
|
||||
elif [ -n "$(type nc 2> /dev/null)" ]; then
|
||||
netcat=nc
|
||||
else
|
||||
err1 "netcat/nc not found"
|
||||
fi
|
||||
# Look for netcat or nc for direct socket http calls
|
||||
if [ -n "$(type netcat 2> /dev/null)" ]; then
|
||||
netcat="netcat -w 1" # -N does not work on fcgi
|
||||
elif [ -n "$(type nc 2> /dev/null)" ]; then
|
||||
netcat=nc
|
||||
else
|
||||
netcat=
|
||||
fi
|
||||
if [ -n "$netcat" ]; then
|
||||
|
||||
# new "restconf try fuzz crash"
|
||||
# expectpart "$(${netcat} 127.0.0.1 80 < ~/tmp/crashes/id:000000,sig:06,src:000493+000365,op:splice,rep:8)" 0 "HTTP/$HVER 400"
|
||||
|
|
@ -236,12 +238,12 @@ EOF
|
|||
|
||||
new "restconf PUT not allowed"
|
||||
expectpart "$(${netcat} 127.0.0.1 80 <<EOF
|
||||
PUT /restconf/.well-known/host-meta HTTP/$HVER
|
||||
PUT /.well-known/host-meta HTTP/$HVER
|
||||
Host: localhost
|
||||
Accept: application/yang-data+xml
|
||||
|
||||
EOF
|
||||
)" 0 "HTTP/$HVER 405" kalle # nginx uses "method not allowed"
|
||||
)" 0 "HTTP/$HVER 405" # nginx uses "method not allowed"
|
||||
|
||||
new "restconf GET wrong http version raw"
|
||||
expectpart "$(${netcat} 127.0.0.1 80 <<EOF
|
||||
|
|
@ -252,7 +254,7 @@ Accept: application/yang-data+xml
|
|||
EOF
|
||||
)" 0 "HTTP/$HVER 400" # native: '<error-tag>malformed-message</error-tag><error-message>The requested URL or a header is in some way badly formed</error-message>'
|
||||
|
||||
fi # Http/1.1 and netcat Cannot get to work on all platforms
|
||||
fi # netcat Cannot get to work on all platforms
|
||||
|
||||
new "restconf XYZ not found"
|
||||
expectpart "$(curl $CURLOPTS -X XYS -H 'Accept: application/yang-data+xml' $RCPROTO://localhost/restconf/data/example:a=0)" 0 "HTTP/$HVER 404"
|
||||
|
|
@ -335,6 +337,7 @@ fi
|
|||
unset RESTCONFIG
|
||||
unset HVER
|
||||
unset RCPROTO
|
||||
unset HAVE_LIBNGHTTP2
|
||||
|
||||
rm -rf $dir
|
||||
|
||||
|
|
|
|||
|
|
@ -145,7 +145,7 @@ function rpcoperation()
|
|||
}
|
||||
|
||||
# This test is confusing:
|
||||
# The whole restconf config is in clixon-config wich binds 0.0.0.0:80 which will be the only
|
||||
# The whole restconf config is in clixon-config which binds 0.0.0.0:80 which will be the only
|
||||
# config the restconf daemon ever reads.
|
||||
# However, enable (and debug) flag is stored in running db but only backend will ever read that.
|
||||
# It just controls how restconf is started, but thereafter the restconf daemon reads the static db in clixon-config file
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue