# FIXME: Move to appropriate Resource
Execute Controller Karaf Command On Background log:set ${bgpcep_level} org.opendaylight.bgpcep
Execute Controller Karaf Command On Background log:set ${protocol_level} org.opendaylight.protocol
+
+Wait For Karaf Log
+ [Arguments] ${message} ${timeout}=60
+ [Documentation] Read karaf logs until message appear
+ Log Waiting for '${message}' in karaf log
+ Open Connection ${CONTROLLER} port=${KARAF_SHELL_PORT} prompt=${KARAF_PROMPT} timeout=${timeout}
+ Flexible SSH Login ${KARAF_USER} ${KARAF_PASSWORD}
+ Write log:tail
+ Read Until ${message}
+ Close Connection
--- /dev/null
+*** Settings ***
+Variables ../variables/Variables.py
+Variables ../variables/topoprocessing/Topologies.py
+Library RequestsLibrary
+Library SSHLibrary
+Library XML
+Resource KarafKeywords.robot
+Resource Utils.robot
+
+*** Variables ***
+${CONFIGURATION_XML} ${CURDIR}/../suites/topoprocessing/configuration.xml
+${OPERATIONAL_XML} ${CURDIR}/../suites/topoprocessing/operational.xml
+${REMOTE_FILE} ${WORKSPACE}/${BUNDLEFOLDER}/etc/opendaylight/karaf/80-topoprocessing-config.xml
+
+*** Keywords ***
+Send Basic Request
+ [Arguments] ${request} ${overlay_topology_url}
+ [Documentation] Test basic aggregation
+ ${resp} Put Request session ${CONFIG_API}/${overlay_topology_url} data=${request}
+ Log ${CONFIG_API}/${overlay_topology_url}
+ Should Be Equal As Strings ${resp.status_code} 200
+ Wait For Karaf Log Correlation configuration successfully read
+ Wait For Karaf Log Transaction successfully written
+ ${resp} Get Request session ${OPERATIONAL_API}/${overlay_topology_url}
+ Should Be Equal As Strings ${resp.status_code} 200
+ Log ${resp.content}
+ [Return] ${resp}
+
+Setup Environment
+ [Documentation] Setup karaf enviroment for following tests
+ Log ---- Setup Environment ----
+ Open Connection ${CONTROLLER}
+ Flexible Controller Login
+ Put File ${CONFIGURATION_XML} ${REMOTE_FILE}
+ Close Connection
+ Issue Command On Karaf Console log:set DEBUG org.opendaylight.topoprocessing
+ Install a Feature odl-restconf-noauth timeout=30
+ Create Session session http://${CONTROLLER}:${RESTCONFPORT} auth=${AUTH} headers=${SEND_ACCEPT_XML_HEADERS}
+ ${features} Get Installed Features
+ ${lines} Get Lines Containing String ${features} odl-topoprocessing-framework
+ ${length} Get Length ${lines}
+ Install a Feature odl-openflowplugin-nsf-model-li odl-topoprocessing-framework odl-topoprocessing-network-topology odl-topoprocessing-inventory odl-bgpcep-pcep-all timeout=100
+ Run Keyword If ${length} == 0 Wait For Karaf Log Registering Topology Request Listener 60
+ Prepare New Feature Installation
+ Insert Underlay topologies
+
+Clean Environment
+ [Documentation] Revert startup changes
+ Log ---- Clean Environment ----
+ Open Connection ${CONTROLLER}
+ Flexible Controller Login
+ Put File ${OPERATIONAL_XML} ${REMOTE_FILE}
+ Close Connection
+ Delete All Sessions
+
+Test Teardown
+ [Arguments] ${overlay_topology}
+ [Documentation] Delete overlay topologies from datastore
+ Log ---- Test Teardown ----
+ Log Deleting overlay topology from ${CONFIG_API}/${overlay_topology}
+ ${resp} Delete Request session ${CONFIG_API}/${overlay_topology}
+ Should Be Equal As Strings ${resp.status_code} 200
+
+Prepare New Feature Installation
+ [Documentation] Clears karaf logs and CONFIGURATION datastore
+ ${resp} Delete Request session ${CONFIG_API}/network-topology:network-topology
+ ${resp} Delete Request session ${CONFIG_API}/opendaylight-inventory:nodes
+ Issue Command On Karaf Console log:clear
+
+Insert Underlay Topologies
+ [Documentation] Insert underlay topologies used by following tests
+ Log Inserting underlay topologies
+ # Network underlay topology 1
+ ${resp} Put Request session ${CONFIG_API}/${TOPOLOGY_URL}/network-topo:1 data=${NETWORK_UNDERLAY_TOPOLOGY_1}
+ Log ${resp.content}
+ Should Be Equal As Strings ${resp.status_code} 200
+ # Network underlay topology 2
+ ${resp} Put Request session ${CONFIG_API}/${TOPOLOGY_URL}/network-topo:2 data=${NETWORK_UNDERLAY_TOPOLOGY_2}
+ Log ${resp.content}
+ Should Be Equal As Strings ${resp.status_code} 200
+ # Openflow underlay nodes
+ ${resp} Put Request session ${CONFIG_API}/opendaylight-inventory:nodes data=${OPENFLOW_UNDERLAY_NODES}
+ Log ${resp.content}
+ Should Be Equal As Strings ${resp.status_code} 200
+ # Openflow underlay topology 1
+ ${resp} Put Request session ${CONFIG_API}/${TOPOLOGY_URL}/openflow-topo:1 data=${OPENFLOW_UNDERLAY_TOPOLOGY_1}
+ Log ${resp.content}
+ Should Be Equal As Strings ${resp.status_code} 200
+ # Openflow underlay topology 2
+ ${resp} Put Request session ${CONFIG_API}/${TOPOLOGY_URL}/openflow-topo:2 data=${OPENFLOW_UNDERLAY_TOPOLOGY_2}
+ Log ${resp.content}
+ Should Be Equal As Strings ${resp.status_code} 200
+ Issue Command On Karaf Console log:clear
+ Log ${resp.content}
+
+Prepare Unification Inside Topology Request
+ [Arguments] ${request_template} ${model} ${correlation_item} ${target-field} ${underlay_topo1}
+ [Documentation] Prepare topology request for unification inside from template
+ ${request_template} Set Element Text ${request_template} ${model} xpath=.//correlations/output-model
+ ${request_template} Set Element Text ${request_template} aggregation-only xpath=.//correlations/correlation/type
+ ${request_template} Set Element Text ${request_template} ${correlation_item} xpath=.//correlation/correlation-item
+ ${request_template} Set Element Text ${request_template} unification xpath=.//correlation/aggregation/aggregation-type
+ ${request_template} Set Element Text ${request_template} ${model} xpath=.//correlation/aggregation/mapping[1]/input-model
+ ${request_template} Set Element Text ${request_template} ${underlay_topo1} xpath=.//correlation/aggregation/mapping[1]/underlay-topology
+ ${request_template} Set Element Text ${request_template} ${target-field} xpath=.//correlation/aggregation/mapping[1]/target-field
+ ${request_template} Element to String ${request_template}
+ [Return] ${request_template}
+
+Prepare Unification Topology Request
+ [Arguments] ${request_template} ${model} ${correlation_item} ${target-field} ${underlay_topo1} ${underlay_topo2}
+ [Documentation] Prepare topology request for unification on two topologies from template
+ ${request_template} Prepare Unification Inside Topology Request ${request_template} ${model} ${correlation_item} ${target-field} ${underlay_topo1}
+ ${request_template} Set Element Text ${request_template} ${underlay_topo2} xpath=.//correlation/aggregation/mapping[2]/underlay-topology
+ ${request_template} Set Element Text ${request_template} ${target-field} xpath=.//correlation/aggregation/mapping[2]/target-field
+ ${request_template} Set Element Text ${request_template} ${model} xpath=.//correlation/aggregation/mapping[2]/input-model
+ ${request_template} Element to String ${request_template}
+ [Return] ${request_template}
+
+Get Installed Features
+ [Documentation] Returns list of installed features as String
+ Open Connection ${CONTROLLER} port=${KARAF_SHELL_PORT} prompt=${KARAF_PROMPT} timeout=5
+ Flexible SSH Login ${KARAF_USER} ${KARAF_PASSWORD}
+ Write feature:list -i
+ ${features} Read until prompt
+ Close Connection
+ Log Installed features:
+ Log ${features}
+ [Return] ${features}
--- /dev/null
+*** Settings ***
+Documentation Test suite to verify unification operation on different models.
+... Before test starts, configurational file have to be rewriten to change listners registration datastore type from CONFIG_API to OPERATIONAL_API.
+... Need for this change is also a reason why main feature (odl-topoprocessing-framework) is installed after file change and not during boot.
+... Suite setup also install features required for tested models, clear karaf logs for further synchronization. Tests themselves send configurational
+... xmls and verify output. Topology-id on the end of each urls must match topology-id from xml. Yang models of components in topology are defined in xmls.
+Suite Setup Setup Environment
+Suite Teardown Clean Environment
+Test Teardown Test Teardown network-topology:network-topology/topology/topo:1
+Library RequestsLibrary
+Library SSHLibrary
+Library XML
+Variables ../../../variables/topoprocessing/TopologyRequests.py
+Variables ../../../variables/Variables.py
+Resource ../../../libraries/KarafKeywords.robot
+Resource ../../../libraries/Utils.robot
+Resource ../../../libraries/TopoprocessingKeywords.robot
+
+*** Test Cases ***
+Unification Node
+ [Documentation] Test unification operation on Network Topology model
+ ${request} Prepare Unification Topology Request ${UNIFICATION_NT} network-topology-model node network-topology-pcep:path-computation-client/network-topology-pcep:ip-address network-topo:1
+ ... network-topo:2
+ ${resp} Send Basic Request ${request} network-topology:network-topology/topology/topo:1
+ Should Contain ${resp.content} <topology-id>topo:1</topology-id>
+ Should Contain X Times ${resp.content} <node-id>node: 9
+ : FOR ${index} IN RANGE 1 9
+ \ Should Contain X Times ${resp.content} <node-ref>pcep:${index}</node-ref> 1
+ ${node} Get Element ${resp.content} xpath=.//node/supporting-node[node-ref='pcep:10']/..
+ ${node} Element to String ${node}
+ Should Contain X Times ${node} <node-ref>pcep:10</node-ref> 1
+ Should Contain X Times ${node} <node-ref>pcep:5</node-ref> 1
+
+Unification Node Inventory
+ [Documentation] Test unification operation on inventory model
+ ${request} Prepare Unification Topology Request ${UNIFICATION_NT} opendaylight-inventory-model node flow-node-inventory:ip-address openflow-topo:1
+ ... openflow-topo:2
+ ${resp} Send Basic Request ${request} network-topology:network-topology/topology/topo:1
+ Should Contain ${resp.content} <topology-id>topo:1</topology-id>
+ Should Contain X Times ${resp.content} <node-id>node: 8
+ : FOR ${index} IN RANGE 1 10
+ \ Should Contain X Times ${resp.content} <node-ref>of-node:${index}</node-ref> 1
+ ${node} Get Element ${resp.content} xpath=.//node/supporting-node[node-ref='of-node:1']/..
+ ${node} Element to String ${node}
+ Should Contain X Times ${node} <node-ref>of-node:6</node-ref> 1
+ Should Contain X Times ${node} <node-ref>of-node:1</node-ref> 1
+ ${node} Get Element ${resp.content} xpath=.//node/supporting-node[node-ref='of-node:4']/..
+ ${node} Element to String ${node}
+ Should Contain X Times ${node} <node-ref>of-node:10</node-ref> 1
+ Should Contain X Times ${node} <node-ref>of-node:4</node-ref> 1
--- /dev/null
+NETWORK_UNDERLAY_TOPOLOGY_1 = '''<topology
+ xmlns="urn:TBD:params:xml:ns:yang:network-topology"
+ xmlns:pcep="urn:opendaylight:params:xml:ns:yang:topology:pcep">
+ <topology-id>network-topo:1</topology-id>
+ <topology-types>
+ <pcep:topology-pcep></pcep:topology-pcep>
+ </topology-types>
+ <node>
+ <node-id>pcep:1</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.1.1</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:2</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.1.2</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:3</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.2.1</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:4</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.2.2</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:5</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.2.3</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ </topology>'''
+
+NETWORK_UNDERLAY_TOPOLOGY_2 = '''<topology
+ xmlns="urn:TBD:params:xml:ns:yang:network-topology"
+ xmlns:pcep="urn:opendaylight:params:xml:ns:yang:topology:pcep">
+ <topology-id>network-topo:2</topology-id>
+ <topology-types>
+ <pcep:topology-pcep></pcep:topology-pcep>
+ </topology-types>
+ <node>
+ <node-id>pcep:6</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.1.3</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:7</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.1.4</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:8</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.2.4</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:9</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.2.5</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ <node>
+ <node-id>pcep:10</node-id>
+ <pcep:path-computation-client>
+ <pcep:ip-address>192.168.2.3</pcep:ip-address>
+ </pcep:path-computation-client>
+ </node>
+ </topology>'''
+
+OPENFLOW_UNDERLAY_NODES = '''
+<nodes
+ xmlns="urn:opendaylight:inventory"
+ xmlns:flov-inv="urn:opendaylight:flow:inventory">
+ <node>
+ <id>openflow:1</id>
+ <flov-inv:manufacturer>Pantheon Technologies</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.1.1</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:2</id>
+ <flov-inv:manufacturer>Pantheon Technologies</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.1.2</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:3</id>
+ <flov-inv:manufacturer>Pantheon Technologies</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.1.3</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:4</id>
+ <flov-inv:manufacturer>Cisco</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.2.1</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:5</id>
+ <flov-inv:manufacturer>Cisco</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.2.2</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:6</id>
+ <flov-inv:manufacturer>Pantheon Technologies</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.1.1</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:7</id>
+ <flov-inv:manufacturer>Pantheon Technologies</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.2.3</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:8</id>
+ <flov-inv:manufacturer>Cisco</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.1.4</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:9</id>
+ <flov-inv:manufacturer>Cisco</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.1.5</flov-inv:ip-address>
+ </node>
+ <node>
+ <id>openflow:10</id>
+ <flov-inv:manufacturer>Cisco</flov-inv:manufacturer>
+ <flov-inv:ip-address>192.168.2.1</flov-inv:ip-address>
+ </node>
+</nodes>
+'''
+
+OPENFLOW_UNDERLAY_TOPOLOGY_1 = '''
+<topology
+ xmlns="urn:TBD:params:xml:ns:yang:network-topology"
+ xmlns:inventory="urn:opendaylight:inventory"
+ xmlns:inventory-topo="urn:opendaylight:model:topology:inventory">
+ <topology-id>openflow-topo:1</topology-id>
+ <node>
+ <node-id>of-node:1</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:1"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:2</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:2"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:3</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:3"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:4</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:4"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:5</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:5"]</inventory-topo:inventory-node-ref>
+ </node>
+</topology>
+'''
+
+OPENFLOW_UNDERLAY_TOPOLOGY_2 = '''
+<topology
+ xmlns="urn:TBD:params:xml:ns:yang:network-topology"
+ xmlns:inventory="urn:opendaylight:inventory"
+ xmlns:inventory-topo="urn:opendaylight:model:topology:inventory">
+ <topology-id>openflow-topo:2</topology-id>
+ <node>
+ <node-id>of-node:6</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:6"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:7</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:7"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:8</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:8"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:9</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:9"]</inventory-topo:inventory-node-ref>
+ </node>
+ <node>
+ <node-id>of-node:10</node-id>
+ <inventory-topo:inventory-node-ref>/inventory:nodes/inventory:node[inventory:id="openflow:10"]</inventory-topo:inventory-node-ref>
+ </node>
+</topology>
+'''
--- /dev/null
+UNIFICATION_NT = '''<topology xmlns="urn:opendaylight:topology:correlation" xmlns:n="urn:TBD:params:xml:ns:yang:network-topology">
+ <n:topology-id>topo:1</n:topology-id>
+ <correlations>
+ <output-model>{output-model}</output-model>
+ <correlation>
+ <correlation-id>1</correlation-id>
+ <type>{type}</type>
+ <correlation-item>{correlation-item}</correlation-item>
+ <aggregation>
+ <aggregation-type>{aggregation-type}</aggregation-type>
+ <mapping>
+ <input-model>{input-model}</input-model>
+ <underlay-topology>{underlay-topology-id}</underlay-topology>
+ <target-field>{target-field}</target-field>
+ <aggregate-inside>false</aggregate-inside>
+ </mapping>
+ <mapping>
+ <input-model>{input-model}</input-model>
+ <underlay-topology>{underlay-topology-id}</underlay-topology>
+ <target-field>{target-field}</target-field>
+ <aggregate-inside>false</aggregate-inside>
+ </mapping>
+ </aggregation>
+ </correlation>
+ </correlations>
+ </topology>'''
+
+UNIFICATION_NT_AGREGATE_INSIDE = '''<topology xmlns="urn:opendaylight:topology:correlation" xmlns:n="urn:TBD:params:xml:ns:yang:network-topology">
+ <n:topology-id>topo:1</n:topology-id>
+ <correlations>
+ <output-model>{output-model}</output-model>
+ <correlation>
+ <correlation-id>1</correlation-id>
+ <type>{type}</type>
+ <correlation-item>{correlation-item}</correlation-item>
+ <aggregation>
+ <aggregation-type>{aggregation-type}</aggregation-type>
+ <mapping>
+ <input-model>{input-model}</input-model>
+ <underlay-topology>{underlay-topology-id}</underlay-topology>
+ <target-field>{target-field}</target-field>
+ <aggregate-inside>true</aggregate-inside>
+ </mapping>
+ </aggregation>
+ </correlation>
+ </correlations>
+ </topology>'''
+
+FILTRATION_NT = '''<topology xmlns="urn:opendaylight:topology:correlation" xmlns:n="urn:TBD:params:xml:ns:yang:network-topology">
+ <n:topology-id>topo:1</n:topology-id>
+ <correlations>
+ <output-model>{output-model}</output-model>
+ <correlation>
+ <correlation-id>1</correlation-id>
+ <type>filtration-only</type>
+ <correlation-item>{correlation-item}</correlation-item>
+ <filtration>
+ <underlay-topology>{underlay-topology-id}</underlay-topology>
+ <!-- Filter -->
+ </filtration>
+ </correlation>
+ </correlations>
+ </topology>'''
+
+FILTER_IPV4 = '''<filter>
+ <input-model>{input-model}</input-model>
+ <filter-id>1</filter-id>
+ <target-field>{target-field}</target-field>
+ <filter-type>ipv4-address</filter-type>
+ <ipv4-address-filter>
+ <ipv4-address>{ipv4}</ipv4-address>
+ </ipv4-address-filter>
+ </filter>'''