* Fixed: [namespace prefix nc is not supported in full #154](https://github.com/clicon/clixon/issues/154)

* edit-config "config" parameter did not work with prefix other than null
This commit is contained in:
Olof hagsand 2020-12-02 14:21:17 +01:00
parent 2b9f19a19f
commit d045e8abce
6 changed files with 85 additions and 17 deletions

View file

@ -74,9 +74,10 @@ Developers may need to change their code
### Corrected Bugs
* Fixed: [namespace prefix nc is not supported in full #154](https://github.com/clicon/clixon/issues/154)
* edit-config "config" parameter did not work with prefix other than null
* Fixed [YANG: key statement in rpc/notification list #148](https://github.com/clicon/clixon/issues/148)
* Do not check uniqueness among lists without keys
* Fixed typo: [False Header Content_type in restconf error #152](https://github.com/clicon/clixon/issues/152)
* Added message-id attributes in error and hello replies
* See [namespace prefix nc is not supported in full #154](https://github.com/clicon/clixon/issues/154)

View file

@ -509,6 +509,7 @@ from_client_get_config(clicon_handle h,
goto done;
goto ok;
}
/* XXX should use prefix cf edit_config */
if ((xfilter = xml_find(xe, "filter")) != NULL){
if ((xpath0 = xml_find_value(xfilter, "select"))==NULL)
xpath0="/";
@ -587,6 +588,8 @@ from_client_edit_config(clicon_handle h,
char *attr;
int autocommit = 0;
char *val = NULL;
cvec *nsc = NULL;
char *prefix = NULL;
username = clicon_username_get(h);
if ((yspec = clicon_dbspec_yang(h)) == NULL){
@ -616,15 +619,28 @@ from_client_edit_config(clicon_handle h,
goto done;
goto ok;
}
if ((x = xpath_first(xn, NULL, "default-operation")) != NULL){
if (xml_nsctx_node(xn, &nsc) < 0)
goto done;
/* Get prefix of netconf base namespace in the incoming message */
if (xml_nsctx_get_prefix(nsc, NETCONF_BASE_NAMESPACE, &prefix) == 0){
cprintf(cbx, "No appropriate prefix exists for: %s", NETCONF_BASE_NAMESPACE);
if (netconf_unknown_namespace(cbret, "protocol", xml_name(xn), cbuf_get(cbx)) < 0)
goto done;
goto ok;
}
/* Get default-operation element */
if ((x = xpath_first(xn, nsc, "%s%sdefault-operation", prefix?prefix:"", prefix?":":"")) != NULL){
if (xml_operation(xml_body(x), &operation) < 0){
if (netconf_invalid_value(cbret, "protocol", "Wrong operation")< 0)
goto done;
goto ok;
}
}
if ((xc = xpath_first(xn, NULL, "config")) == NULL){
if (netconf_missing_element(cbret, "protocol", "config", NULL) < 0)
/* Get config element */
if ((xc = xpath_first(xn, nsc, "%s%sconfig", prefix?prefix:"", prefix?":":"")) == NULL){
cprintf(cbx, "Element not found, or mismatching prefix %s for namespace %s",
prefix?prefix:"null", NETCONF_BASE_NAMESPACE);
if (netconf_missing_element(cbret, "protocol", "config", cbuf_get(cbx)) < 0)
goto done;
goto ok;
}
@ -713,6 +729,8 @@ from_client_edit_config(clicon_handle h,
ok:
retval = 0;
done:
if (nsc)
cvec_free(nsc);
if (xret)
xml_free(xret);
if (cbx)
@ -822,6 +840,7 @@ from_client_delete_config(clicon_handle h,
uint32_t myid = ce->ce_id;
cbuf *cbx = NULL; /* Assist cbuf */
/* XXX should use prefix cf edit_config */
if ((target = netconf_db_find(xe, "target")) == NULL ||
strcmp(target, "running")==0){
if (netconf_missing_element(cbret, "protocol", "target", NULL) < 0)
@ -1340,6 +1359,7 @@ from_client_create_subscription(clicon_handle h,
struct timeval stop;
cvec *nsc = NULL;
/* XXX should use prefix cf edit_config */
if ((nsc = xml_nsctx_init(NULL, EVENT_RFC5277_NAMESPACE)) == NULL)
goto done;
if ((x = xpath_first(xe, nsc, "//stream")) != NULL)
@ -1654,7 +1674,7 @@ from_client_msg(clicon_handle h,
goto reply;
}
else if (strcmp(namespace, NETCONF_BASE_NAMESPACE) != 0){
cbuf *cbmsg;
cbuf *cbmsg = NULL;
if ((cbmsg = cbuf_new()) == NULL){
clicon_err(OE_UNIX, errno, "cbuf_new");
goto done;

View file

@ -1406,6 +1406,7 @@ netconf_db_find(cxobj *xn,
cxobj *xi;
char *db = NULL;
/* XXX should use prefix cf edit_config */
if ((xs = xml_find(xn, name)) == NULL)
goto done;
if ((xi = xml_child_i(xs, 0)) == NULL)

View file

@ -1697,7 +1697,7 @@ xml_find_type_value(cxobj *xt,
*
* The value can be of an attribute only
* @param[in] xt xml tree node
* @param[in] prefix Prefix (namespace local name) or NULL
* @param[in] prefix Prefix (namespace local name) or NULL (any prefix)
* @param[in] name name of xml tree node (eg attr name or "body")
* @param[in] type Matching type or -1 for any
* @retval val Pointer to the name string

View file

@ -35,26 +35,24 @@
* Clixon XML XPATH 1.0 according to https://www.w3.org/TR/xpath-10
*
* Some notes on namespace extensions in Netconf/Yang
* RFC6241 8.9.1
* The set of namespace declarations are those in scope on the <filter> element.
* 1) The xpath is not "namespace-aware" in the sense that if you look for a path, eg
* "n:a/n:b", those must match the XML, so they need to match prefixes AND name in the xml
* such as <n:a><n:b>. An xml with <m:a><m:b> (or <a><b>) will NOT match EVEN IF they have the
* same namespace given by xmlns settings.
* 2) RFC6241 8.9.1
* In the scope of get-.config, the set of namespace declarations are those in scope on the
* <filter> element.
* <rpc message-id="101" xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
* <get-config>
* <filter xmlns:t="http://example.com/schema/1.2/config"
* type="xpath"
* select="/t:top/t:users/t:user[t:name='fred']"/>
* </get-config>
* We need to add namespace context to the cpath tree, typically in eval. How do
* we do that?
* One observation is that the namespace context is static, so it can not be a part
* of the xpath-tree, which is context-dependent.
* Best is to send it as a (read-only) parameter to the xp_eval family of functions
* as an exlicit namespace context.
* For that you need an API to get/set namespaces: clixon_xml_nscache.c?
* Then you need to fix API functions and this is the real work:
* - Replace all existing functions or create new?
* - Expose explicit namespace parameter, or xml object, or default namespace?
*
* @see README.md#xml-and-xpath for description of xpath implementation
*/
#ifdef HAVE_CONFIG_H
#include "clixon_config.h" /* generated by config & autoconf */
@ -587,7 +585,9 @@ xpath_vec_ctx(cxobj *xcur,
*
* @code
* cxobj *x;
* cvec *nsc; // namespace context
* cvec *nsc = NULL; // namespace context
* if (xml_nsctx_node(xtop, &nsc) < 0)
* err;
* if ((x = xpath_first(xtop, nsc, "//symbol/foo")) != NULL) {
* ...
* }

View file

@ -1,5 +1,8 @@
#!/usr/bin/env bash
# Basic Netconf functionality
# Mainly default/null prefix, but also xx: prefix
# XXX: could add tests for dual prefixes xx and xy with doppelganger names, ie xy:filter that is
# syntactic correct but wrong
# Magic line must be first in script (see README.md)
s="$_" ; . ./lib.sh || if [ "$s" = $0 ]; then exit 0; else return 0; fi
@ -80,9 +83,12 @@ expecteof "$clixon_netconf -f $cfg" 0 "<?xml version=\"1.0\" encoding=\"UTF-8\"?
new "netconf rcv hello, disable RFC7895/ietf-yang-library"
expecteof "$clixon_netconf -f $cfg -o CLICON_MODULE_LIBRARY_RFC7895=0" 0 "<rpc $DEFAULTNS><get-config><source><candidate/></source></get-config></rpc>]]>]]>" "^<hello $DEFAULTNS><capabilities><capability>urn:ietf:params:netconf:base:1.0</capability><capability>urn:ietf:params:netconf:capability:candidate:1.0</capability><capability>urn:ietf:params:netconf:capability:validate:1.1</capability><capability>urn:ietf:params:netconf:capability:startup:1.0</capability><capability>urn:ietf:params:netconf:capability:xpath:1.0</capability><capability>urn:ietf:params:netconf:capability:notification:1.0</capability></capabilities><session-id>[0-9]*</session-id></hello>]]>]]><rpc-reply $DEFAULTNS><data/></rpc-reply>]]>]]>$"
new "netconf get-config prefix"
new "netconf get-config nc prefix"
expecteof "$clixon_netconf -qf $cfg" 0 "<nc:rpc xmlns:nc=\"urn:ietf:params:xml:ns:netconf:base:1.0\" nc:message-id=\"42\"><nc:get-config><nc:source><nc:candidate/></nc:source></nc:get-config></nc:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:nc=\"urn:ietf:params:xml:ns:netconf:base:1.0\" nc:message-id=\"42\"><data/></rpc-reply>]]>]]>$"
new "netconf get-config xx prefix"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:get-config><xx:source><xx:candidate/></xx:source></xx:get-config></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><data/></rpc-reply>]]>]]>$"
new "netconf get-config double quotes"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><get-config><source><candidate/></source></get-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><data/></rpc-reply>]]>]]>$"
@ -92,6 +98,13 @@ expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><get-config><source><can
new "Add subtree eth/0/0 using none which should not change anything"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><edit-config><default-operation>none</default-operation><target><candidate/></target><config><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth/0/0</name></interface></interfaces></config></edit-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
# Trying prefixes
new "Add subtree eth/0/0 using nc prefix"
expecteof "$clixon_netconf -qf $cfg" 0 "<nc:rpc xmlns:nc=\"urn:ietf:params:xml:ns:netconf:base:1.0\" nc:message-id=\"42\"><nc:edit-config><nc:default-operation>none</nc:default-operation><nc:target><nc:candidate/></nc:target><nc:config><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth/0/0</name></interface></interfaces></nc:config></nc:edit-config></nc:rpc>]]>]]>" "^<rpc-reply $DEFAULTONLY xmlns:nc=\"urn:ietf:params:xml:ns:netconf:base:1.0\" nc:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
new "Add subtree eth/0/0 using xx prefix"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:edit-config><xx:default-operation>none</xx:default-operation><xx:target><xx:candidate/></xx:target><xx:config><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth/0/0</name></interface></interfaces></xx:config></xx:edit-config></xx:rpc>]]>]]>" "^<rpc-reply $DEFAULTONLY xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
new "Check nothing added"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><get-config><source><candidate/></source></get-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><data/></rpc-reply>]]>]]>$"
@ -124,6 +137,9 @@ expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><edit-config><target><ca
new "netconf discard-changes"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><discard-changes/></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
new "netconf discard-changes using xx prefix"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:discard-changes/></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
new "netconf edit config"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><edit-config><target><candidate/></target><config><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth/0/0</name></interface><interface xmlns:ip=\"urn:ietf:params:xml:ns:yang:ietf-ip\"><name>eth1</name><enabled>true</enabled><ip:ipv4><ip:address><ip:ip>9.2.3.4</ip:ip><ip:prefix-length>24</ip:prefix-length></ip:address></ip:ipv4></interface></interfaces></config></edit-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
@ -146,6 +162,9 @@ expecteof "$clixon_netconf -qf $cfg" 0 "$(cat $tmp)" "^<rpc-reply $DEFAULTNS><da
new "netconf validate missing type"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><validate><source><candidate/></source></validate></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><rpc-error>"
new "netconf validate using xx prefix"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:validate><xx:source><xx:candidate/></xx:source></xx:validate></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><rpc-error>"
new "netconf discard-changes"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><discard-changes/></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
@ -167,6 +186,9 @@ expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><validate><source><candi
new "netconf commit"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><commit/></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
new "netconf commit using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:commit/></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
new "netconf edit config merge eth2"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><edit-config><target><candidate/></target><config><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth2</name><type>ex:eth</type></interface></interfaces></config><default-operation>merge</default-operation></edit-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
@ -196,12 +218,21 @@ expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><edit-config><target><ca
new "netconf get state operation"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><get><filter type=\"xpath\" select=\"/if:interfaces\" xmlns:if=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\" /></get></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><data><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth1</name><type>ex:eth</type><enabled>true</enabled><oper-status>up</oper-status><ex:my-status xmlns:ex=\"urn:example:clixon\"><ex:int>42</ex:int><ex:str>foo</ex:str></ex:my-status></interface></interfaces></data></rpc-reply>]]>]]>$"
new "netconf get state operation use prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:get><xx:filter xx:type=\"xpath\" xx:select=\"/if:interfaces\" xmlns:if=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\" /></xx:get></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><data><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth1</name><type>ex:eth</type><enabled>true</enabled><oper-status>up</oper-status><ex:my-status xmlns:ex=\"urn:example:clixon\"><ex:int>42</ex:int><ex:str>foo</ex:str></ex:my-status></interface></interfaces></data></rpc-reply>]]>]]>$"
new "netconf lock"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><lock><target><candidate/></target></lock></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
new "netconf unlock"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><unlock><target><candidate/></target></unlock></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><rpc-error><error-type>protocol</error-type><error-tag>lock-denied</error-tag><error-info><session-id>0</session-id></error-info><error-severity>error</error-severity><error-message>Unlock failed, lock is not currently active</error-message></rpc-error></rpc-reply>]]>]]>$"
new "netconf lock using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:lock><xx:target><xx:candidate/></xx:target></xx:lock></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
new "netconf unlock using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:unlock><xx:target><xx:candidate/></xx:target></xx:unlock></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><rpc-error><error-type>protocol</error-type><error-tag>lock-denied</error-tag><error-info><session-id>0</session-id></error-info><error-severity>error</error-severity><error-message>Unlock failed, lock is not currently active</error-message></rpc-error></rpc-reply>]]>]]>$"
new "netconf lock/unlock"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><lock><target><candidate/></target></lock></rpc>]]>]]><rpc $DEFAULTNS><unlock><target><candidate/></target></unlock></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]><rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
@ -214,10 +245,16 @@ expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><unlock><target><candida
new "close-session"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><close-session/></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
new "close-session using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:close-session/></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
# XXX NOTE that this does not actually kill a running session - and may even kill some random process,...
new "kill-session"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><kill-session><session-id>44</session-id></kill-session></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
new "kill-session using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:kill-session><xx:session-id>44</xx:session-id></xx:kill-session></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
# modify candidate, then lock, should fail.
new "netconf edit config"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><edit-config><target><candidate/></target><config><table xmlns=\"urn:example:clixon\"><parameter><name>a</name></parameter></table></config></edit-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
@ -234,18 +271,27 @@ expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><lock><target><candidate
new "copy startup to candidate"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><copy-config><target><startup/></target><source><candidate/></source></copy-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
new "copy startup to candidate using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:copy-config><xx:target><xx:startup/></xx:target><xx:source><xx:candidate/></xx:source></xx:copy-config></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
new "netconf get startup"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><get-config><source><startup/></source></get-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><data><interfaces xmlns=\"urn:ietf:params:xml:ns:yang:ietf-interfaces\"><interface><name>eth1</name><type>ex:eth</type><enabled>true</enabled></interface></interfaces></data></rpc-reply>]]>]]>$"
new "netconf delete startup"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><delete-config><target><startup/></target></delete-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"
new "netconf delete startup using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><xx:delete-config><xx:target><xx:startup/></xx:target></xx:delete-config></xx:rpc>]]>]]>" "^<rpc-reply xmlns=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><ok/></rpc-reply>]]>]]>$"
new "netconf check empty startup"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><get-config><source><startup/></source></get-config></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><data/></rpc-reply>]]>]]>$"
new "netconf example rpc"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><example xmlns=\"urn:example:clixon\"><x>42</x></example></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><x xmlns=\"urn:example:clixon\">42</x><y xmlns=\"urn:example:clixon\">42</y></rpc-reply>]]>]]>$"
new "netconf example rpc using prefix xx"
expecteof "$clixon_netconf -qf $cfg" 0 "<xx:rpc xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\" xx:message-id=\"42\"><example xmlns=\"urn:example:clixon\"><x>42</x></example></xx:rpc>]]>]]>" "^<rpc-reply $DEFAULTNS xmlns:xx=\"urn:ietf:params:xml:ns:netconf:base:1.0\"><x xmlns=\"urn:example:clixon\">42</x><y xmlns=\"urn:example:clixon\">42</y></rpc-reply>]]>]]>$"
new "netconf empty rpc"
expecteof "$clixon_netconf -qf $cfg" 0 "<rpc $DEFAULTNS><empty xmlns=\"urn:example:clixon\"/></rpc>]]>]]>" "^<rpc-reply $DEFAULTNS><ok/></rpc-reply>]]>]]>$"