2 * Copyright (c) 2015 Red Hat, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
8 package org.opendaylight.ovsdb.southbound.it;
10 import static org.junit.Assert.assertNotNull;
11 import static org.junit.Assert.fail;
12 import static org.ops4j.pax.exam.CoreOptions.composite;
13 import static org.ops4j.pax.exam.CoreOptions.maven;
14 import static org.ops4j.pax.exam.CoreOptions.vmOption;
15 import static org.ops4j.pax.exam.CoreOptions.when;
16 import static org.ops4j.pax.exam.karaf.options.KarafDistributionOption.editConfigurationFilePut;
17 import static org.ops4j.pax.exam.karaf.options.KarafDistributionOption.karafDistributionConfiguration;
18 import static org.ops4j.pax.exam.karaf.options.KarafDistributionOption.keepRuntimeFolder;
20 import com.google.common.collect.ImmutableBiMap;
21 import com.google.common.collect.Lists;
22 import com.google.common.collect.Sets;
25 import java.lang.reflect.Array;
26 import java.net.InetAddress;
27 import java.net.UnknownHostException;
28 import java.util.ArrayList;
29 import java.util.HashSet;
30 import java.util.List;
31 import java.util.Properties;
33 import java.util.concurrent.ExecutionException;
34 import java.util.concurrent.ExecutorService;
35 import java.util.concurrent.Executors;
36 import java.util.concurrent.TimeUnit;
38 import javax.inject.Inject;
40 import org.junit.Assert;
41 import org.junit.Before;
42 import org.junit.Test;
43 import org.junit.runner.RunWith;
44 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
45 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
46 import org.opendaylight.controller.mdsal.it.base.AbstractMdsalTestBase;
47 import org.opendaylight.ovsdb.southbound.SouthboundConstants;
48 import org.opendaylight.ovsdb.southbound.SouthboundMapper;
49 import org.opendaylight.ovsdb.southbound.SouthboundProvider;
50 import org.opendaylight.ovsdb.southbound.SouthboundUtil;
51 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpAddress;
52 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.PortNumber;
53 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.Uri;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.VlanId;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.DatapathTypeBase;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.InterfaceTypeBase;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeAugmentation;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeAugmentationBuilder;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeName;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeProtocolBase;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbFailModeBase;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbNodeAugmentation;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbNodeAugmentationBuilder;
64 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbNodeRef;
65 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbPortInterfaceAttributes.VlanMode;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbTerminationPointAugmentation;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbTerminationPointAugmentationBuilder;
68 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeExternalIds;
69 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeExternalIdsBuilder;
70 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeOtherConfigs;
71 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeOtherConfigsBuilder;
72 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ControllerEntry;
73 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ControllerEntryBuilder;
74 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ProtocolEntry;
75 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ProtocolEntryBuilder;
76 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.ConnectionInfo;
77 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.ConnectionInfoBuilder;
78 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.DatapathTypeEntry;
79 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.InterfaceTypeEntryBuilder;
80 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.OpenvswitchOtherConfigs;
81 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceExternalIds;
82 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceExternalIdsBuilder;
83 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceOtherConfigs;
84 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceOtherConfigsBuilder;
85 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.Options;
86 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.OptionsBuilder;
87 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortExternalIds;
88 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortExternalIdsBuilder;
89 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortOtherConfigs;
90 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortOtherConfigsBuilder;
91 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.Trunks;
92 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.TrunksBuilder;
93 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NetworkTopology;
94 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NodeId;
95 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.TpId;
96 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.Topology;
97 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.TopologyKey;
98 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.Node;
99 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.NodeBuilder;
100 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.NodeKey;
101 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.node.TerminationPoint;
102 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.node.TerminationPointBuilder;
103 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.node.TerminationPointKey;
104 import org.opendaylight.yangtools.concepts.Builder;
105 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
106 import org.ops4j.pax.exam.Configuration;
107 import org.ops4j.pax.exam.Option;
108 import org.ops4j.pax.exam.junit.PaxExam;
109 import org.ops4j.pax.exam.karaf.options.KarafDistributionOption;
110 import org.ops4j.pax.exam.karaf.options.LogLevelOption;
111 import org.ops4j.pax.exam.options.MavenUrlReference;
112 import org.ops4j.pax.exam.spi.reactors.ExamReactorStrategy;
113 import org.ops4j.pax.exam.spi.reactors.PerClass;
114 import org.osgi.framework.BundleContext;
115 import org.slf4j.Logger;
116 import org.slf4j.LoggerFactory;
119 * Integration tests for southbound-impl
121 * @author Sam Hague (shague@redhat.com)
123 @RunWith(PaxExam.class)
124 @ExamReactorStrategy(PerClass.class)
125 public class SouthboundIT extends AbstractMdsalTestBase {
126 private static final String NETDEV_DP_TYPE = "netdev";
127 private static final Logger LOG = LoggerFactory.getLogger(SouthboundIT.class);
128 private static final int OVSDB_UPDATE_TIMEOUT = 1000;
129 private static final String FORMAT_STR = "%s_%s_%d";
130 public static final int NUM_THREADS = 4;
131 private static String addressStr;
132 private static String portStr;
133 private static String connectionType;
134 private static Boolean setup = false;
135 private static MdsalUtils mdsalUtils = null;
137 // TODO Constants copied from AbstractConfigTestBase, need to be removed (see TODO below)
138 private static final String PAX_EXAM_UNPACK_DIRECTORY = "target/exam";
139 private static final String KARAF_DEBUG_PORT = "5005";
140 private static final String KARAF_DEBUG_PROP = "karaf.debug";
141 private static final String KEEP_UNPACK_DIRECTORY_PROP = "karaf.keep.unpack";
144 private BundleContext bundleContext;
147 public Option[] config() {
148 // TODO Figure out how to use the parent Karaf setup, then just use super.config()
149 Option[] options = new Option[] {
150 when(Boolean.getBoolean(KARAF_DEBUG_PROP))
151 .useOptions(KarafDistributionOption.debugConfiguration(KARAF_DEBUG_PORT, true)),
152 karafDistributionConfiguration().frameworkUrl(getKarafDistro())
153 .unpackDirectory(new File(PAX_EXAM_UNPACK_DIRECTORY))
154 .useDeployFolder(false),
155 when(Boolean.getBoolean(KEEP_UNPACK_DIRECTORY_PROP)).useOptions(keepRuntimeFolder()),
156 // Works only if we don't specify the feature repo and name
158 Option[] propertyOptions = getPropertiesOptions();
159 Option[] otherOptions = getOtherOptions();
160 Option[] combinedOptions = new Option[options.length + propertyOptions.length + otherOptions.length];
161 System.arraycopy(options, 0, combinedOptions, 0, options.length);
162 System.arraycopy(propertyOptions, 0, combinedOptions, options.length, propertyOptions.length);
163 System.arraycopy(otherOptions, 0, combinedOptions, options.length + propertyOptions.length,
164 otherOptions.length);
165 return combinedOptions;
168 private Option[] getOtherOptions() {
169 return new Option[] {
170 vmOption("-javaagent:../jars/org.jacoco.agent.jar=destfile=../../jacoco-it.exec"),
176 public String getKarafDistro() {
178 .groupId("org.opendaylight.ovsdb")
179 .artifactId("southbound-karaf")
180 .versionAsInProject()
186 public String getModuleName() {
187 return "southbound-impl";
191 public String getInstanceName() {
192 return "southbound-default";
196 public MavenUrlReference getFeatureRepo() {
198 .groupId("org.opendaylight.ovsdb")
199 .artifactId("southbound-features")
200 .classifier("features")
202 .versionAsInProject();
206 public String getFeatureName() {
207 return "odl-ovsdb-southbound-impl-ui";
210 protected String usage() {
211 return "Integration Test needs a valid connection configuration as follows :\n"
212 + "active connection : mvn -Dovsdbserver.ipaddress=x.x.x.x -Dovsdbserver.port=yyyy verify\n"
213 + "passive connection : mvn -Dovsdbserver.connection=passive verify\n";
217 public Option getLoggingOption() {
219 editConfigurationFilePut(SouthboundITConstants.ORG_OPS4J_PAX_LOGGING_CFG,
220 "log4j.logger.org.opendaylight.ovsdb",
221 LogLevelOption.LogLevel.TRACE.name()),
222 super.getLoggingOption());
225 private Option[] getPropertiesOptions() {
226 Properties props = new Properties(System.getProperties());
227 String addressStr = props.getProperty(SouthboundITConstants.SERVER_IPADDRESS,
228 SouthboundITConstants.DEFAULT_SERVER_IPADDRESS);
229 String portStr = props.getProperty(SouthboundITConstants.SERVER_PORT,
230 SouthboundITConstants.DEFAULT_SERVER_PORT);
231 String connectionType = props.getProperty(SouthboundITConstants.CONNECTION_TYPE,
232 SouthboundITConstants.CONNECTION_TYPE_ACTIVE);
234 LOG.info("getPropertiesOptions: Using the following properties: mode= {}, ip:port= {}:{}",
235 connectionType, addressStr, portStr);
237 return new Option[] {
238 editConfigurationFilePut(SouthboundITConstants.CUSTOM_PROPERTIES,
239 SouthboundITConstants.SERVER_IPADDRESS, addressStr),
240 editConfigurationFilePut(SouthboundITConstants.CUSTOM_PROPERTIES,
241 SouthboundITConstants.SERVER_PORT, portStr),
242 editConfigurationFilePut(SouthboundITConstants.CUSTOM_PROPERTIES,
243 SouthboundITConstants.CONNECTION_TYPE, connectionType),
249 public void setup() throws InterruptedException {
251 LOG.info("Skipping setUp, already initialized");
257 } catch (Exception e) {
260 //dataBroker = getSession().getSALService(DataBroker.class);
262 DataBroker dataBroker = SouthboundProvider.getDb();
263 Assert.assertNotNull("db should not be null", dataBroker);
265 addressStr = bundleContext.getProperty(SouthboundITConstants.SERVER_IPADDRESS);
266 portStr = bundleContext.getProperty(SouthboundITConstants.SERVER_PORT);
267 connectionType = bundleContext.getProperty(SouthboundITConstants.CONNECTION_TYPE);
269 LOG.info("setUp: Using the following properties: mode= {}, ip:port= {}:{}",
270 connectionType, addressStr, portStr);
271 if (connectionType.equalsIgnoreCase(SouthboundITConstants.CONNECTION_TYPE_ACTIVE)) {
272 if (addressStr == null) {
277 mdsalUtils = new MdsalUtils(dataBroker);
282 * Test passive connection mode. The southbound starts in a listening mode waiting for connections on port
283 * 6640. This test will wait for incoming connections for {@link SouthboundITConstants#CONNECTION_INIT_TIMEOUT} ms.
285 * @throws InterruptedException
288 public void testPassiveNode() throws InterruptedException {
289 if (connectionType.equalsIgnoreCase(SouthboundITConstants.CONNECTION_TYPE_PASSIVE)) {
290 //Wait for CONNECTION_INIT_TIMEOUT for the Passive connection to be initiated by the ovsdb-server.
291 Thread.sleep(SouthboundITConstants.CONNECTION_INIT_TIMEOUT);
295 private ConnectionInfo getConnectionInfo(final String addressStr, final String portStr) {
296 InetAddress inetAddress = null;
298 inetAddress = InetAddress.getByName(addressStr);
299 } catch (UnknownHostException e) {
300 fail("Could not allocate InetAddress: " + e);
303 IpAddress address = SouthboundMapper.createIpAddress(inetAddress);
304 PortNumber port = new PortNumber(Integer.parseInt(portStr));
306 LOG.info("connectionInfo: {}", new ConnectionInfoBuilder()
307 .setRemoteIp(address)
310 return new ConnectionInfoBuilder()
311 .setRemoteIp(address)
316 private String connectionInfoToString(final ConnectionInfo connectionInfo) {
317 return new String(connectionInfo.getRemoteIp().getValue()) + ":" + connectionInfo.getRemotePort().getValue();
321 public void testNetworkTopology() throws InterruptedException {
322 NetworkTopology networkTopology = mdsalUtils.read(LogicalDatastoreType.CONFIGURATION,
323 InstanceIdentifier.create(NetworkTopology.class));
324 Assert.assertNotNull("NetworkTopology could not be found in " + LogicalDatastoreType.CONFIGURATION,
327 networkTopology = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL,
328 InstanceIdentifier.create(NetworkTopology.class));
329 Assert.assertNotNull("NetworkTopology could not be found in " + LogicalDatastoreType.OPERATIONAL,
334 public void testOvsdbTopology() throws InterruptedException {
335 InstanceIdentifier<Topology> path = InstanceIdentifier
336 .create(NetworkTopology.class)
337 .child(Topology.class, new TopologyKey(SouthboundConstants.OVSDB_TOPOLOGY_ID));
339 Topology topology = mdsalUtils.read(LogicalDatastoreType.CONFIGURATION, path);
340 Assert.assertNotNull("Topology could not be found in " + LogicalDatastoreType.CONFIGURATION,
343 topology = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, path);
345 Assert.assertNotNull("Topology could not be found in " + LogicalDatastoreType.OPERATIONAL,
349 private boolean addOvsdbNode(final ConnectionInfo connectionInfo) throws InterruptedException {
350 InstanceIdentifier<Node> iid = createInstanceIdentifier(connectionInfo);
351 // Check that the node doesn't already exist (we don't support connecting twice)
352 Assert.assertNull("The OVSDB node has already been added",
353 mdsalUtils.read(LogicalDatastoreType.CONFIGURATION, iid));
354 boolean result = mdsalUtils.put(LogicalDatastoreType.CONFIGURATION,
356 createNode(connectionInfo));
357 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
361 private InstanceIdentifier<Node> createInstanceIdentifier(
362 ConnectionInfo connectionInfo) {
363 return InstanceIdentifier
364 .create(NetworkTopology.class)
365 .child(Topology.class, new TopologyKey(SouthboundConstants.OVSDB_TOPOLOGY_ID))
367 createNodeKey(connectionInfo.getRemoteIp(), connectionInfo.getRemotePort()));
370 private Node getOvsdbNode(final ConnectionInfo connectionInfo) {
371 return mdsalUtils.read(LogicalDatastoreType.OPERATIONAL,
372 createInstanceIdentifier(connectionInfo));
375 private boolean deleteOvsdbNode(final ConnectionInfo connectionInfo) throws InterruptedException {
376 boolean result = mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION,
377 createInstanceIdentifier(connectionInfo));
378 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
382 private Node connectOvsdbNode(final ConnectionInfo connectionInfo) throws InterruptedException {
383 Assert.assertTrue(addOvsdbNode(connectionInfo));
384 Node node = getOvsdbNode(connectionInfo);
385 Assert.assertNotNull(node);
386 LOG.info("Connected to {}", connectionInfoToString(connectionInfo));
390 private boolean disconnectOvsdbNode(final ConnectionInfo connectionInfo) throws InterruptedException {
391 Assert.assertTrue(deleteOvsdbNode(connectionInfo));
392 Node node = getOvsdbNode(connectionInfo);
393 Assert.assertNull(node);
394 LOG.info("Disconnected from {}", connectionInfoToString(connectionInfo));
399 public void testAddDeleteOvsdbNode() throws InterruptedException {
400 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
401 connectOvsdbNode(connectionInfo);
402 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
406 public void testDpdkSwitch() throws InterruptedException {
407 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
408 Node ovsdbNode = connectOvsdbNode(connectionInfo);
409 List<DatapathTypeEntry> datapathTypeEntries = ovsdbNode.getAugmentation(OvsdbNodeAugmentation.class)
410 .getDatapathTypeEntry();
411 if (datapathTypeEntries == null) {
412 LOG.info("DPDK not supported on this node.");
414 for (DatapathTypeEntry dpTypeEntry : datapathTypeEntries) {
415 Class<? extends DatapathTypeBase> dpType = dpTypeEntry.getDatapathType();
416 String dpTypeStr = SouthboundConstants.DATAPATH_TYPE_MAP.get(dpType);
417 LOG.info("dp type is {}", dpTypeStr);
418 if (dpTypeStr.equals(NETDEV_DP_TYPE)) {
419 LOG.info("Found a DPDK node; adding a corresponding netdev device");
420 InstanceIdentifier<Node> bridgeIid = createInstanceIdentifier(connectionInfo,
421 new OvsdbBridgeName(SouthboundITConstants.BRIDGE_NAME));
422 NodeId bridgeNodeId = createManagedNodeId(bridgeIid);
423 addBridge(connectionInfo, bridgeIid, SouthboundITConstants.BRIDGE_NAME, bridgeNodeId, false, null,
424 true, dpType, null, null, null);
426 // Verify that the device is netdev
427 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
428 Assert.assertNotNull(bridge);
429 Assert.assertEquals(dpType, bridge.getDatapathType());
432 final String TEST_PORT_NAME = "testDPDKPort";
433 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
434 createGenericDpdkOvsdbTerminationPointAugmentationBuilder(TEST_PORT_NAME);
435 Assert.assertTrue(addTerminationPoint(bridgeNodeId, TEST_PORT_NAME, ovsdbTerminationBuilder));
437 // Verify that DPDK port was created
438 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
439 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL,
440 terminationPointIid);
441 Assert.assertNotNull(terminationPointNode);
443 // Verify that each termination point has DPDK ifType
444 Class<? extends InterfaceTypeBase> dpdkIfType = SouthboundConstants.OVSDB_INTERFACE_TYPE_MAP
446 List<TerminationPoint> terminationPoints = terminationPointNode.getTerminationPoint();
447 for (TerminationPoint terminationPoint : terminationPoints) {
448 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation = terminationPoint
449 .getAugmentation(OvsdbTerminationPointAugmentation.class);
450 if (ovsdbTerminationPointAugmentation.getName().equals(TEST_PORT_NAME)) {
451 Class<? extends InterfaceTypeBase> opPort = ovsdbTerminationPointAugmentation
453 Assert.assertEquals(dpdkIfType, opPort);
456 Assert.assertTrue(deleteBridge(connectionInfo));
461 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
465 public void testOvsdbNodeOvsVersion() throws InterruptedException {
466 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
467 Node ovsdbNode = connectOvsdbNode(connectionInfo);
468 OvsdbNodeAugmentation ovsdbNodeAugmentation = ovsdbNode.getAugmentation(OvsdbNodeAugmentation.class);
469 Assert.assertNotNull(ovsdbNodeAugmentation);
470 assertNotNull(ovsdbNodeAugmentation.getOvsVersion());
471 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
475 public void testOpenVSwitchOtherConfig() throws InterruptedException {
476 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
477 Node ovsdbNode = connectOvsdbNode(connectionInfo);
478 OvsdbNodeAugmentation ovsdbNodeAugmentation = ovsdbNode.getAugmentation(OvsdbNodeAugmentation.class);
479 Assert.assertNotNull(ovsdbNodeAugmentation);
480 List<OpenvswitchOtherConfigs> otherConfigsList = ovsdbNodeAugmentation.getOpenvswitchOtherConfigs();
481 if (otherConfigsList != null) {
482 for (OpenvswitchOtherConfigs otherConfig : otherConfigsList) {
483 if (otherConfig.getOtherConfigKey().equals("local_ip")) {
484 LOG.info("local_ip: {}", otherConfig.getOtherConfigValue());
487 LOG.info("other_config {}:{}", otherConfig.getOtherConfigKey(), otherConfig.getOtherConfigValue());
491 LOG.info("other_config is not present");
493 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
497 public void testOvsdbBridgeControllerInfo() throws InterruptedException {
498 ConnectionInfo connectionInfo = getConnectionInfo(addressStr,portStr);
499 Node ovsdbNode = connectOvsdbNode(connectionInfo);
500 String controllerTarget = SouthboundUtil.getControllerTarget(ovsdbNode);
501 assertNotNull("Failed to get controller target", controllerTarget);
502 List<ControllerEntry> setControllerEntry = createControllerEntry(controllerTarget);
503 Uri setUri = new Uri(controllerTarget);
504 Assert.assertTrue(addBridge(connectionInfo, null, SouthboundITConstants.BRIDGE_NAME,null, true,
505 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"), true, null, null,
506 setControllerEntry, null));
507 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
508 Assert.assertNotNull("bridge was not found: " + SouthboundITConstants.BRIDGE_NAME, bridge);
509 Assert.assertNotNull("ControllerEntry was not found: " + setControllerEntry.iterator().next(),
510 bridge.getControllerEntry());
511 List<ControllerEntry> getControllerEntries = bridge.getControllerEntry();
512 for (ControllerEntry entry : getControllerEntries) {
513 if (entry.getTarget() != null) {
514 Assert.assertEquals(setUri.toString(), entry.getTarget().toString());
518 Assert.assertTrue(deleteBridge(connectionInfo));
519 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
522 private List<ControllerEntry> createControllerEntry(String controllerTarget) {
523 List<ControllerEntry> controllerEntriesList = new ArrayList<>();
524 controllerEntriesList.add(new ControllerEntryBuilder()
525 .setTarget(new Uri(controllerTarget))
527 return controllerEntriesList;
530 private void setManagedBy(final OvsdbBridgeAugmentationBuilder ovsdbBridgeAugmentationBuilder,
531 final ConnectionInfo connectionInfo) {
532 InstanceIdentifier<Node> connectionNodePath = createInstanceIdentifier(connectionInfo);
533 ovsdbBridgeAugmentationBuilder.setManagedBy(new OvsdbNodeRef(connectionNodePath));
536 private List<ProtocolEntry> createMdsalProtocols() {
537 List<ProtocolEntry> protocolList = new ArrayList<>();
538 ImmutableBiMap<String, Class<? extends OvsdbBridgeProtocolBase>> mapper =
539 SouthboundConstants.OVSDB_PROTOCOL_MAP.inverse();
540 protocolList.add(new ProtocolEntryBuilder().setProtocol(mapper.get("OpenFlow13")).build());
544 private OvsdbTerminationPointAugmentationBuilder createGenericOvsdbTerminationPointAugmentationBuilder() {
545 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationPointAugmentationBuilder =
546 new OvsdbTerminationPointAugmentationBuilder();
547 ovsdbTerminationPointAugmentationBuilder.setInterfaceType(
548 new InterfaceTypeEntryBuilder()
550 SouthboundMapper.createInterfaceType("internal"))
551 .build().getInterfaceType());
552 return ovsdbTerminationPointAugmentationBuilder;
555 private OvsdbTerminationPointAugmentationBuilder createGenericDpdkOvsdbTerminationPointAugmentationBuilder(
556 final String portName) {
557 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
558 createGenericOvsdbTerminationPointAugmentationBuilder();
559 ovsdbTerminationBuilder.setName(portName);
560 Class<? extends InterfaceTypeBase> ifType = SouthboundConstants.OVSDB_INTERFACE_TYPE_MAP
562 ovsdbTerminationBuilder.setInterfaceType(ifType);
563 return ovsdbTerminationBuilder;
566 private boolean addTerminationPoint(final NodeId bridgeNodeId, final String portName,
567 final OvsdbTerminationPointAugmentationBuilder
568 ovsdbTerminationPointAugmentationBuilder)
569 throws InterruptedException {
571 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(bridgeNodeId);
572 NodeBuilder portNodeBuilder = new NodeBuilder();
573 NodeId portNodeId = SouthboundMapper.createManagedNodeId(portIid);
574 portNodeBuilder.setNodeId(portNodeId);
575 TerminationPointBuilder entry = new TerminationPointBuilder();
576 entry.setKey(new TerminationPointKey(new TpId(portName)));
577 entry.addAugmentation(
578 OvsdbTerminationPointAugmentation.class,
579 ovsdbTerminationPointAugmentationBuilder.build());
580 portNodeBuilder.setTerminationPoint(Lists.newArrayList(entry.build()));
581 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
582 portIid, portNodeBuilder.build());
583 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
588 * base method for adding test bridges. Other helper methods used to create bridges should utilize this method.
590 * @param connectionInfo
591 * @param bridgeIid if passed null, one is created
592 * @param bridgeName cannot be null
593 * @param bridgeNodeId if passed null, one is created based on <code>bridgeIid</code>
594 * @param setProtocolEntries toggles whether default protocol entries are set for the bridge
595 * @param failMode toggles whether default fail mode is set for the bridge
596 * @param setManagedBy toggles whether to setManagedBy for the bridge
597 * @param dpType if passed null, this parameter is ignored
598 * @param externalIds if passed null, this parameter is ignored
599 * @param otherConfig if passed null, this parameter is ignored
600 * @return success of bridge addition
601 * @throws InterruptedException
603 private boolean addBridge(final ConnectionInfo connectionInfo, InstanceIdentifier<Node> bridgeIid,
604 final String bridgeName, NodeId bridgeNodeId, final boolean setProtocolEntries,
605 final Class<? extends OvsdbFailModeBase> failMode, final boolean setManagedBy,
606 final Class<? extends DatapathTypeBase> dpType,
607 final List<BridgeExternalIds> externalIds,
608 final List<ControllerEntry> controllerEntries,
609 final List<BridgeOtherConfigs> otherConfigs) throws InterruptedException {
611 NodeBuilder bridgeNodeBuilder = new NodeBuilder();
612 if (bridgeIid == null) {
613 bridgeIid = createInstanceIdentifier(connectionInfo, new OvsdbBridgeName(bridgeName));
615 if (bridgeNodeId == null) {
616 bridgeNodeId = SouthboundMapper.createManagedNodeId(bridgeIid);
618 bridgeNodeBuilder.setNodeId(bridgeNodeId);
619 OvsdbBridgeAugmentationBuilder ovsdbBridgeAugmentationBuilder = new OvsdbBridgeAugmentationBuilder();
620 ovsdbBridgeAugmentationBuilder.setBridgeName(new OvsdbBridgeName(bridgeName));
621 if (setProtocolEntries) {
622 ovsdbBridgeAugmentationBuilder.setProtocolEntry(createMdsalProtocols());
624 if (failMode != null) {
625 ovsdbBridgeAugmentationBuilder.setFailMode(failMode);
628 setManagedBy(ovsdbBridgeAugmentationBuilder, connectionInfo);
630 if (dpType != null) {
631 ovsdbBridgeAugmentationBuilder.setDatapathType(dpType);
633 if (externalIds != null) {
634 ovsdbBridgeAugmentationBuilder.setBridgeExternalIds(externalIds);
636 if (controllerEntries != null) {
637 ovsdbBridgeAugmentationBuilder.setControllerEntry(controllerEntries);
639 if (otherConfigs != null) {
640 ovsdbBridgeAugmentationBuilder.setBridgeOtherConfigs(otherConfigs);
642 bridgeNodeBuilder.addAugmentation(OvsdbBridgeAugmentation.class, ovsdbBridgeAugmentationBuilder.build());
643 LOG.debug("Built with the intent to store bridge data {}",
644 ovsdbBridgeAugmentationBuilder.toString());
645 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
646 bridgeIid, bridgeNodeBuilder.build());
647 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
651 private boolean addBridge(final ConnectionInfo connectionInfo, final String bridgeName)
652 throws InterruptedException {
654 return addBridge(connectionInfo, null, bridgeName, null, true,
655 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"), true, null, null, null, null);
658 private OvsdbBridgeAugmentation getBridge(ConnectionInfo connectionInfo) {
659 return getBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME);
663 * Extract the <code>store</code> type data store contents for the particular bridge identified by
664 * <code>bridgeName</code>.
666 * @param connectionInfo the connection information
667 * @param bridgeName the bridge name
668 * @param store defined by the <code>LogicalDatastoreType</code> enumeration
669 * @return <code>store</code> type data store contents
671 private OvsdbBridgeAugmentation getBridge(ConnectionInfo connectionInfo, String bridgeName,
672 LogicalDatastoreType store) {
673 Node bridgeNode = getBridgeNode(connectionInfo, bridgeName, store);
674 Assert.assertNotNull(bridgeNode);
675 OvsdbBridgeAugmentation ovsdbBridgeAugmentation = bridgeNode.getAugmentation(OvsdbBridgeAugmentation.class);
676 Assert.assertNotNull(ovsdbBridgeAugmentation);
677 return ovsdbBridgeAugmentation;
681 * extract the <code>LogicalDataStoreType.OPERATIONAL</code> type data store contents for the particular bridge
682 * identified by <code>bridgeName</code>
684 * @param connectionInfo the connection information
685 * @param bridgeName the bridge name
686 * @see <code>SouthboundIT.getBridge(ConnectionInfo, String, LogicalDatastoreType)</code>
687 * @return <code>LogicalDatastoreType.OPERATIONAL</code> type data store contents
689 private OvsdbBridgeAugmentation getBridge(ConnectionInfo connectionInfo, String bridgeName) {
690 return getBridge(connectionInfo, bridgeName, LogicalDatastoreType.OPERATIONAL);
694 * Extract the node contents from <code>store</code> type data store for the
695 * bridge identified by <code>bridgeName</code>
697 * @param connectionInfo the connection information
698 * @param bridgeName the bridge name
699 * @param store defined by the <code>LogicalDatastoreType</code> enumeration
700 * @return <code>store</code> type data store contents
702 private Node getBridgeNode(ConnectionInfo connectionInfo, String bridgeName, LogicalDatastoreType store) {
703 InstanceIdentifier<Node> bridgeIid =
704 createInstanceIdentifier(connectionInfo,
705 new OvsdbBridgeName(bridgeName));
706 return mdsalUtils.read(store, bridgeIid);
710 * Extract the node contents from <code>LogicalDataStoreType.OPERATIONAL</code> data store for the
711 * bridge identified by <code>bridgeName</code>
713 * @param connectionInfo the connection information
714 * @param bridgeName the bridge name
715 * @return <code>LogicalDatastoreType.OPERATIONAL</code> type data store contents
717 private Node getBridgeNode(ConnectionInfo connectionInfo, String bridgeName) {
718 return getBridgeNode(connectionInfo, bridgeName, LogicalDatastoreType.OPERATIONAL);
721 private boolean deleteBridge(ConnectionInfo connectionInfo) throws InterruptedException {
722 return deleteBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME);
725 private boolean deleteBridge(final ConnectionInfo connectionInfo, final String bridgeName)
726 throws InterruptedException {
728 boolean result = mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION,
729 createInstanceIdentifier(connectionInfo,
730 new OvsdbBridgeName(bridgeName)));
731 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
736 public void testAddDeleteBridge() throws InterruptedException {
737 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
738 connectOvsdbNode(connectionInfo);
740 Assert.assertTrue(addBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME));
741 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
742 Assert.assertNotNull(bridge);
743 LOG.info("bridge: {}", bridge);
745 Assert.assertTrue(deleteBridge(connectionInfo));
747 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
750 private InstanceIdentifier<Node> getTpIid(ConnectionInfo connectionInfo, OvsdbBridgeAugmentation bridge) {
751 return createInstanceIdentifier(connectionInfo,
752 bridge.getBridgeName());
756 * Extracts the <code>TerminationPointAugmentation</code> for the <code>index</code> <code>TerminationPoint</code>
757 * on <code>bridgeName</code>
759 * @param connectionInfo the connection information
760 * @param bridgeName the bridge name
761 * @param store defined by the <code>LogicalDatastoreType</code> enumeration
762 * @param index the index we're interested in
763 * @return the augmentation (or {@code null} if none)
765 private OvsdbTerminationPointAugmentation getOvsdbTerminationPointAugmentation(
766 ConnectionInfo connectionInfo, String bridgeName, LogicalDatastoreType store, int index ) {
768 List<TerminationPoint> tpList = getBridgeNode(connectionInfo, bridgeName, store).getTerminationPoint();
769 if (tpList == null) {
772 return tpList.get(index).getAugmentation(OvsdbTerminationPointAugmentation.class);
776 public void testCRDTerminationPointOfPort() throws InterruptedException {
777 final Long OFPORT_EXPECTED = 45002L;
779 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
780 connectOvsdbNode(connectionInfo);
783 Assert.assertTrue(addBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME));
784 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
785 Assert.assertNotNull(bridge);
786 LOG.info("bridge: {}", bridge);
787 NodeId nodeId = SouthboundMapper.createManagedNodeId(createInstanceIdentifier(
788 connectionInfo, bridge.getBridgeName()));
789 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
790 createGenericOvsdbTerminationPointAugmentationBuilder();
791 String portName = "testOfPort";
792 ovsdbTerminationBuilder.setName(portName);
794 ovsdbTerminationBuilder.setOfport(OFPORT_EXPECTED);
795 Assert.assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
796 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
797 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
798 Assert.assertNotNull(terminationPointNode);
801 List<TerminationPoint> terminationPoints = terminationPointNode.getTerminationPoint();
802 for (TerminationPoint terminationPoint : terminationPoints) {
803 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
804 terminationPoint.getAugmentation(OvsdbTerminationPointAugmentation.class);
805 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
806 Long ofPort = ovsdbTerminationPointAugmentation.getOfport();
807 // if ephemeral port 45002 is in use, ofPort is set to 1
808 Assert.assertTrue(ofPort.equals(OFPORT_EXPECTED) || ofPort.equals(new Long(1)));
809 LOG.info("ofPort: {}", ofPort);
813 // UPDATE- Not Applicable. From the OpenVSwitch Documentation:
814 // "A client should ideally set this column’s value in the same database transaction that it uses to create
818 Assert.assertTrue(deleteBridge(connectionInfo));
819 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
823 public void testCRDTerminationPointOfPortRequest() throws InterruptedException {
824 final Long OFPORT_EXPECTED = 45008L;
825 final Long OFPORT_INPUT = 45008L;
827 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
828 connectOvsdbNode(connectionInfo);
831 Assert.assertTrue(addBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME));
832 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
833 Assert.assertNotNull(bridge);
834 NodeId nodeId = createManagedNodeId(createInstanceIdentifier(
835 connectionInfo, bridge.getBridgeName()));
836 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
837 createGenericOvsdbTerminationPointAugmentationBuilder();
838 String portName = "testOfPortRequest";
839 ovsdbTerminationBuilder.setName(portName);
840 Integer ofPortRequestExpected = OFPORT_EXPECTED.intValue();
841 ovsdbTerminationBuilder.setOfport(OFPORT_INPUT);
842 ovsdbTerminationBuilder.setOfportRequest(ofPortRequestExpected);
843 Assert.assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
844 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
845 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
846 Assert.assertNotNull(terminationPointNode);
849 List<TerminationPoint> terminationPoints = terminationPointNode.getTerminationPoint();
850 for (TerminationPoint terminationPoint : terminationPoints) {
851 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
852 terminationPoint.getAugmentation(OvsdbTerminationPointAugmentation.class);
853 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
854 Long ofPort = ovsdbTerminationPointAugmentation.getOfport();
855 // if ephemeral port 45008 is in use, ofPort is set to 1
856 Assert.assertTrue(ofPort.equals(OFPORT_EXPECTED) || ofPort.equals(new Long(1)));
857 LOG.info("ofPort: {}", ofPort);
859 Integer ofPortRequest = ovsdbTerminationPointAugmentation.getOfportRequest();
860 Assert.assertTrue(ofPortRequest.equals(ofPortRequestExpected));
861 LOG.info("ofPortRequest: {}", ofPortRequest);
865 // UPDATE- Not Applicable. From the OpenVSwitch documentation:
866 // "A client should ideally set this column’s value in the same database transaction that it uses to create
870 Assert.assertTrue(deleteBridge(connectionInfo));
871 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
874 private interface KeyValueBuilder<T> {
875 T build(String testName, String key, String value);
876 T[] build(String testName, int count, String key, String value);
880 private abstract static class BaseKeyValueBuilder<T> implements KeyValueBuilder<T> {
881 private static final int COUNTER_START = 0;
882 private int counter = COUNTER_START;
883 private final Class<T> builtClass;
885 protected abstract Builder<T> builder();
887 protected abstract void setKey(Builder<T> builder, String key);
889 protected abstract void setValue(Builder<T> builder, String value);
891 @SuppressWarnings("unchecked")
892 private BaseKeyValueBuilder() {
893 builtClass = (Class<T>) this.getClass().getSuperclass().getTypeParameters()[0].getClass();
897 public final T build(final String testName, final String key, final String value) {
898 final Builder<T> builder = builder();
901 setKey(builder, String.format(FORMAT_STR, testName, key, this.counter));
904 setValue(builder, String.format(FORMAT_STR, testName, value, this.counter));
906 return builder.build();
909 @SuppressWarnings("unchecked")
911 public final T[] build(final String testName, final int count, final String key, final String value) {
912 final T[] instances = (T[]) Array.newInstance(builtClass, count);
913 for (int idx = 0; idx < count; idx++) {
914 instances[idx] = build(testName, key, value);
920 public final void reset() {
921 this.counter = COUNTER_START;
925 private static final class SouthboundPortExternalIdsBuilder extends BaseKeyValueBuilder<PortExternalIds> {
927 protected Builder<PortExternalIds> builder() {
928 return new PortExternalIdsBuilder();
932 protected void setKey(Builder<PortExternalIds> builder, String key) {
933 ((PortExternalIdsBuilder) builder).setExternalIdKey(key);
937 protected void setValue(Builder<PortExternalIds> builder, String value) {
938 ((PortExternalIdsBuilder) builder).setExternalIdValue(value);
942 private static final class SouthboundInterfaceExternalIdsBuilder extends BaseKeyValueBuilder<InterfaceExternalIds> {
944 protected Builder<InterfaceExternalIds> builder() {
945 return new InterfaceExternalIdsBuilder();
949 protected void setKey(Builder<InterfaceExternalIds> builder, String key) {
950 ((InterfaceExternalIdsBuilder) builder).setExternalIdKey(key);
954 protected void setValue(Builder<InterfaceExternalIds> builder, String value) {
955 ((InterfaceExternalIdsBuilder) builder).setExternalIdValue(value);
959 private static final class SouthboundOptionsBuilder extends BaseKeyValueBuilder<Options> {
961 protected Builder<Options> builder() {
962 return new OptionsBuilder();
966 protected void setKey(Builder<Options> builder, String key) {
967 ((OptionsBuilder) builder).setOption(key);
971 protected void setValue(Builder<Options> builder, String value) {
972 ((OptionsBuilder) builder).setValue(value);
976 private static final class SouthboundInterfaceOtherConfigsBuilder extends BaseKeyValueBuilder<InterfaceOtherConfigs> {
978 protected Builder<InterfaceOtherConfigs> builder() {
979 return new InterfaceOtherConfigsBuilder();
983 protected void setKey(Builder<InterfaceOtherConfigs> builder, String key) {
984 ((InterfaceOtherConfigsBuilder) builder).setOtherConfigKey(key);
988 protected void setValue(Builder<InterfaceOtherConfigs> builder, String value) {
989 ((InterfaceOtherConfigsBuilder) builder).setOtherConfigValue(value);
993 private static final class SouthboundPortOtherConfigsBuilder extends BaseKeyValueBuilder<PortOtherConfigs> {
995 protected Builder<PortOtherConfigs> builder() {
996 return new PortOtherConfigsBuilder();
1000 protected void setKey(Builder<PortOtherConfigs> builder, String key) {
1001 ((PortOtherConfigsBuilder) builder).setOtherConfigKey(key);
1005 protected void setValue(Builder<PortOtherConfigs> builder, String value) {
1006 ((PortOtherConfigsBuilder) builder).setOtherConfigValue(value);
1010 private static final class SouthboundBridgeOtherConfigsBuilder extends BaseKeyValueBuilder<BridgeOtherConfigs> {
1012 protected Builder<BridgeOtherConfigs> builder() {
1013 return new BridgeOtherConfigsBuilder();
1017 protected void setKey(Builder<BridgeOtherConfigs> builder, String key) {
1018 ((BridgeOtherConfigsBuilder) builder).setBridgeOtherConfigKey(key);
1022 protected void setValue(Builder<BridgeOtherConfigs> builder, String value) {
1023 ((BridgeOtherConfigsBuilder) builder).setBridgeOtherConfigValue(value);
1027 private static final class SouthboundBridgeExternalIdsBuilder extends BaseKeyValueBuilder<BridgeExternalIds> {
1029 protected Builder<BridgeExternalIds> builder() {
1030 return new BridgeExternalIdsBuilder();
1034 protected void setKey(Builder<BridgeExternalIds> builder, String key) {
1035 ((BridgeExternalIdsBuilder) builder).setBridgeExternalIdKey(key);
1039 protected void setValue(Builder<BridgeExternalIds> builder, String value) {
1040 ((BridgeExternalIdsBuilder) builder).setBridgeExternalIdValue(value);
1045 * Generates the test cases involved in testing key-value-based data. See inline comments for descriptions of
1046 * the particular cases considered.
1048 private static <T> List<SouthboundTestCase<T>> generateKeyValueTestCases(
1049 KeyValueBuilder<T> builder, String idKey, String idValue) {
1050 List<SouthboundTestCase<T>> testCases = new ArrayList<>();
1052 final String GOOD_KEY = "GoodKey";
1053 final String GOOD_VALUE = "GoodValue";
1054 final String NO_VALUE_FOR_KEY = "NoValueForKey";
1055 final String NO_KEY_FOR_VALUE = "NoKeyForValue";
1057 // Test Case 1: TestOne
1058 // Test Type: Positive
1059 // Description: Create a termination point with one value
1060 // Expected: A port is created with the single value specified below
1061 final String testOneName = "TestOne";
1062 testCases.add(new SouthboundTestCaseBuilder<T>()
1064 .input(builder.build(testOneName, idKey, idValue))
1065 .expectInputAsOutput()
1069 // Test Case 2: TestFive
1070 // Test Type: Positive
1071 // Description: Create a termination point with multiple (five) values
1072 // Expected: A port is created with the five values specified below
1073 final String testFiveName = "TestFive";
1074 testCases.add(new SouthboundTestCaseBuilder<T>()
1076 .input(builder.build(testFiveName, 5, idKey, idValue))
1077 .expectInputAsOutput()
1081 // Test Case 3: TestOneGoodOneMalformedValue
1082 // Test Type: Negative
1084 // One perfectly fine input
1085 // (TestOneGoodOneMalformedValue_GoodKey_1,
1086 // TestOneGoodOneMalformedValue_GoodValue_1)
1087 // and one malformed input which only has key specified
1088 // (TestOneGoodOneMalformedValue_NoValueForKey_2,
1090 // Expected: A port is created without any values
1091 final String testOneGoodOneMalformedValueName = "TestOneGoodOneMalformedValue";
1092 testCases.add(new SouthboundTestCaseBuilder<T>()
1093 .name(testOneGoodOneMalformedValueName)
1095 builder.build(testOneGoodOneMalformedValueName, GOOD_KEY, GOOD_VALUE),
1096 builder.build(testOneGoodOneMalformedValueName, NO_VALUE_FOR_KEY, null)
1102 // Test Case 4: TestOneGoodOneMalformedKey
1103 // Test Type: Negative
1105 // One perfectly fine input
1106 // (TestOneGoodOneMalformedKey_GoodKey_1,
1107 // TestOneGoodOneMalformedKey_GoodValue_1)
1108 // and one malformed input which only has value specified
1110 // TestOneGoodOneMalformedKey_NoKeyForValue_2)
1111 // Expected: A port is created without any values
1112 final String testOneGoodOneMalformedKeyName = "TestOneGoodOneMalformedKey";
1113 testCases.add(new SouthboundTestCaseBuilder<T>()
1114 .name(testOneGoodOneMalformedKeyName)
1116 builder.build(testOneGoodOneMalformedKeyName, GOOD_KEY, GOOD_VALUE),
1117 builder.build(testOneGoodOneMalformedKeyName, null, NO_KEY_FOR_VALUE)
1127 * Generates the test cases involved in testing PortExternalIds. See inline comments for descriptions of
1128 * the particular cases considered.
1130 private List<SouthboundTestCase<PortExternalIds>> generatePortExternalIdsTestCases() {
1131 return generateKeyValueTestCases(new SouthboundPortExternalIdsBuilder(), "PortExternalIdKey",
1132 "PortExternalIdValue");
1136 * Tests the CRUD operations for <code>Port</code>
1137 * <code>external_ids</code>.
1139 * @see <code>SouthboundIT.generatePortExternalIdsTestCases()</code> for
1140 * specific test case information
1143 public void testCRUDTerminationPointPortExternalIds()
1144 throws InterruptedException, ExecutionException {
1146 final String TEST_PREFIX = "CRUDTPPortExternalIds";
1148 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1149 connectOvsdbNode(connectionInfo);
1151 // updateFromTestCases represent the original test case value.
1152 // updateToTestCases represent the new value after the update has been
1154 List<SouthboundTestCase<PortExternalIds>> updateFromTestCases = generatePortExternalIdsTestCases();
1155 List<SouthboundTestCase<PortExternalIds>> updateToTestCases = generatePortExternalIdsTestCases();
1156 String testBridgeName;
1157 String testPortName;
1160 // multihreads the test using NUM_THREADS
1161 ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
1162 for (SouthboundTestCase<PortExternalIds> fromTestCase : updateFromTestCases) {
1163 for (SouthboundTestCase<PortExternalIds> toTestCase : updateToTestCases) {
1164 testPortName = testBridgeName = String.format(FORMAT_STR,
1165 TEST_PREFIX, toTestCase.name, counter);
1167 executor.submit(new TestCRUDTerminationPointRunnable<>(
1168 new SouthboundTestHelper<PortExternalIds>() {
1170 public List<PortExternalIds> readValues(
1171 OvsdbTerminationPointAugmentation augmentation) {
1172 return augmentation.getPortExternalIds();
1176 public void writeValues(
1177 OvsdbTerminationPointAugmentationBuilder augmentationBuilder,
1178 List<PortExternalIds> updateFromInput) {
1179 augmentationBuilder.setPortExternalIds(updateFromInput);
1182 connectionInfo, testBridgeName, testPortName,
1183 fromTestCase.inputValues,
1184 fromTestCase.expectedValues,
1185 toTestCase.inputValues,
1186 toTestCase.expectedValues));
1189 executor.shutdown();
1190 executor.awaitTermination(5, TimeUnit.MINUTES);
1191 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1195 * Southbound test helper. Classes implementing this interface are used to provide concrete access to the input and
1196 * output of the underlying augmentation for the type being managed.
1198 * @param <T> The type of data used for the test case.
1200 private interface SouthboundTestHelper<T> {
1202 * Read the values from the augmentation. These would usually be checked against the expected values provided
1203 * for the test case.
1205 * @param augmentation The augmentation to read from.
1206 * @return The values read.
1208 List<T> readValues(OvsdbTerminationPointAugmentation augmentation);
1211 * Write the values to the augmentation (via its builder). This would usually be used to apply the input values
1212 * provided for the test case.
1214 * @param augmentationBuilder The augmentation builder.
1215 * @param values The values to write.
1217 void writeValues(OvsdbTerminationPointAugmentationBuilder augmentationBuilder, List<T> values);
1222 * Test runner used to apply a suite of create/read/update/delete tests. Each instance of a runner expects:
1225 * <li>a helper used to manipulate the appropriate data structures in the termination point augmentation (see
1226 * {@link SouthboundTestHelper});</li>
1227 * <li>connection information for the southbound;</li>
1228 * <li>a name to use for the test bridge (this allows multiple tests to be conducted in parallel against different
1230 * <li>a name to use for the test port;</li>
1231 * <li>the initial input values to use for the termination point augmentation;</li>
1232 * <li>the initial expected values to check the augmentation against;</li>
1233 * <li>the target input values to update the terminal point to;</li>
1234 * <li>the target expected values to check the augmentation point against.</li>
1236 * <p>The following tests are performed:</p>
1238 * <li>the bridge is added;</li>
1239 * <li>the termination point is added, with the provided initial input values;</li>
1240 * <li>the termination point is read from the <em>configuration</em> data store, and checked against the provided
1241 * initial expected values;</li>
1242 * <li>the termination point is read from the <em>operational</em> data store, and checked against the provided
1243 * initial expected values;</li>
1244 * <li>the termination point is updated by merging the provided target input values;</li>
1245 * <li>the termination point is read from the <em>configuration</em> data store, and checked against the provided
1246 * initial <b>and</b> target expected values;</li>
1247 * <li>the termination point is read from the <em>operational</em> data store, and checked against the provided
1248 * initial <b>and</b> target expected values;</li>
1249 * <li>the bridge is deleted.</li>
1252 * @param <T> The type of data used for the test case.
1254 private final class TestCRUDTerminationPointRunnable<T> implements Runnable {
1255 private final SouthboundTestHelper<T> helper;
1256 private final ConnectionInfo connectionInfo;
1257 private final String testBridgeName;
1258 private final String testPortName;
1259 private final List<T> updateFromInput;
1260 private final List<T> updateFromExpected;
1261 private final List<T> updateToInput;
1262 private final List<T> updateToExpected;
1264 private TestCRUDTerminationPointRunnable(
1265 SouthboundTestHelper<T> helper, ConnectionInfo connectionInfo, String testBridgeName,
1266 String testPortName, List<T> updateFromInput, List<T> updateFromExpected, List<T> updateToInput,
1267 List<T> updateToExpected) {
1268 this.helper = helper;
1269 this.connectionInfo = connectionInfo;
1270 this.testBridgeName = testBridgeName;
1271 this.testPortName = testPortName;
1272 this.updateFromInput = updateFromInput;
1273 this.updateFromExpected = updateFromExpected;
1274 this.updateToInput = updateToInput;
1275 this.updateToExpected = updateToExpected;
1281 final int TERMINATION_POINT_TEST_INDEX = 0;
1282 // CREATE: Create the test bridge
1283 Assert.assertTrue(addBridge(connectionInfo, null,
1284 testBridgeName, null, true,
1285 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"),
1286 true, null, null, null, null));
1287 NodeId testBridgeNodeId = createManagedNodeId(createInstanceIdentifier(
1288 connectionInfo, new OvsdbBridgeName(testBridgeName)));
1289 OvsdbTerminationPointAugmentationBuilder tpCreateAugmentationBuilder =
1290 createGenericOvsdbTerminationPointAugmentationBuilder();
1291 tpCreateAugmentationBuilder.setName(testPortName);
1292 helper.writeValues(tpCreateAugmentationBuilder, updateFromInput);
1293 Assert.assertTrue(addTerminationPoint(testBridgeNodeId, testPortName, tpCreateAugmentationBuilder));
1295 // READ: Read the test port and ensure changes are propagated to the CONFIGURATION data store,
1296 // then repeat for OPERATIONAL data store
1297 OvsdbTerminationPointAugmentation updateFromConfigurationTerminationPointAugmentation =
1298 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeName,
1299 LogicalDatastoreType.CONFIGURATION, TERMINATION_POINT_TEST_INDEX);
1300 List<T> updateFromConfiguration = null;
1301 if (updateFromConfigurationTerminationPointAugmentation != null) {
1302 updateFromConfiguration =
1303 helper.readValues(updateFromConfigurationTerminationPointAugmentation);
1305 if (updateFromConfiguration != null) {
1306 Assert.assertTrue(updateFromConfiguration.containsAll(updateFromExpected));
1308 OvsdbTerminationPointAugmentation updateFromOperationalTerminationPointAugmentation =
1309 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeName,
1310 LogicalDatastoreType.OPERATIONAL, TERMINATION_POINT_TEST_INDEX);
1311 List<T> updateFromOperational = null;
1312 if (updateFromOperationalTerminationPointAugmentation != null) {
1313 updateFromOperational = helper.readValues(updateFromOperationalTerminationPointAugmentation);
1315 if (updateFromOperational != null) {
1316 Assert.assertTrue(updateFromOperational.containsAll(updateFromExpected));
1319 // UPDATE: update the external_ids
1320 testBridgeNodeId = getBridgeNode(connectionInfo, testBridgeName).getNodeId();
1321 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1322 new OvsdbTerminationPointAugmentationBuilder();
1323 helper.writeValues(tpUpdateAugmentationBuilder, updateToInput);
1324 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1325 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1326 NodeId portUpdateNodeId = createManagedNodeId(portIid);
1327 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1328 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1329 tpUpdateBuilder.setKey(new TerminationPointKey(new TpId(testPortName)));
1330 tpUpdateBuilder.addAugmentation(
1331 OvsdbTerminationPointAugmentation.class,
1332 tpUpdateAugmentationBuilder.build());
1333 portUpdateNodeBuilder.setTerminationPoint(Lists.newArrayList(tpUpdateBuilder.build()));
1334 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
1335 portIid, portUpdateNodeBuilder.build());
1336 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1337 Assert.assertTrue(result);
1339 // READ: the test port and ensure changes are propagated to the CONFIGURATION data store,
1340 // then repeat for OPERATIONAL data store
1341 OvsdbTerminationPointAugmentation updateToConfigurationTerminationPointAugmentation =
1342 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeName,
1343 LogicalDatastoreType.CONFIGURATION, TERMINATION_POINT_TEST_INDEX);
1344 List<T> updateToConfiguration = helper.readValues(updateToConfigurationTerminationPointAugmentation);
1345 Assert.assertTrue(updateToConfiguration.containsAll(updateToExpected));
1346 Assert.assertTrue(updateToConfiguration.containsAll(updateFromExpected));
1347 OvsdbTerminationPointAugmentation updateToOperationalTerminationPointAugmentation =
1348 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeName,
1349 LogicalDatastoreType.OPERATIONAL, TERMINATION_POINT_TEST_INDEX);
1350 List<T> updateToOperational = helper.readValues(updateToOperationalTerminationPointAugmentation);
1351 Assert.assertTrue(updateToOperational.containsAll(updateToExpected));
1352 Assert.assertTrue(updateToOperational.containsAll(updateFromExpected));
1355 Assert.assertTrue(deleteBridge(connectionInfo, testBridgeName));
1356 } catch (InterruptedException e) {
1357 LOG.error("Test interrupted", e);
1364 * Generates the test cases involved in testing InterfaceExternalIds. See inline comments for descriptions of
1365 * the particular cases considered.
1367 private static List<SouthboundTestCase<InterfaceExternalIds>> generateInterfaceExternalIdsTestCases() {
1368 return generateKeyValueTestCases(new SouthboundInterfaceExternalIdsBuilder(), "IntExternalIdKey",
1369 "IntExternalIdValue");
1373 * Tests the CRUD operations for <code>Interface</code> <code>external_ids</code>.
1375 * @see <code>SouthboundIT.generateInterfaceExternalIdsTestCases()</code> for specific test case information
1378 public void testCRUDTerminationPointInterfaceExternalIds() throws InterruptedException, ExecutionException {
1379 final String TEST_PREFIX = "CRUDTPInterfaceExternalIds";
1381 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1382 connectOvsdbNode(connectionInfo);
1384 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
1385 // the update has been performed.
1386 List<SouthboundTestCase<InterfaceExternalIds>> updateFromTestCases = generateInterfaceExternalIdsTestCases();
1387 List<SouthboundTestCase<InterfaceExternalIds>> updateToTestCases = generateInterfaceExternalIdsTestCases();
1388 String testBridgeName;
1389 String testPortName;
1392 // multithreads the test using NUM_THREADS
1393 ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
1394 for (SouthboundTestCase<InterfaceExternalIds> fromTestCase : updateFromTestCases) {
1395 for (SouthboundTestCase<InterfaceExternalIds> toTestCase : updateToTestCases) {
1396 testPortName = testBridgeName = String.format(FORMAT_STR,
1397 TEST_PREFIX, toTestCase.name, counter);
1399 executor.submit(new TestCRUDTerminationPointRunnable<>(
1400 new SouthboundTestHelper<InterfaceExternalIds>() {
1402 public List<InterfaceExternalIds> readValues(
1403 OvsdbTerminationPointAugmentation augmentation) {
1404 return augmentation.getInterfaceExternalIds();
1408 public void writeValues(
1409 OvsdbTerminationPointAugmentationBuilder augmentationBuilder,
1410 List<InterfaceExternalIds> values) {
1411 augmentationBuilder.setInterfaceExternalIds(values);
1414 connectionInfo, testBridgeName, testPortName,
1415 fromTestCase.inputValues,
1416 fromTestCase.expectedValues,
1417 toTestCase.inputValues,
1418 toTestCase.expectedValues));
1421 executor.shutdown();
1422 executor.awaitTermination(5, TimeUnit.MINUTES);
1423 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1427 * Generates the test cases involved in testing TP Options. See inline comments for descriptions of
1428 * the particular cases considered.
1430 private List<SouthboundTestCase<Options>> generateTerminationPointOptionsTestCases() {
1431 return generateKeyValueTestCases(new SouthboundOptionsBuilder(), "TOPOptionsKey", "TPOptionsValue");
1435 * Tests the CRUD operations for <code>TerminationPoint</code> <code>options</code>.
1437 * @see <code>SouthboundIT.generateTerminationPointOptions()</code> for specific test case information
1440 public void testCRUDTerminationPointOptions() throws InterruptedException {
1441 final String TEST_PREFIX = "CRUDTPOptions";
1443 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1444 connectOvsdbNode(connectionInfo);
1446 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
1447 // the update has been performed.
1448 List<SouthboundTestCase<Options>> updateFromTestCases = generateTerminationPointOptionsTestCases();
1449 List<SouthboundTestCase<Options>> updateToTestCases = generateTerminationPointOptionsTestCases();
1450 String testBridgeName;
1451 String testPortName;
1454 ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
1455 for (SouthboundTestCase<Options> fromTestCase : updateFromTestCases) {
1456 for (SouthboundTestCase<Options> toTestCase : updateToTestCases) {
1457 testPortName = testBridgeName = String.format(FORMAT_STR,
1458 TEST_PREFIX, toTestCase.name, counter);
1460 executor.submit(new TestCRUDTerminationPointRunnable<>(
1461 new SouthboundTestHelper<Options>() {
1463 public List<Options> readValues(
1464 OvsdbTerminationPointAugmentation augmentation) {
1465 return augmentation.getOptions();
1469 public void writeValues(
1470 OvsdbTerminationPointAugmentationBuilder augmentationBuilder,
1471 List<Options> values) {
1472 augmentationBuilder.setOptions(values);
1475 connectionInfo, testBridgeName, testPortName,
1476 fromTestCase.inputValues,
1477 fromTestCase.expectedValues,
1478 toTestCase.inputValues,
1479 toTestCase.expectedValues));
1482 executor.shutdown();
1483 executor.awaitTermination(5, TimeUnit.MINUTES);
1484 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1488 * Generates the test cases involved in testing Interface other_configs. See inline comments for descriptions of
1489 * the particular cases considered.
1491 private List<SouthboundTestCase<InterfaceOtherConfigs>> generateInterfaceOtherConfigsTestCases() {
1492 return generateKeyValueTestCases(new SouthboundInterfaceOtherConfigsBuilder(), "IntOtherConfigsKey",
1493 "IntOtherConfigsValue");
1497 * Tests the CRUD operations for <code>Interface</code> <code>other_configs</code>.
1499 * @see <code>SouthboundIT.generateInterfaceExternalIdsTestCases()</code> for specific test case information
1502 public void testCRUDTerminationPointInterfaceOtherConfigs() throws InterruptedException {
1503 final String TEST_PREFIX = "CRUDTPInterfaceOtherConfigs";
1505 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1506 connectOvsdbNode(connectionInfo);
1508 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
1509 // the update has been performed.
1510 List<SouthboundTestCase<InterfaceOtherConfigs>> updateFromTestCases = generateInterfaceOtherConfigsTestCases();
1511 List<SouthboundTestCase<InterfaceOtherConfigs>> updateToTestCases = generateInterfaceOtherConfigsTestCases();
1512 String testBridgeName;
1513 String testPortName;
1516 ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
1517 for (SouthboundTestCase<InterfaceOtherConfigs> fromTestCase : updateFromTestCases) {
1518 for (SouthboundTestCase<InterfaceOtherConfigs> toTestCase : updateToTestCases) {
1519 testPortName = testBridgeName = String.format(FORMAT_STR,
1520 TEST_PREFIX, toTestCase.name, counter);
1522 executor.submit(new TestCRUDTerminationPointRunnable<>(
1523 new SouthboundTestHelper<InterfaceOtherConfigs>() {
1525 public List<InterfaceOtherConfigs> readValues(
1526 OvsdbTerminationPointAugmentation augmentation) {
1527 return augmentation.getInterfaceOtherConfigs();
1531 public void writeValues(
1532 OvsdbTerminationPointAugmentationBuilder augmentationBuilder,
1533 List<InterfaceOtherConfigs> values) {
1534 augmentationBuilder.setInterfaceOtherConfigs(values);
1537 connectionInfo, testBridgeName, testPortName,
1538 fromTestCase.inputValues,
1539 fromTestCase.expectedValues,
1540 toTestCase.inputValues,
1541 toTestCase.expectedValues));
1544 executor.shutdown();
1545 executor.awaitTermination(5, TimeUnit.MINUTES);
1546 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1550 * Generates the test cases involved in testing Port other_configs. See inline comments for descriptions of
1551 * the particular cases considered.
1553 private List<SouthboundTestCase<PortOtherConfigs>> generatePortOtherConfigsTestCases() {
1554 return generateKeyValueTestCases(new SouthboundPortOtherConfigsBuilder(), "PortOtherConfigsKey",
1555 "PortOtherConfigsValue");
1559 * Tests the CRUD operations for <code>Port</code> <code>other_configs</code>.
1561 * @see <code>SouthboundIT.generatePortExternalIdsTestCases()</code> for specific test case information
1564 public void testCRUDTerminationPointPortOtherConfigs() throws InterruptedException {
1565 final String TEST_PREFIX = "CRUDTPPortOtherConfigs";
1567 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1568 connectOvsdbNode(connectionInfo);
1570 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
1571 // the update has been performed.
1572 List<SouthboundTestCase<PortOtherConfigs>> updateFromTestCases = generatePortOtherConfigsTestCases();
1573 List<SouthboundTestCase<PortOtherConfigs>> updateToTestCases = generatePortOtherConfigsTestCases();
1574 String testBridgeName;
1575 String testPortName;
1578 ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
1579 for (SouthboundTestCase<PortOtherConfigs> fromTestCase : updateFromTestCases) {
1580 for (SouthboundTestCase<PortOtherConfigs> toTestCase : updateToTestCases) {
1581 testPortName = testBridgeName = String.format(FORMAT_STR,
1582 TEST_PREFIX, toTestCase.name, counter);
1584 executor.submit(new TestCRUDTerminationPointRunnable<>(
1585 new SouthboundTestHelper<PortOtherConfigs>() {
1587 public List<PortOtherConfigs> readValues(
1588 OvsdbTerminationPointAugmentation augmentation) {
1589 return augmentation.getPortOtherConfigs();
1593 public void writeValues(
1594 OvsdbTerminationPointAugmentationBuilder augmentationBuilder,
1595 List<PortOtherConfigs> values) {
1596 augmentationBuilder.setPortOtherConfigs(values);
1599 connectionInfo, testBridgeName, testPortName,
1600 fromTestCase.inputValues,
1601 fromTestCase.expectedValues,
1602 toTestCase.inputValues,
1603 toTestCase.expectedValues));
1606 executor.shutdown();
1607 executor.awaitTermination(5, TimeUnit.MINUTES);
1608 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1612 public void testCRUDTerminationPointVlan() throws InterruptedException {
1613 final Integer CREATED_VLAN_ID = 4000;
1614 final Integer UPDATED_VLAN_ID = 4001;
1616 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1617 connectOvsdbNode(connectionInfo);
1620 Assert.assertTrue(addBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME));
1621 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME);
1622 Assert.assertNotNull(bridge);
1623 NodeId nodeId = createManagedNodeId(createInstanceIdentifier(
1624 connectionInfo, bridge.getBridgeName()));
1625 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1626 createGenericOvsdbTerminationPointAugmentationBuilder();
1627 String portName = "testTerminationPointVlanId";
1628 ovsdbTerminationBuilder.setName(portName);
1629 ovsdbTerminationBuilder.setVlanTag(new VlanId(CREATED_VLAN_ID));
1630 Assert.assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1631 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1632 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1633 Assert.assertNotNull(terminationPointNode);
1636 List<TerminationPoint> terminationPoints = terminationPointNode.getTerminationPoint();
1637 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation;
1638 for (TerminationPoint terminationPoint : terminationPoints) {
1639 ovsdbTerminationPointAugmentation = terminationPoint.getAugmentation(
1640 OvsdbTerminationPointAugmentation.class);
1641 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1642 VlanId actualVlanId = ovsdbTerminationPointAugmentation.getVlanTag();
1643 Assert.assertNotNull(actualVlanId);
1644 Integer actualVlanIdInt = actualVlanId.getValue();
1645 Assert.assertEquals(CREATED_VLAN_ID, actualVlanIdInt);
1650 NodeId testBridgeNodeId = getBridgeNode(connectionInfo, SouthboundITConstants.BRIDGE_NAME).getNodeId();
1651 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1652 new OvsdbTerminationPointAugmentationBuilder();
1653 tpUpdateAugmentationBuilder.setVlanTag(new VlanId(UPDATED_VLAN_ID));
1654 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1655 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1656 NodeId portUpdateNodeId = createManagedNodeId(portIid);
1657 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1658 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1659 tpUpdateBuilder.setKey(new TerminationPointKey(new TpId(portName)));
1660 tpUpdateBuilder.addAugmentation(
1661 OvsdbTerminationPointAugmentation.class,
1662 tpUpdateAugmentationBuilder.build());
1663 tpUpdateBuilder.setTpId(new TpId(portName));
1664 portUpdateNodeBuilder.setTerminationPoint(Lists.newArrayList(tpUpdateBuilder.build()));
1665 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
1666 portIid, portUpdateNodeBuilder.build());
1667 Assert.assertTrue(result);
1668 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1670 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1671 terminationPoints = terminationPointNode.getTerminationPoint();
1672 for (TerminationPoint terminationPoint : terminationPoints) {
1673 ovsdbTerminationPointAugmentation = terminationPoint.getAugmentation(
1674 OvsdbTerminationPointAugmentation.class);
1675 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1676 VlanId actualVlanId = ovsdbTerminationPointAugmentation.getVlanTag();
1677 Assert.assertNotNull(actualVlanId);
1678 Integer actualVlanIdInt = actualVlanId.getValue();
1679 Assert.assertEquals(UPDATED_VLAN_ID, actualVlanIdInt);
1684 Assert.assertTrue(deleteBridge(connectionInfo));
1685 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1689 public void testCRUDTerminationPointVlanModes() throws InterruptedException {
1690 final VlanMode UPDATED_VLAN_MODE = VlanMode.Access;
1691 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1692 connectOvsdbNode(connectionInfo);
1693 VlanMode []vlanModes = VlanMode.values();
1694 for (VlanMode vlanMode : vlanModes) {
1696 Assert.assertTrue(addBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME));
1697 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1698 Assert.assertNotNull(bridge);
1699 NodeId nodeId = createManagedNodeId(createInstanceIdentifier(
1700 connectionInfo, bridge.getBridgeName()));
1701 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1702 createGenericOvsdbTerminationPointAugmentationBuilder();
1703 String portName = "testTerminationPointVlanMode" + vlanMode.toString();
1704 ovsdbTerminationBuilder.setName(portName);
1705 ovsdbTerminationBuilder.setVlanMode(vlanMode);
1706 Assert.assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1707 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1708 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1709 Assert.assertNotNull(terminationPointNode);
1712 List<TerminationPoint> terminationPoints = terminationPointNode.getTerminationPoint();
1713 for (TerminationPoint terminationPoint : terminationPoints) {
1714 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1715 terminationPoint.getAugmentation(OvsdbTerminationPointAugmentation.class);
1716 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1718 Assert.assertTrue(ovsdbTerminationPointAugmentation.getVlanMode().equals(vlanMode));
1723 NodeId testBridgeNodeId = getBridgeNode(connectionInfo, SouthboundITConstants.BRIDGE_NAME).getNodeId();
1724 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1725 new OvsdbTerminationPointAugmentationBuilder();
1726 tpUpdateAugmentationBuilder.setVlanMode(UPDATED_VLAN_MODE);
1727 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1728 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1729 NodeId portUpdateNodeId = createManagedNodeId(portIid);
1730 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1731 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1732 tpUpdateBuilder.setKey(new TerminationPointKey(new TpId(portName)));
1733 tpUpdateBuilder.addAugmentation(
1734 OvsdbTerminationPointAugmentation.class,
1735 tpUpdateAugmentationBuilder.build());
1736 tpUpdateBuilder.setTpId(new TpId(portName));
1737 portUpdateNodeBuilder.setTerminationPoint(Lists.newArrayList(tpUpdateBuilder.build()));
1738 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
1739 portIid, portUpdateNodeBuilder.build());
1740 Assert.assertTrue(result);
1741 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1743 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1744 terminationPoints = terminationPointNode.getTerminationPoint();
1745 for (TerminationPoint terminationPoint : terminationPoints) {
1746 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1747 terminationPoint.getAugmentation(OvsdbTerminationPointAugmentation.class);
1748 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1750 Assert.assertEquals(UPDATED_VLAN_MODE, ovsdbTerminationPointAugmentation.getVlanMode());
1755 Assert.assertTrue(deleteBridge(connectionInfo));
1757 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1760 private ArrayList<Set<Integer>> generateVlanSets() {
1761 ArrayList<Set<Integer>> vlanSets = new ArrayList<>();
1763 Set<Integer> emptySet = new HashSet<>();
1764 vlanSets.add(emptySet);
1766 Set<Integer> singleSet = new HashSet<>();
1767 Integer single = 2222;
1768 singleSet.add(single);
1769 vlanSets.add(singleSet);
1771 Set<Integer> minMaxMiddleSet = new HashSet<>();
1773 minMaxMiddleSet.add(min);
1775 minMaxMiddleSet.add(max);
1776 Integer minPlusOne = min + 1;
1777 minMaxMiddleSet.add(minPlusOne);
1778 Integer maxMinusOne = max - 1;
1779 minMaxMiddleSet.add(maxMinusOne);
1780 Integer middle = (max - min) / 2;
1781 minMaxMiddleSet.add(middle);
1782 vlanSets.add(minMaxMiddleSet);
1787 private List<Trunks> buildTrunkList(Set<Integer> trunkSet) {
1788 List<Trunks> trunkList = Lists.newArrayList();
1789 for (Integer trunk : trunkSet) {
1790 TrunksBuilder trunkBuilder = new TrunksBuilder();
1791 trunkBuilder.setTrunk(new VlanId(trunk));
1792 trunkList.add(trunkBuilder.build());
1798 public void testCRUDTerminationPointVlanTrunks() throws InterruptedException {
1799 final List<Trunks> UPDATED_TRUNKS = buildTrunkList(Sets.newHashSet(2011));
1800 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1801 connectOvsdbNode(connectionInfo);
1802 Iterable<Set<Integer>> vlanSets = generateVlanSets();
1804 for (Set<Integer> vlanSet : vlanSets) {
1807 Assert.assertTrue(addBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME));
1808 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1809 Assert.assertNotNull(bridge);
1810 NodeId nodeId = createManagedNodeId(createInstanceIdentifier(
1811 connectionInfo, bridge.getBridgeName()));
1812 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1813 createGenericOvsdbTerminationPointAugmentationBuilder();
1814 String portName = "testTerminationPointVlanTrunks" + testCase;
1815 ovsdbTerminationBuilder.setName(portName);
1816 List<Trunks> trunks = buildTrunkList(vlanSet);
1817 ovsdbTerminationBuilder.setTrunks(trunks);
1818 Assert.assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1819 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1820 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1821 Assert.assertNotNull(terminationPointNode);
1824 List<TerminationPoint> terminationPoints = terminationPointNode.getTerminationPoint();
1825 for (TerminationPoint terminationPoint : terminationPoints) {
1826 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1827 terminationPoint.getAugmentation(OvsdbTerminationPointAugmentation.class);
1828 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1829 List<Trunks> actualTrunks = ovsdbTerminationPointAugmentation.getTrunks();
1830 for (Trunks trunk : trunks) {
1831 Assert.assertTrue(actualTrunks.contains(trunk));
1838 NodeId testBridgeNodeId = getBridgeNode(connectionInfo, SouthboundITConstants.BRIDGE_NAME).getNodeId();
1839 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1840 new OvsdbTerminationPointAugmentationBuilder();
1841 tpUpdateAugmentationBuilder.setTrunks(UPDATED_TRUNKS);
1842 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1843 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1844 NodeId portUpdateNodeId = createManagedNodeId(portIid);
1845 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1846 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1847 tpUpdateBuilder.setKey(new TerminationPointKey(new TpId(portName)));
1848 tpUpdateBuilder.addAugmentation(
1849 OvsdbTerminationPointAugmentation.class,
1850 tpUpdateAugmentationBuilder.build());
1851 tpUpdateBuilder.setTpId(new TpId(portName));
1852 portUpdateNodeBuilder.setTerminationPoint(Lists.newArrayList(tpUpdateBuilder.build()));
1853 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
1854 portIid, portUpdateNodeBuilder.build());
1855 Assert.assertTrue(result);
1856 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1858 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1859 terminationPoints = terminationPointNode.getTerminationPoint();
1860 for (TerminationPoint terminationPoint : terminationPoints) {
1861 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1862 terminationPoint.getAugmentation(OvsdbTerminationPointAugmentation.class);
1863 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1865 Assert.assertEquals(UPDATED_TRUNKS, ovsdbTerminationPointAugmentation.getTrunks());
1870 Assert.assertTrue(deleteBridge(connectionInfo));
1872 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1876 public void testGetOvsdbNodes() throws InterruptedException {
1877 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1878 connectOvsdbNode(connectionInfo);
1879 InstanceIdentifier<Topology> topologyPath = InstanceIdentifier
1880 .create(NetworkTopology.class)
1881 .child(Topology.class, new TopologyKey(SouthboundConstants.OVSDB_TOPOLOGY_ID));
1883 Topology topology = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, topologyPath);
1884 InstanceIdentifier<Node> expectedNodeIid = createInstanceIdentifier(connectionInfo);
1885 NodeId expectedNodeId = expectedNodeIid.firstKeyOf(Node.class, NodeKey.class).getNodeId();
1886 Node foundNode = null;
1887 Assert.assertNotNull("Expected to find topology: " + topologyPath, topology);
1888 Assert.assertNotNull("Expected to find some nodes" + topology.getNode());
1889 LOG.info("expectedNodeId: {}, getNode: {}", expectedNodeId, topology.getNode());
1890 for (Node node : topology.getNode()) {
1891 if (node.getNodeId().getValue().equals(expectedNodeId.getValue())) {
1896 Assert.assertNotNull("Expected to find Node: " + expectedNodeId, foundNode);
1897 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1901 * Generates the test cases involved in testing BridgeOtherConfigs. See inline comments for descriptions of
1902 * the particular cases considered.
1904 private List<SouthboundTestCase<BridgeOtherConfigs>> generateBridgeOtherConfigsTestCases() {
1905 return generateKeyValueTestCases(new SouthboundBridgeOtherConfigsBuilder(), "BridgeOtherConfigsKey",
1906 "BridgeOtherConfigsValue");
1910 * @see <code>SouthboundIT.testCRUDBridgeOtherConfigs()</code>
1911 * This is helper test method to compare a test "set" of BridgeExternalIds against an expected "set"
1913 private void assertExpectedBridgeOtherConfigsExist( List<BridgeOtherConfigs> expected,
1914 List<BridgeOtherConfigs> test ) {
1916 if (expected != null) {
1917 for (BridgeOtherConfigs expectedOtherConfig : expected) {
1918 Assert.assertTrue(test.contains(expectedOtherConfig));
1924 * @see <code>SouthboundIT.generateBridgeOtherConfigsTestCases()</code> for specific test case information.
1927 public void testCRUDBridgeOtherConfigs() throws InterruptedException {
1928 final String TEST_BRIDGE_PREFIX = "CRUDBridgeOtherConfigs";
1929 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
1930 connectOvsdbNode(connectionInfo);
1931 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
1932 // the update has been performed.
1933 List<SouthboundTestCase<BridgeOtherConfigs>> updateFromTestCases = generateBridgeOtherConfigsTestCases();
1934 List<SouthboundTestCase<BridgeOtherConfigs>> updateToTestCases = generateBridgeOtherConfigsTestCases();
1935 String testBridgeName;
1938 ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
1939 for (SouthboundTestCase<BridgeOtherConfigs> fromTestCase : updateFromTestCases) {
1940 for (SouthboundTestCase<BridgeOtherConfigs> toTestCase : updateToTestCases) {
1941 testBridgeName = String.format(FORMAT_STR, TEST_BRIDGE_PREFIX, toTestCase.name, counter);
1943 TestCRUDBridgeOtherConfigsRunnable testRunnable =
1944 new TestCRUDBridgeOtherConfigsRunnable(
1945 connectionInfo, testBridgeName,
1946 fromTestCase.inputValues,
1947 fromTestCase.expectedValues,
1948 toTestCase.inputValues,
1949 toTestCase.expectedValues);
1950 executor.submit(testRunnable);
1953 executor.shutdown();
1954 executor.awaitTermination(5, TimeUnit.MINUTES);
1956 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
1959 class TestCRUDBridgeOtherConfigsRunnable implements Runnable {
1961 ConnectionInfo connectionInfo;
1962 String testBridgeName;
1963 List<BridgeOtherConfigs> updateFromInputOtherConfigs;
1964 List<BridgeOtherConfigs> updateFromExpectedOtherConfigs;
1965 List<BridgeOtherConfigs> updateToInputOtherConfigs;
1966 List<BridgeOtherConfigs> updateToExpectedOtherConfigs;
1968 TestCRUDBridgeOtherConfigsRunnable(
1969 ConnectionInfo connectionInfo, String testBridgeName,
1970 List<BridgeOtherConfigs> updateFromInputOtherConfigs,
1971 List<BridgeOtherConfigs> updateFromExpectedOtherConfigs,
1972 List<BridgeOtherConfigs> updateToInputOtherConfigs,
1973 List<BridgeOtherConfigs> updateToExpectedOtherConfigs) {
1975 this.connectionInfo = connectionInfo;
1976 this.testBridgeName = testBridgeName;
1977 this.updateFromInputOtherConfigs = updateFromInputOtherConfigs;
1978 this.updateFromExpectedOtherConfigs = updateFromExpectedOtherConfigs;
1979 this.updateToInputOtherConfigs = updateToInputOtherConfigs;
1980 this.updateToExpectedOtherConfigs = updateToExpectedOtherConfigs;
1987 } catch (InterruptedException e) {
1988 e.printStackTrace();
1992 public void test() throws InterruptedException {
1993 // CREATE: Create the test bridge
1994 boolean bridgeAdded = addBridge(connectionInfo, null,
1995 testBridgeName, null, true, SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"),
1996 true, null, null, null, updateFromInputOtherConfigs);
1997 Assert.assertTrue(bridgeAdded);
1999 // READ: Read the test bridge and ensure changes are propagated to the CONFIGURATION data store,
2000 // then repeat for OPERATIONAL data store
2001 List<BridgeOtherConfigs> updateFromConfigurationOtherConfigs = getBridge(connectionInfo, testBridgeName,
2002 LogicalDatastoreType.CONFIGURATION).getBridgeOtherConfigs();
2003 assertExpectedBridgeOtherConfigsExist(updateFromExpectedOtherConfigs,
2004 updateFromConfigurationOtherConfigs);
2005 List<BridgeOtherConfigs> updateFromOperationalOtherConfigs = getBridge(connectionInfo, testBridgeName)
2006 .getBridgeOtherConfigs();
2007 assertExpectedBridgeOtherConfigsExist(updateFromExpectedOtherConfigs,
2008 updateFromOperationalOtherConfigs);
2010 // UPDATE: update the external_ids
2011 OvsdbBridgeAugmentationBuilder bridgeAugmentationBuilder = new OvsdbBridgeAugmentationBuilder();
2012 bridgeAugmentationBuilder.setBridgeOtherConfigs(updateToInputOtherConfigs);
2013 InstanceIdentifier<Node> bridgeIid =
2014 createInstanceIdentifier(connectionInfo,
2015 new OvsdbBridgeName(testBridgeName));
2016 NodeBuilder bridgeNodeBuilder = new NodeBuilder();
2017 Node bridgeNode = getBridgeNode(connectionInfo, testBridgeName);
2018 bridgeNodeBuilder.setNodeId(bridgeNode.getNodeId());
2019 bridgeNodeBuilder.setKey(bridgeNode.getKey());
2020 bridgeNodeBuilder.addAugmentation(OvsdbBridgeAugmentation.class, bridgeAugmentationBuilder.build());
2021 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, bridgeIid,
2022 bridgeNodeBuilder.build());
2023 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
2024 Assert.assertTrue(result);
2026 // READ: the test bridge and ensure changes are propagated to the CONFIGURATION data store,
2027 // then repeat for OPERATIONAL data store
2028 List<BridgeOtherConfigs> updateToConfigurationOtherConfigs = getBridge(connectionInfo, testBridgeName,
2029 LogicalDatastoreType.CONFIGURATION).getBridgeOtherConfigs();
2030 assertExpectedBridgeOtherConfigsExist(updateToExpectedOtherConfigs, updateToConfigurationOtherConfigs);
2031 assertExpectedBridgeOtherConfigsExist(updateFromExpectedOtherConfigs,
2032 updateToConfigurationOtherConfigs);
2033 List<BridgeOtherConfigs> updateToOperationalOtherConfigs = getBridge(connectionInfo, testBridgeName)
2034 .getBridgeOtherConfigs();
2035 if (updateFromExpectedOtherConfigs != null) {
2036 assertExpectedBridgeOtherConfigsExist(updateToExpectedOtherConfigs,
2037 updateToOperationalOtherConfigs);
2038 assertExpectedBridgeOtherConfigsExist(updateFromExpectedOtherConfigs,
2039 updateToOperationalOtherConfigs);
2043 Assert.assertTrue(deleteBridge(connectionInfo, testBridgeName));
2048 * Generates the test cases involved in testing BridgeExternalIds. See inline comments for descriptions of
2049 * the particular cases considered.
2051 private List<SouthboundTestCase<BridgeExternalIds>> generateBridgeExternalIdsTestCases() {
2052 return generateKeyValueTestCases(new SouthboundBridgeExternalIdsBuilder(), "BridgeExternalIdsKey",
2053 "BridgeExternalIdsValue");
2057 * @see <code>SouthboundIT.testCRUDBridgeExternalIds()</code>
2058 * This is helper test method to compare a test "set" of BridgeExternalIds against an expected "set"
2060 private void assertExpectedBridgeExternalIdsExist( List<BridgeExternalIds> expected,
2061 List<BridgeExternalIds> test ) {
2063 if (expected != null) {
2064 for (BridgeExternalIds expectedExternalId : expected) {
2065 Assert.assertTrue(test.contains(expectedExternalId));
2071 * @see <code>SouthboundIT.generateBridgeExternalIdsTestCases()</code> for specific test case information
2074 public void testCRUDBridgeExternalIds() throws InterruptedException {
2075 final String TEST_BRIDGE_PREFIX = "CRUDBridgeExternalIds";
2076 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portStr);
2077 connectOvsdbNode(connectionInfo);
2078 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
2079 // the update has been performed.
2080 List<SouthboundTestCase<BridgeExternalIds>> updateFromTestCases = generateBridgeExternalIdsTestCases();
2081 List<SouthboundTestCase<BridgeExternalIds>> updateToTestCases = generateBridgeExternalIdsTestCases();
2082 String testBridgeName;
2085 ExecutorService executor = Executors.newFixedThreadPool(NUM_THREADS);
2086 for (SouthboundTestCase<BridgeExternalIds> fromTestCase : updateFromTestCases) {
2087 for (SouthboundTestCase<BridgeExternalIds> toTestCase : updateToTestCases) {
2088 testBridgeName = String.format(FORMAT_STR, TEST_BRIDGE_PREFIX, toTestCase.name, counter);
2090 TestCRUDBridgeExternalIdsRunnable testRunnable =
2091 new TestCRUDBridgeExternalIdsRunnable(
2092 connectionInfo, testBridgeName,
2093 fromTestCase.inputValues,
2094 fromTestCase.expectedValues,
2095 toTestCase.inputValues,
2096 toTestCase.expectedValues);
2097 executor.submit(testRunnable);
2100 executor.shutdown();
2101 executor.awaitTermination(5, TimeUnit.MINUTES);
2103 Assert.assertTrue(disconnectOvsdbNode(connectionInfo));
2106 class TestCRUDBridgeExternalIdsRunnable implements Runnable {
2107 ConnectionInfo connectionInfo;
2108 String testBridgeName;
2109 List<BridgeExternalIds> updateFromInputExternalIds;
2110 List<BridgeExternalIds> updateFromExpectedExternalIds;
2111 List<BridgeExternalIds> updateToInputExternalIds;
2112 List<BridgeExternalIds> updateToExpectedExternalIds;
2114 TestCRUDBridgeExternalIdsRunnable(
2115 ConnectionInfo connectionInfo, String testBridgeName,
2116 List<BridgeExternalIds> updateFromInputExternalIds,
2117 List<BridgeExternalIds> updateFromExpectedExternalIds,
2118 List<BridgeExternalIds> updateToInputExternalIds,
2119 List<BridgeExternalIds> updateToExpectedExternalIds) {
2121 this.connectionInfo = connectionInfo;
2122 this.testBridgeName = testBridgeName;
2123 this.updateFromInputExternalIds = updateFromInputExternalIds;
2124 this.updateFromExpectedExternalIds = updateFromExpectedExternalIds;
2125 this.updateToInputExternalIds = updateToInputExternalIds;
2126 this.updateToExpectedExternalIds = updateToExpectedExternalIds;
2133 } catch (InterruptedException e) {
2134 e.printStackTrace();
2138 public void test() throws InterruptedException {
2139 // CREATE: Create the test bridge
2140 boolean bridgeAdded = addBridge(connectionInfo, null,
2141 testBridgeName, null, true, SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"),
2142 true, null, updateFromInputExternalIds, null, null);
2143 Assert.assertTrue(bridgeAdded);
2145 // READ: Read the test bridge and ensure changes are propagated to the CONFIGURATION data store,
2146 // then repeat for OPERATIONAL data store
2147 List<BridgeExternalIds> updateFromConfigurationExternalIds = getBridge(connectionInfo, testBridgeName,
2148 LogicalDatastoreType.CONFIGURATION).getBridgeExternalIds();
2149 assertExpectedBridgeExternalIdsExist(updateFromExpectedExternalIds, updateFromConfigurationExternalIds);
2150 List<BridgeExternalIds> updateFromOperationalExternalIds = getBridge(connectionInfo, testBridgeName)
2151 .getBridgeExternalIds();
2152 assertExpectedBridgeExternalIdsExist(updateFromExpectedExternalIds, updateFromOperationalExternalIds);
2154 // UPDATE: update the external_ids
2155 OvsdbBridgeAugmentationBuilder bridgeAugmentationBuilder = new OvsdbBridgeAugmentationBuilder();
2156 bridgeAugmentationBuilder.setBridgeExternalIds(updateToInputExternalIds);
2157 InstanceIdentifier<Node> bridgeIid =
2158 createInstanceIdentifier(connectionInfo,
2159 new OvsdbBridgeName(testBridgeName));
2160 NodeBuilder bridgeNodeBuilder = new NodeBuilder();
2161 Node bridgeNode = getBridgeNode(connectionInfo, testBridgeName);
2162 bridgeNodeBuilder.setNodeId(bridgeNode.getNodeId());
2163 bridgeNodeBuilder.setKey(bridgeNode.getKey());
2164 bridgeNodeBuilder.addAugmentation(OvsdbBridgeAugmentation.class, bridgeAugmentationBuilder.build());
2165 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, bridgeIid,
2166 bridgeNodeBuilder.build());
2167 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
2168 Assert.assertTrue(result);
2170 // READ: the test bridge and ensure changes are propagated to the CONFIGURATION data store,
2171 // then repeat for OPERATIONAL data store
2172 List<BridgeExternalIds> updateToConfigurationExternalIds = getBridge(connectionInfo, testBridgeName,
2173 LogicalDatastoreType.CONFIGURATION).getBridgeExternalIds();
2174 assertExpectedBridgeExternalIdsExist(updateToExpectedExternalIds, updateToConfigurationExternalIds);
2175 assertExpectedBridgeExternalIdsExist(updateFromExpectedExternalIds, updateToConfigurationExternalIds);
2176 List<BridgeExternalIds> updateToOperationalExternalIds = getBridge(connectionInfo, testBridgeName)
2177 .getBridgeExternalIds();
2178 if (updateFromExpectedExternalIds != null) {
2179 assertExpectedBridgeExternalIdsExist(updateToExpectedExternalIds, updateToOperationalExternalIds);
2180 assertExpectedBridgeExternalIdsExist(updateFromExpectedExternalIds, updateToOperationalExternalIds);
2184 Assert.assertTrue(deleteBridge(connectionInfo, testBridgeName));
2188 public static InstanceIdentifier<Node> createInstanceIdentifier(ConnectionInfo key,OvsdbBridgeName bridgeName) {
2189 return SouthboundMapper.createInstanceIdentifier(createManagedNodeId(key, bridgeName));
2192 public static NodeId createManagedNodeId(ConnectionInfo key, OvsdbBridgeName bridgeName) {
2193 return createManagedNodeId(key.getRemoteIp(), key.getRemotePort(), bridgeName);
2196 public static NodeId createManagedNodeId(IpAddress ip, PortNumber port, OvsdbBridgeName bridgeName) {
2197 return new NodeId(createNodeId(ip,port).getValue()
2198 + "/" + SouthboundConstants.BRIDGE_URI_PREFIX + "/" + bridgeName.getValue());
2201 public static NodeId createNodeId(IpAddress ip, PortNumber port) {
2202 String uriString = SouthboundConstants.OVSDB_URI_PREFIX + "://"
2203 + new String(ip.getValue()) + ":" + port.getValue();
2204 Uri uri = new Uri(uriString);
2205 return new NodeId(uri);
2208 public static NodeKey createNodeKey(IpAddress ip, PortNumber port) {
2209 return new NodeKey(createNodeId(ip,port));
2212 public static Node createNode(ConnectionInfo key) {
2213 NodeBuilder nodeBuilder = new NodeBuilder();
2214 nodeBuilder.setNodeId(createNodeId(key.getRemoteIp(),key.getRemotePort()));
2215 nodeBuilder.addAugmentation(OvsdbNodeAugmentation.class, createOvsdbAugmentation(key));
2216 return nodeBuilder.build();
2219 public static OvsdbNodeAugmentation createOvsdbAugmentation(ConnectionInfo key) {
2220 OvsdbNodeAugmentationBuilder ovsdbNodeBuilder = new OvsdbNodeAugmentationBuilder();
2221 ovsdbNodeBuilder.setConnectionInfo(key);
2222 return ovsdbNodeBuilder.build();
2225 public static NodeId createManagedNodeId(InstanceIdentifier<Node> iid) {
2226 NodeKey nodeKey = iid.firstKeyOf(Node.class, NodeKey.class);
2227 return nodeKey.getNodeId();
2232 * Representation of a southbound test case. Each test case has a name, a list of input values and a list of
2233 * expected values. The input values are provided to the augmentation builder, and the expected values are checked
2234 * against the output of the resulting augmentation.
2237 * Instances of this class are immutable.
2240 * @param <T> The type of data used for the test case.
2242 private static final class SouthboundTestCase<T> {
2243 private final String name;
2244 private final List<T> inputValues;
2245 private final List<T> expectedValues;
2248 * Creates an instance of a southbound test case.
2250 * @param name The test case's name.
2251 * @param inputValues The input values (provided as input to the underlying augmentation builder).
2252 * @param expectedValues The expected values (checked against the output of the underlying augmentation).
2254 public SouthboundTestCase(
2255 final String name, final List<T> inputValues, final List<T> expectedValues) {
2257 this.inputValues = inputValues;
2258 this.expectedValues = expectedValues;
2263 * Southbound test case builder.
2265 * @param <T> The type of data used for the test case.
2267 private static final class SouthboundTestCaseBuilder<T> {
2268 private String name;
2269 private List<T> inputValues;
2270 private List<T> expectedValues;
2273 * Creates a builder. Builders may be reused, the generated immutable instances are independent of the
2274 * builders. There are no default values.
2276 public SouthboundTestCaseBuilder() {
2281 * Sets the test case's name.
2283 * @param name The test case's name.
2284 * @return The builder.
2286 public SouthboundTestCaseBuilder<T> name(final String name) {
2292 * Sets the input values.
2294 * @param inputValues The input values.
2295 * @return The builder.
2298 public final SouthboundTestCaseBuilder<T> input(final T... inputValues) {
2299 this.inputValues = Lists.newArrayList(inputValues);
2304 * Sets the expected output values.
2306 * @param expectedValues The expected output values.
2307 * @return The builder.
2310 public final SouthboundTestCaseBuilder<T> expect(final T... expectedValues) {
2311 this.expectedValues = Lists.newArrayList(expectedValues);
2316 * Indicates that the provided input values should be expected as output values.
2318 * @return The builder.
2320 public SouthboundTestCaseBuilder<T> expectInputAsOutput() {
2321 this.expectedValues = this.inputValues;
2326 * Builds an immutable instance representing the test case.
2328 * @return The test case.
2330 @SuppressWarnings("unchecked")
2331 public SouthboundTestCase<T> build() {
2332 return new SouthboundTestCase<>(name, inputValues, expectedValues);