2 * Copyright © 2015, 2017 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.assertEquals;
11 import static org.junit.Assert.assertFalse;
12 import static org.junit.Assert.assertNotNull;
13 import static org.junit.Assert.assertNull;
14 import static org.junit.Assert.assertTrue;
15 import static org.junit.Assert.fail;
16 import static org.junit.Assume.assumeFalse;
17 import static org.ops4j.pax.exam.CoreOptions.composite;
18 import static org.ops4j.pax.exam.CoreOptions.maven;
19 import static org.ops4j.pax.exam.CoreOptions.propagateSystemProperties;
20 import static org.ops4j.pax.exam.CoreOptions.vmOption;
21 import static org.ops4j.pax.exam.karaf.options.KarafDistributionOption.editConfigurationFilePut;
22 import static org.ops4j.pax.exam.karaf.options.KarafDistributionOption.keepRuntimeFolder;
24 import com.google.common.collect.ImmutableBiMap;
25 import com.google.common.collect.Iterables;
26 import com.google.common.collect.Lists;
27 import com.google.common.collect.Sets;
28 import java.lang.annotation.Annotation;
29 import java.lang.reflect.Method;
30 import java.net.InetAddress;
31 import java.net.UnknownHostException;
32 import java.util.ArrayList;
33 import java.util.Collection;
34 import java.util.Collections;
35 import java.util.HashSet;
36 import java.util.List;
38 import java.util.Properties;
40 import javax.inject.Inject;
41 import org.eclipse.jdt.annotation.NonNull;
42 import org.eclipse.jdt.annotation.Nullable;
43 import org.junit.After;
44 import org.junit.Before;
45 import org.junit.Ignore;
46 import org.junit.Test;
47 import org.junit.internal.AssumptionViolatedException;
48 import org.junit.runner.RunWith;
49 import org.opendaylight.controller.mdsal.it.base.AbstractMdsalTestBase;
50 import org.opendaylight.mdsal.binding.api.DataBroker;
51 import org.opendaylight.mdsal.binding.api.DataObjectModification;
52 import org.opendaylight.mdsal.binding.api.DataTreeChangeListener;
53 import org.opendaylight.mdsal.binding.api.DataTreeIdentifier;
54 import org.opendaylight.mdsal.binding.api.DataTreeModification;
55 import org.opendaylight.mdsal.common.api.LogicalDatastoreType;
56 import org.opendaylight.ovsdb.lib.notation.Version;
57 import org.opendaylight.ovsdb.southbound.SouthboundConstants;
58 import org.opendaylight.ovsdb.southbound.SouthboundMapper;
59 import org.opendaylight.ovsdb.southbound.SouthboundUtil;
60 import org.opendaylight.ovsdb.utils.mdsal.utils.MdsalUtils;
61 import org.opendaylight.ovsdb.utils.southbound.utils.SouthboundUtils;
62 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.IpAddress;
63 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.PortNumber;
64 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Uri;
65 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Uuid;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.VlanId;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.DatapathTypeBase;
68 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.InterfaceTypeBase;
69 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeAugmentation;
70 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeAugmentationBuilder;
71 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeName;
72 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbBridgeProtocolBase;
73 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbFailModeBase;
74 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbNodeAugmentation;
75 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbNodeRef;
76 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbPortInterfaceAttributes.VlanMode;
77 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbQueueRef;
78 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbTerminationPointAugmentation;
79 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.OvsdbTerminationPointAugmentationBuilder;
80 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.QosTypeBase;
81 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeExternalIds;
82 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeExternalIdsBuilder;
83 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeExternalIdsKey;
84 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeOtherConfigs;
85 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeOtherConfigsBuilder;
86 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.BridgeOtherConfigsKey;
87 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ControllerEntry;
88 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ControllerEntryBuilder;
89 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ControllerEntryKey;
90 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ProtocolEntry;
91 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ProtocolEntryBuilder;
92 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.bridge.attributes.ProtocolEntryKey;
93 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.Autoattach;
94 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.AutoattachBuilder;
95 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.AutoattachKey;
96 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.ConnectionInfo;
97 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.ConnectionInfoBuilder;
98 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.DatapathTypeEntry;
99 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.DatapathTypeEntryKey;
100 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.InterfaceTypeEntryBuilder;
101 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.ManagedNodeEntry;
102 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.OpenvswitchOtherConfigs;
103 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.OpenvswitchOtherConfigsKey;
104 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.QosEntries;
105 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.QosEntriesBuilder;
106 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.QosEntriesKey;
107 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.Queues;
108 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.QueuesBuilder;
109 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.QueuesKey;
110 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.autoattach.AutoattachExternalIds;
111 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.autoattach.AutoattachExternalIdsBuilder;
112 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.autoattach.AutoattachExternalIdsKey;
113 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.autoattach.Mappings;
114 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.autoattach.MappingsBuilder;
115 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.autoattach.MappingsKey;
116 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QosExternalIds;
117 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QosExternalIdsBuilder;
118 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QosExternalIdsKey;
119 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QosOtherConfig;
120 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QosOtherConfigBuilder;
121 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QosOtherConfigKey;
122 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QueueList;
123 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QueueListBuilder;
124 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.qos.entries.QueueListKey;
125 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.queues.QueuesExternalIds;
126 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.queues.QueuesExternalIdsBuilder;
127 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.queues.QueuesExternalIdsKey;
128 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.queues.QueuesOtherConfig;
129 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.queues.QueuesOtherConfigBuilder;
130 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.node.attributes.queues.QueuesOtherConfigKey;
131 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceExternalIds;
132 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceExternalIdsBuilder;
133 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceExternalIdsKey;
134 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceLldp;
135 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceLldpBuilder;
136 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceLldpKey;
137 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceOtherConfigs;
138 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceOtherConfigsBuilder;
139 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.InterfaceOtherConfigsKey;
140 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.Options;
141 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.OptionsBuilder;
142 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.OptionsKey;
143 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortExternalIds;
144 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortExternalIdsBuilder;
145 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortExternalIdsKey;
146 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortOtherConfigs;
147 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortOtherConfigsBuilder;
148 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.PortOtherConfigsKey;
149 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.Trunks;
150 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.ovsdb.rev150105.ovsdb.port._interface.attributes.TrunksBuilder;
151 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NetworkTopology;
152 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NodeId;
153 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.TopologyId;
154 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.TpId;
155 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.Topology;
156 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.TopologyKey;
157 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.Node;
158 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.NodeBuilder;
159 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.node.TerminationPoint;
160 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.node.TerminationPointBuilder;
161 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.node.TerminationPointKey;
162 import org.opendaylight.yangtools.yang.binding.DataObject;
163 import org.opendaylight.yangtools.yang.binding.Identifiable;
164 import org.opendaylight.yangtools.yang.binding.Identifier;
165 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
166 import org.opendaylight.yangtools.yang.binding.KeyedInstanceIdentifier;
167 import org.opendaylight.yangtools.yang.binding.util.BindingMap;
168 import org.opendaylight.yangtools.yang.common.Uint16;
169 import org.opendaylight.yangtools.yang.common.Uint32;
170 import org.opendaylight.yangtools.yang.common.Uint8;
171 import org.ops4j.pax.exam.Configuration;
172 import org.ops4j.pax.exam.Option;
173 import org.ops4j.pax.exam.junit.PaxExam;
174 import org.ops4j.pax.exam.karaf.options.LogLevelOption;
175 import org.ops4j.pax.exam.options.MavenUrlReference;
176 import org.ops4j.pax.exam.spi.reactors.ExamReactorStrategy;
177 import org.ops4j.pax.exam.spi.reactors.PerClass;
178 import org.ops4j.pax.exam.util.Filter;
179 import org.osgi.framework.BundleContext;
180 import org.slf4j.Logger;
181 import org.slf4j.LoggerFactory;
184 * Integration tests for southbound-impl.
186 * @author Sam Hague (shague@redhat.com)
188 @RunWith(PaxExam.class)
189 @ExamReactorStrategy(PerClass.class)
190 public class SouthboundIT extends AbstractMdsalTestBase {
191 private static final String NETDEV_DP_TYPE = "netdev";
192 private static final Logger LOG = LoggerFactory.getLogger(SouthboundIT.class);
193 private static final int OVSDB_UPDATE_TIMEOUT = 1000;
194 private static final int OVSDB_ROUNDTRIP_TIMEOUT = 10000;
195 private static final String FORMAT_STR = "%s_%s_%d";
196 private static final Version AUTOATTACH_FROM_VERSION = Version.fromString("7.11.2");
197 private static final Version IF_INDEX_FROM_VERSION = Version.fromString("7.2.1");
198 private static final Uint32 MAX_BACKOFF = Uint32.valueOf(10000);
199 private static final Uint32 INACTIVITY_PROBE = Uint32.valueOf(30000);
200 private static String addressStr;
201 private static Uint16 portNumber;
202 private static String connectionType;
203 private static boolean setup = false;
204 private static MdsalUtils mdsalUtils = null;
205 private static Node ovsdbNode;
206 private static int testMethodsRemaining;
207 private static Version schemaVersion;
208 @Inject @Filter(timeout = 60000)
209 private static DataBroker dataBroker = null;
212 private BundleContext bundleContext;
214 private static final NotifyingDataChangeListener CONFIGURATION_LISTENER =
215 new NotifyingDataChangeListener(LogicalDatastoreType.CONFIGURATION);
216 private static final NotifyingDataChangeListener OPERATIONAL_LISTENER =
217 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL);
220 private static final class NotifyingDataChangeListener implements DataTreeChangeListener<DataObject> {
221 private static final int RETRY_WAIT = 100;
223 private final LogicalDatastoreType type;
224 private final Set<InstanceIdentifier<?>> createdIids = new HashSet<>();
225 private final Set<InstanceIdentifier<?>> removedIids = new HashSet<>();
226 private final Set<InstanceIdentifier<?>> updatedIids = new HashSet<>();
227 private final InstanceIdentifier<?> iid;
229 private NotifyingDataChangeListener(final LogicalDatastoreType type) {
234 private NotifyingDataChangeListener(final LogicalDatastoreType type, final InstanceIdentifier<?> iid) {
240 public void onDataTreeChanged(final Collection<DataTreeModification<DataObject>> changes) {
241 for (DataTreeModification<DataObject> change: changes) {
242 DataObjectModification<DataObject> rootNode = change.getRootNode();
243 final InstanceIdentifier<DataObject> identifier = change.getRootPath().getRootIdentifier();
244 switch (rootNode.getModificationType()) {
245 case SUBTREE_MODIFIED:
247 if (rootNode.getDataBefore() == null) {
248 LOG.info("{} DataTreeChanged: created {}", type, identifier);
249 createdIids.add(identifier);
251 final DataObject obj = rootNode.getDataAfter();
252 if (obj instanceof ManagedNodeEntry) {
253 ManagedNodeEntry managedNodeEntry = (ManagedNodeEntry) obj;
254 LOG.info("{} DataChanged: created managed {}",
255 managedNodeEntry.getBridgeRef().getValue());
256 createdIids.add(managedNodeEntry.getBridgeRef().getValue());
259 LOG.info("{} DataTreeChanged: updated {}", type, identifier);
260 updatedIids.add(identifier);
264 LOG.info("{} DataTreeChanged: removed {}", type, identifier);
265 removedIids.add(identifier);
272 synchronized (this) {
277 public boolean isCreated(final InstanceIdentifier<?> path) {
278 return createdIids.remove(path);
281 public boolean isRemoved(final InstanceIdentifier<?> path) {
282 return removedIids.remove(path);
285 public boolean isUpdated(final InstanceIdentifier<?> path) {
286 return updatedIids.remove(path);
289 public void clear() {
295 public void registerDataChangeListener() {
296 dataBroker.registerDataTreeChangeListener(DataTreeIdentifier.create(type,
297 (InstanceIdentifier)iid), this);
300 public void waitForCreation(final long timeout) throws InterruptedException {
301 synchronized (this) {
302 long start = System.currentTimeMillis();
303 LOG.info("Waiting for {} DataChanged creation on {}", type, iid);
304 while (!isCreated(iid) && System.currentTimeMillis() - start < timeout) {
307 LOG.info("Woke up, waited {}ms for creation of {}", System.currentTimeMillis() - start, iid);
311 public void waitForDeletion(final long timeout) throws InterruptedException {
312 synchronized (this) {
313 long start = System.currentTimeMillis();
314 LOG.info("Waiting for {} DataChanged deletion on {}", type, iid);
315 while (!isRemoved(iid) && System.currentTimeMillis() - start < timeout) {
318 LOG.info("Woke up, waited {}ms for deletion of {}", System.currentTimeMillis() - start, iid);
322 public void waitForUpdate(final long timeout) throws InterruptedException {
323 synchronized (this) {
324 long start = System.currentTimeMillis();
325 LOG.info("Waiting for {} DataChanged update on {}", type, iid);
326 while (!isUpdated(iid) && System.currentTimeMillis() - start < timeout) {
329 LOG.info("Woke up, waited {}ms for update of {}", System.currentTimeMillis() - start, iid);
336 public Option[] config() {
337 Option[] options = super.config();
338 Option[] propertyOptions = getPropertiesOptions();
339 Option[] otherOptions = getOtherOptions();
340 Option[] combinedOptions = new Option[options.length + propertyOptions.length + otherOptions.length];
341 System.arraycopy(options, 0, combinedOptions, 0, options.length);
342 System.arraycopy(propertyOptions, 0, combinedOptions, options.length, propertyOptions.length);
343 System.arraycopy(otherOptions, 0, combinedOptions, options.length + propertyOptions.length,
344 otherOptions.length);
345 return combinedOptions;
348 private static Option[] getOtherOptions() {
349 return new Option[] {
350 vmOption("-javaagent:../jars/org.jacoco.agent.jar=destfile=../../jacoco-it.exec"),
356 public String getKarafDistro() {
358 .groupId("org.opendaylight.ovsdb")
359 .artifactId("southbound-karaf")
360 .versionAsInProject()
366 public MavenUrlReference getFeatureRepo() {
368 .groupId("org.opendaylight.ovsdb")
369 .artifactId("southbound-features")
370 .classifier("features")
372 .versionAsInProject();
376 public String getFeatureName() {
377 return "odl-ovsdb-southbound-test";
380 protected String usage() {
381 return "Integration Test needs a valid connection configuration as follows :\n"
382 + "active connection : mvn -Dovsdbserver.ipaddress=x.x.x.x -Dovsdbserver.port=yyyy verify\n"
383 + "passive connection : mvn -Dovsdbserver.connection=passive verify\n";
387 public Option getLoggingOption() {
389 editConfigurationFilePut(SouthboundITConstants.ORG_OPS4J_PAX_LOGGING_CFG,
390 "log4j.logger.org.opendaylight.ovsdb",
391 LogLevelOption.LogLevel.TRACE.name()),
392 super.getLoggingOption());
395 private static Option[] getPropertiesOptions() {
396 Properties props = new Properties(System.getProperties());
397 String ipAddressStr = props.getProperty(SouthboundITConstants.SERVER_IPADDRESS,
398 SouthboundITConstants.DEFAULT_SERVER_IPADDRESS);
399 String portStr = props.getProperty(SouthboundITConstants.SERVER_PORT,
400 SouthboundITConstants.DEFAULT_SERVER_PORT);
401 String connectionTypeStr = props.getProperty(SouthboundITConstants.CONNECTION_TYPE,
402 SouthboundITConstants.CONNECTION_TYPE_ACTIVE);
404 LOG.info("getPropertiesOptions: Using the following properties: mode= {}, ip:port= {}:{}",
405 connectionTypeStr, ipAddressStr, portStr);
407 return new Option[] {
408 propagateSystemProperties(
409 SouthboundITConstants.SERVER_IPADDRESS,
410 SouthboundITConstants.SERVER_PORT,
411 SouthboundITConstants.CONNECTION_TYPE),
412 editConfigurationFilePut(SouthboundITConstants.CUSTOM_PROPERTIES,
413 SouthboundITConstants.SERVER_IPADDRESS, ipAddressStr),
414 editConfigurationFilePut(SouthboundITConstants.CUSTOM_PROPERTIES,
415 SouthboundITConstants.SERVER_PORT, portStr),
416 editConfigurationFilePut(SouthboundITConstants.CUSTOM_PROPERTIES,
417 SouthboundITConstants.CONNECTION_TYPE, connectionTypeStr),
423 public void setup() throws Exception {
425 LOG.info("Skipping setup, already initialized");
430 assertNotNull("db should not be null", dataBroker);
432 LOG.info("sleeping for 10s to let the features finish installing");
435 addressStr = bundleContext.getProperty(SouthboundITConstants.SERVER_IPADDRESS);
436 String portStr = bundleContext.getProperty(SouthboundITConstants.SERVER_PORT);
438 portNumber = Uint16.valueOf(portStr);
439 } catch (IllegalArgumentException e) {
440 fail("Invalid port number " + portStr + System.lineSeparator() + usage());
442 connectionType = bundleContext.getProperty(SouthboundITConstants.CONNECTION_TYPE);
444 LOG.info("setUp: Using the following properties: mode= {}, ip:port= {}:{}",
445 connectionType, addressStr, portNumber);
446 if (connectionType.equalsIgnoreCase(SouthboundITConstants.CONNECTION_TYPE_ACTIVE)) {
447 if (addressStr == null) {
452 mdsalUtils = new MdsalUtils(dataBroker);
453 assertTrue("Did not find " + SouthboundUtils.OVSDB_TOPOLOGY_ID.getValue(), getOvsdbTopology());
454 final ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
455 final InstanceIdentifier<Node> iid = SouthboundUtils.createInstanceIdentifier(connectionInfo);
456 dataBroker.registerDataTreeChangeListener(DataTreeIdentifier.create(LogicalDatastoreType.CONFIGURATION,
457 (InstanceIdentifier)iid), CONFIGURATION_LISTENER);
458 dataBroker.registerDataTreeChangeListener(DataTreeIdentifier.create(LogicalDatastoreType.OPERATIONAL,
459 (InstanceIdentifier)iid), OPERATIONAL_LISTENER);
461 ovsdbNode = connectOvsdbNode(connectionInfo);
462 OvsdbNodeAugmentation ovsdbNodeAugmentation = ovsdbNode.augmentation(OvsdbNodeAugmentation.class);
463 assertNotNull("The OvsdbNodeAugmentation cannot be null", ovsdbNodeAugmentation);
464 schemaVersion = Version.fromString(ovsdbNodeAugmentation.getDbVersion());
465 LOG.info("schemaVersion = {}", schemaVersion);
467 // Let's count the test methods (we need to use this instead of @AfterClass on teardown() since the latter is
468 // useless with pax-exam)
469 for (Method method : getClass().getMethods()) {
470 boolean testMethod = false;
471 boolean ignoreMethod = false;
472 for (Annotation annotation : method.getAnnotations()) {
473 if (Test.class.equals(annotation.annotationType())) {
476 if (Ignore.class.equals(annotation.annotationType())) {
480 if (testMethod && !ignoreMethod) {
481 testMethodsRemaining++;
484 LOG.info("{} test methods to run", testMethodsRemaining);
490 public void teardown() {
491 testMethodsRemaining--;
492 LOG.info("{} test methods remaining", testMethodsRemaining);
493 if (testMethodsRemaining == 0) {
495 disconnectOvsdbNode(getConnectionInfo(addressStr, portNumber));
496 } catch (InterruptedException e) {
497 LOG.warn("Interrupted while disconnecting", e);
502 private static Boolean getOvsdbTopology() {
503 LOG.info("getOvsdbTopology: looking for {}...", SouthboundUtils.OVSDB_TOPOLOGY_ID.getValue());
504 Boolean found = false;
505 final TopologyId topologyId = SouthboundUtils.OVSDB_TOPOLOGY_ID;
506 InstanceIdentifier<Topology> path =
507 InstanceIdentifier.create(NetworkTopology.class).child(Topology.class, new TopologyKey(topologyId));
508 for (int i = 0; i < 60; i++) {
509 Topology topology = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, path);
510 if (topology != null) {
511 LOG.info("getOvsdbTopology: found {}...", SouthboundUtils.OVSDB_TOPOLOGY_ID.getValue());
515 LOG.info("getOvsdbTopology: still looking ({})...", i);
518 } catch (InterruptedException e) {
519 LOG.warn("Interrupted while waiting for {}", SouthboundUtils.OVSDB_TOPOLOGY_ID.getValue(), e);
527 * Test passive connection mode. The southbound starts in a listening mode waiting for connections on port
528 * 6640. This test will wait for incoming connections for {@link SouthboundITConstants#CONNECTION_INIT_TIMEOUT} ms.
531 public void testPassiveNode() throws InterruptedException {
532 if (connectionType.equalsIgnoreCase(SouthboundITConstants.CONNECTION_TYPE_PASSIVE)) {
533 //Wait for CONNECTION_INIT_TIMEOUT for the Passive connection to be initiated by the ovsdb-server.
534 Thread.sleep(SouthboundITConstants.CONNECTION_INIT_TIMEOUT);
538 private static ConnectionInfo getConnectionInfo(final String ipAddressStr, final Uint16 portNum) {
539 InetAddress inetAddress = null;
541 inetAddress = InetAddress.getByName(ipAddressStr);
542 } catch (UnknownHostException e) {
543 fail("Could not resolve " + ipAddressStr + ": " + e);
546 IpAddress address = SouthboundMapper.createIpAddress(inetAddress);
547 PortNumber port = new PortNumber(portNum);
549 final ConnectionInfo connectionInfo = new ConnectionInfoBuilder()
550 .setRemoteIp(address)
553 LOG.info("connectionInfo: {}", connectionInfo);
554 return connectionInfo;
558 public void testNetworkTopology() throws InterruptedException {
559 NetworkTopology networkTopology = mdsalUtils.read(LogicalDatastoreType.CONFIGURATION,
560 InstanceIdentifier.create(NetworkTopology.class));
561 assertNotNull("NetworkTopology could not be found in " + LogicalDatastoreType.CONFIGURATION, networkTopology);
563 networkTopology = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL,
564 InstanceIdentifier.create(NetworkTopology.class));
565 assertNotNull("NetworkTopology could not be found in " + LogicalDatastoreType.OPERATIONAL, networkTopology);
569 public void testOvsdbTopology() throws InterruptedException {
570 InstanceIdentifier<Topology> path = InstanceIdentifier
571 .create(NetworkTopology.class)
572 .child(Topology.class, new TopologyKey(SouthboundConstants.OVSDB_TOPOLOGY_ID));
574 Topology topology = mdsalUtils.read(LogicalDatastoreType.CONFIGURATION, path);
575 assertNotNull("Topology could not be found in " + LogicalDatastoreType.CONFIGURATION, topology);
577 topology = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, path);
579 assertNotNull("Topology could not be found in " + LogicalDatastoreType.OPERATIONAL, topology);
582 private static Node connectOvsdbNode(final ConnectionInfo connectionInfo) throws InterruptedException {
583 final InstanceIdentifier<Node> iid = SouthboundUtils.createInstanceIdentifier(connectionInfo);
585 mdsalUtils.put(LogicalDatastoreType.CONFIGURATION, iid, SouthboundUtils.createNode(connectionInfo)));
586 waitForOperationalCreation(iid);
587 Node node = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, iid);
589 LOG.info("Connected to {}", SouthboundUtils.connectionInfoToString(connectionInfo));
593 private static void waitForOperationalCreation(final InstanceIdentifier<Node> iid) throws InterruptedException {
594 synchronized (OPERATIONAL_LISTENER) {
595 long start = System.currentTimeMillis();
596 LOG.info("Waiting for OPERATIONAL DataChanged creation on {}", iid);
597 while (!OPERATIONAL_LISTENER.isCreated(
598 iid) && System.currentTimeMillis() - start < OVSDB_ROUNDTRIP_TIMEOUT) {
599 OPERATIONAL_LISTENER.wait(OVSDB_UPDATE_TIMEOUT);
601 LOG.info("Woke up, waited {} for creation of {}", System.currentTimeMillis() - start, iid);
605 private static void waitForOperationalDeletion(final InstanceIdentifier<Node> iid) throws InterruptedException {
606 synchronized (OPERATIONAL_LISTENER) {
607 long start = System.currentTimeMillis();
608 LOG.info("Waiting for OPERATIONAL DataChanged deletion on {}", iid);
609 while (!OPERATIONAL_LISTENER.isRemoved(
610 iid) && System.currentTimeMillis() - start < OVSDB_ROUNDTRIP_TIMEOUT) {
611 OPERATIONAL_LISTENER.wait(OVSDB_UPDATE_TIMEOUT);
613 LOG.info("Woke up, waited {} for deletion of {}", System.currentTimeMillis() - start, iid);
617 private static void waitForOperationalUpdate(final InstanceIdentifier<Node> iid) throws InterruptedException {
618 synchronized (OPERATIONAL_LISTENER) {
619 long start = System.currentTimeMillis();
620 LOG.info("Waiting for OPERATIONAL DataChanged update on {}", iid);
621 while (!OPERATIONAL_LISTENER.isUpdated(
622 iid) && System.currentTimeMillis() - start < OVSDB_ROUNDTRIP_TIMEOUT) {
623 OPERATIONAL_LISTENER.wait(OVSDB_UPDATE_TIMEOUT);
625 LOG.info("Woke up, waited {} for update of {}", System.currentTimeMillis() - start, iid);
629 private static void disconnectOvsdbNode(final ConnectionInfo connectionInfo) throws InterruptedException {
630 final InstanceIdentifier<Node> iid = SouthboundUtils.createInstanceIdentifier(connectionInfo);
631 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, iid));
632 waitForOperationalDeletion(iid);
633 Node node = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, iid);
635 LOG.info("Disconnected from {}", SouthboundUtils.connectionInfoToString(connectionInfo));
639 public void testAddDeleteOvsdbNode() throws InterruptedException {
640 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
641 // At this point we're connected, disconnect and reconnect (the connection will be removed at the very end)
642 disconnectOvsdbNode(connectionInfo);
643 connectOvsdbNode(connectionInfo);
647 public void testDpdkSwitch() throws InterruptedException {
648 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
649 Map<DatapathTypeEntryKey, DatapathTypeEntry> datapathTypeEntries =
650 ovsdbNode.augmentation(OvsdbNodeAugmentation.class).nonnullDatapathTypeEntry();
651 if (datapathTypeEntries == null) {
652 LOG.info("DPDK not supported on this node.");
654 for (DatapathTypeEntry dpTypeEntry : datapathTypeEntries.values()) {
655 Class<? extends DatapathTypeBase> dpType = dpTypeEntry.getDatapathType();
656 String dpTypeStr = SouthboundMapper.DATAPATH_TYPE_MAP.get(dpType);
657 LOG.info("dp type is {}", dpTypeStr);
658 if (dpTypeStr.equals(NETDEV_DP_TYPE)) {
659 LOG.info("Found a DPDK node; adding a corresponding netdev device");
660 InstanceIdentifier<Node> bridgeIid = SouthboundUtils.createInstanceIdentifier(connectionInfo,
661 new OvsdbBridgeName(SouthboundITConstants.BRIDGE_NAME));
662 NodeId bridgeNodeId = SouthboundUtils.createManagedNodeId(bridgeIid);
663 try (TestBridge testBridge = new TestBridge(connectionInfo, bridgeIid,
664 SouthboundITConstants.BRIDGE_NAME, bridgeNodeId, false, null, true, dpType, null, null,
666 // Verify that the device is netdev
667 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
668 assertNotNull(bridge);
669 assertEquals(dpType, bridge.getDatapathType());
671 // Add port for all dpdk interface types (dpdkvhost not supported in existing dpdk ovs)
672 List<String> dpdkTypes = new ArrayList<>();
673 dpdkTypes.add("dpdk");
674 dpdkTypes.add("dpdkr");
675 dpdkTypes.add("dpdkvhostuser");
676 //dpdkTypes.add("dpdkvhost");
678 for (String dpdkType : dpdkTypes) {
679 String testPortname = "test" + dpdkType + "port";
680 LOG.info("DPDK portname and type is {}, {}", testPortname, dpdkType);
681 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationpointBuilder =
682 createSpecificDpdkOvsdbTerminationPointAugmentationBuilder(testPortname,
683 SouthboundMapper.OVSDB_INTERFACE_TYPE_MAP.get(dpdkType));
684 assertTrue(addTerminationPoint(bridgeNodeId, testPortname, ovsdbTerminationpointBuilder));
687 // Verify that all DPDK ports are created
688 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
689 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL,
690 terminationPointIid);
691 assertNotNull(terminationPointNode);
693 // Verify that each termination point has the specific DPDK ifType
694 for (String dpdkType : dpdkTypes) {
695 String testPortname = "test" + dpdkType + "port";
696 Class<? extends InterfaceTypeBase> dpdkIfType =
697 SouthboundMapper.OVSDB_INTERFACE_TYPE_MAP.get(dpdkType);
698 for (TerminationPoint terminationPoint
699 : terminationPointNode.nonnullTerminationPoint().values()) {
700 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation = terminationPoint
701 .augmentation(OvsdbTerminationPointAugmentation.class);
702 if (ovsdbTerminationPointAugmentation.getName().equals(testPortname)) {
703 assertEquals(dpdkIfType, ovsdbTerminationPointAugmentation.getInterfaceType());
715 public void testOvsdbNodeOvsVersion() throws InterruptedException {
716 OvsdbNodeAugmentation ovsdbNodeAugmentation = ovsdbNode.augmentation(OvsdbNodeAugmentation.class);
717 assertNotNull(ovsdbNodeAugmentation);
718 assertNotNull(ovsdbNodeAugmentation.getOvsVersion());
722 public void testOvsdbNodeDbVersion() throws InterruptedException {
723 OvsdbNodeAugmentation ovsdbNodeAugmentation = ovsdbNode.augmentation(OvsdbNodeAugmentation.class);
724 assertNotNull(ovsdbNodeAugmentation);
725 assertNotNull(ovsdbNodeAugmentation.getDbVersion());
729 public void testOpenVSwitchOtherConfig() throws InterruptedException {
730 OvsdbNodeAugmentation ovsdbNodeAugmentation = ovsdbNode.augmentation(OvsdbNodeAugmentation.class);
731 assertNotNull(ovsdbNodeAugmentation);
732 Map<OpenvswitchOtherConfigsKey, OpenvswitchOtherConfigs> otherConfigsList =
733 ovsdbNodeAugmentation.getOpenvswitchOtherConfigs();
734 if (otherConfigsList != null) {
735 for (OpenvswitchOtherConfigs otherConfig : otherConfigsList.values()) {
736 if (otherConfig.getOtherConfigKey().equals("local_ip")) {
737 LOG.info("local_ip: {}", otherConfig.getOtherConfigValue());
740 LOG.info("other_config {}:{}", otherConfig.getOtherConfigKey(), otherConfig.getOtherConfigValue());
744 LOG.info("other_config is not present");
749 public void testOvsdbBridgeControllerInfo() throws InterruptedException {
750 ConnectionInfo connectionInfo = getConnectionInfo(addressStr,portNumber);
751 String controllerTarget = SouthboundUtil.getControllerTarget(ovsdbNode);
752 assertNotNull("Failed to get controller target", controllerTarget);
753 ControllerEntry setControllerEntry = createControllerEntry(controllerTarget);
754 Uri setUri = new Uri(controllerTarget);
755 try (TestBridge testBridge = new TestBridge(connectionInfo, null, SouthboundITConstants.BRIDGE_NAME,null, true,
756 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"), true, null, null,
757 BindingMap.of(setControllerEntry), null)) {
758 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
759 assertNotNull("bridge was not found: " + SouthboundITConstants.BRIDGE_NAME, bridge);
760 assertNotNull("ControllerEntry was not found: " + setControllerEntry, bridge.getControllerEntry());
761 for (ControllerEntry entry : bridge.getControllerEntry().values()) {
762 if (entry.getTarget() != null) {
763 assertEquals(setUri.toString(), entry.getTarget().toString());
765 if (entry.getMaxBackoff() != null) {
766 assertEquals(MAX_BACKOFF, entry.getMaxBackoff());
768 if (entry.getInactivityProbe() != null) {
769 assertEquals(INACTIVITY_PROBE, entry.getInactivityProbe());
775 private static @NonNull ControllerEntry createControllerEntry(final String controllerTarget) {
776 return new ControllerEntryBuilder()
777 .setTarget(new Uri(controllerTarget))
778 .setMaxBackoff(MAX_BACKOFF)
779 .setInactivityProbe(INACTIVITY_PROBE)
783 private static void setManagedBy(final OvsdbBridgeAugmentationBuilder ovsdbBridgeAugmentationBuilder,
784 final ConnectionInfo connectionInfo) {
785 InstanceIdentifier<Node> connectionNodePath = SouthboundUtils.createInstanceIdentifier(connectionInfo);
786 ovsdbBridgeAugmentationBuilder.setManagedBy(new OvsdbNodeRef(connectionNodePath));
789 private static Map<ProtocolEntryKey, ProtocolEntry> createMdsalProtocols() {
790 ImmutableBiMap<String, Class<? extends OvsdbBridgeProtocolBase>> mapper =
791 SouthboundConstants.OVSDB_PROTOCOL_MAP.inverse();
792 return BindingMap.of(new ProtocolEntryBuilder().setProtocol(mapper.get("OpenFlow13")).build());
795 private static OvsdbTerminationPointAugmentationBuilder createGenericOvsdbTerminationPointAugmentationBuilder() {
796 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationPointAugmentationBuilder =
797 new OvsdbTerminationPointAugmentationBuilder();
798 ovsdbTerminationPointAugmentationBuilder.setInterfaceType(
799 new InterfaceTypeEntryBuilder()
801 SouthboundMapper.createInterfaceType("internal"))
802 .build().getInterfaceType());
803 return ovsdbTerminationPointAugmentationBuilder;
806 private static OvsdbTerminationPointAugmentationBuilder createGenericDpdkOvsdbTerminationPointAugmentationBuilder(
807 final String portName) {
808 return createGenericOvsdbTerminationPointAugmentationBuilder()
810 .setInterfaceType(SouthboundMapper.OVSDB_INTERFACE_TYPE_MAP.get("dpdk"));
813 private static OvsdbTerminationPointAugmentationBuilder createSpecificDpdkOvsdbTerminationPointAugmentationBuilder(
814 final String testPortname, final Class<? extends InterfaceTypeBase> dpdkIfType) {
815 return createGenericOvsdbTerminationPointAugmentationBuilder()
816 .setName(testPortname)
817 .setInterfaceType(dpdkIfType);
820 private static boolean addTerminationPoint(final NodeId bridgeNodeId, final String portName,
821 final OvsdbTerminationPointAugmentationBuilder
822 ovsdbTerminationPointAugmentationBuilder)
823 throws InterruptedException {
825 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(bridgeNodeId);
826 NodeBuilder portNodeBuilder = new NodeBuilder();
827 NodeId portNodeId = SouthboundMapper.createManagedNodeId(portIid);
828 portNodeBuilder.setNodeId(portNodeId);
829 TerminationPointBuilder entry = new TerminationPointBuilder()
830 .withKey(new TerminationPointKey(new TpId(portName)))
831 .addAugmentation(ovsdbTerminationPointAugmentationBuilder.build());
832 portNodeBuilder.setTerminationPoint(BindingMap.of(entry.build()));
833 boolean result = mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, portIid, portNodeBuilder.build());
834 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
838 private static class TestBridge implements AutoCloseable {
839 private final ConnectionInfo connectionInfo;
840 private final String bridgeName;
843 * Creates a test bridge which can be automatically removed when no longer necessary.
845 * @param connectionInfo The connection information.
846 * @param bridgeIid The bridge identifier; if {@code null}, one is created based on {@code bridgeName}.
847 * @param bridgeName The bridge name; must be provided.
848 * @param bridgeNodeId The bridge node identifier; if {@code null}, one is created based on {@code bridgeIid}.
849 * @param setProtocolEntries {@code true} to set default protocol entries for the bridge.
850 * @param failMode The fail mode to set for the bridge.
851 * @param setManagedBy {@code true} to specify {@code setManagedBy} for the bridge.
852 * @param dpType The datapath type.
853 * @param externalIds The external identifiers if any.
854 * @param otherConfigs The other configuration items if any.
856 TestBridge(final ConnectionInfo connectionInfo, @Nullable InstanceIdentifier<Node> bridgeIid,
857 final String bridgeName, NodeId bridgeNodeId, final boolean setProtocolEntries,
858 final Class<? extends OvsdbFailModeBase> failMode, final boolean setManagedBy,
859 @Nullable final Class<? extends DatapathTypeBase> dpType,
860 @Nullable final Map<BridgeExternalIdsKey, BridgeExternalIds> externalIds,
861 @Nullable final Map<ControllerEntryKey, ControllerEntry> controllerEntries,
862 @Nullable final Map<BridgeOtherConfigsKey, BridgeOtherConfigs> otherConfigs) {
863 this.connectionInfo = connectionInfo;
864 this.bridgeName = bridgeName;
865 NodeBuilder bridgeNodeBuilder = new NodeBuilder();
866 if (bridgeIid == null) {
867 bridgeIid = SouthboundUtils.createInstanceIdentifier(connectionInfo, new OvsdbBridgeName(bridgeName));
869 if (bridgeNodeId == null) {
870 bridgeNodeId = SouthboundMapper.createManagedNodeId(bridgeIid);
872 bridgeNodeBuilder.setNodeId(bridgeNodeId);
873 OvsdbBridgeAugmentationBuilder ovsdbBridgeAugmentationBuilder = new OvsdbBridgeAugmentationBuilder();
874 ovsdbBridgeAugmentationBuilder.setBridgeName(new OvsdbBridgeName(bridgeName));
875 if (setProtocolEntries) {
876 ovsdbBridgeAugmentationBuilder.setProtocolEntry(createMdsalProtocols());
878 ovsdbBridgeAugmentationBuilder.setFailMode(failMode);
880 setManagedBy(ovsdbBridgeAugmentationBuilder, connectionInfo);
882 ovsdbBridgeAugmentationBuilder.setDatapathType(dpType);
883 ovsdbBridgeAugmentationBuilder.setBridgeExternalIds(externalIds);
884 ovsdbBridgeAugmentationBuilder.setControllerEntry(controllerEntries);
885 ovsdbBridgeAugmentationBuilder.setBridgeOtherConfigs(otherConfigs);
886 bridgeNodeBuilder.addAugmentation(ovsdbBridgeAugmentationBuilder.build());
887 LOG.debug("Built with the intent to store bridge data {}", ovsdbBridgeAugmentationBuilder);
888 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, bridgeIid, bridgeNodeBuilder.build()));
890 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
891 } catch (InterruptedException e) {
892 LOG.warn("Sleep interrupted while waiting for bridge creation (bridge {})", bridgeName, e);
896 TestBridge(final ConnectionInfo connectionInfo, final String bridgeName) {
897 this(connectionInfo, null, bridgeName, null, true,
898 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"), true, null, null, null, null);
902 public void close() {
903 final InstanceIdentifier<Node> iid =
904 SouthboundUtils.createInstanceIdentifier(connectionInfo, new OvsdbBridgeName(bridgeName));
905 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, iid));
907 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
908 } catch (InterruptedException e) {
909 LOG.warn("Sleep interrupted while waiting for bridge deletion (bridge {})", bridgeName, e);
914 private static class TestAutoAttach implements AutoCloseable {
915 private final ConnectionInfo connectionInfo;
916 private final Uri autoattachId;
917 private final Uri bridgeId;
919 TestAutoAttach(final ConnectionInfo connectionInfo,
920 final Uri autoattachId,
922 @Nullable final String systemName,
923 @Nullable final String systemDescription,
924 @Nullable final Map<MappingsKey, Mappings> mappings,
925 @Nullable final Map<AutoattachExternalIdsKey, AutoattachExternalIds> externalIds) {
926 this.connectionInfo = connectionInfo;
927 this.autoattachId = autoattachId;
928 this.bridgeId = bridgeId;
930 Autoattach aaEntry = new AutoattachBuilder()
931 .setAutoattachId(autoattachId)
932 .setBridgeId(bridgeId)
933 .setSystemName(systemName)
934 .setSystemDescription(systemDescription)
935 .setMappings(mappings)
936 .setAutoattachExternalIds(externalIds)
938 InstanceIdentifier<Autoattach> iid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
939 .augmentation(OvsdbNodeAugmentation.class)
940 .child(Autoattach.class, aaEntry.key());
941 final NotifyingDataChangeListener aaOperationalListener =
942 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, iid);
943 aaOperationalListener.registerDataChangeListener();
945 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, iid, aaEntry));
947 aaOperationalListener.waitForCreation(OVSDB_ROUNDTRIP_TIMEOUT);
948 } catch (InterruptedException e) {
949 LOG.warn("Sleep interrupted while waiting for queue {}", iid, e);
954 public void close() {
955 final InstanceIdentifier<Autoattach> iid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
956 .augmentation(OvsdbNodeAugmentation.class)
957 .child(Autoattach.class, new AutoattachKey(autoattachId));
958 final NotifyingDataChangeListener aaOperationalListener =
959 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, iid);
960 aaOperationalListener.registerDataChangeListener();
962 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, iid));
964 aaOperationalListener.waitForDeletion(OVSDB_ROUNDTRIP_TIMEOUT);
965 } catch (InterruptedException e) {
966 LOG.warn("Sleep interrupted while waiting for qos deletion (qos {})", iid, e);
972 public void testCRUDAutoAttach() throws InterruptedException {
973 final boolean isOldSchema = schemaVersion.compareTo(AUTOATTACH_FROM_VERSION) < 0;
975 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
976 String testAutoattachId = "testAutoattachEntry";
977 String testSystemName = "testSystemName";
978 String testSystemDescription = "testSystemDescription";
979 String testAutoattachExternalKey = "testAutoattachExternalKey";
980 String testAutoattachExternalValue = "testAutoattachExternalValue";
982 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
983 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
984 assertNotNull(bridge);
986 // CREATE: Create Autoattach table
987 NodeId nodeId = SouthboundUtils.createManagedNodeId(SouthboundUtils.createInstanceIdentifier(
988 connectionInfo, bridge.getBridgeName()));
989 String bridgeId = nodeId.getValue();
990 try (TestAutoAttach testAutoattach = new TestAutoAttach(connectionInfo, new Uri(testAutoattachId),
991 new Uri(bridgeId), testSystemName, testSystemDescription, null, null)) {
992 // READ: Read md-sal operational datastore to see if the AutoAttach table was created
993 // and if Bridge table was updated with AutoAttach Uuid
994 OvsdbNodeAugmentation ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
995 LogicalDatastoreType.OPERATIONAL);
996 Autoattach operAa = getAutoAttach(ovsdbNodeAugmentation, new Uri(testAutoattachId));
998 // skip tests after verifying that Autoattach doesn't break with unsupported schema
999 assumeFalse(isOldSchema);
1001 // FIXME: Remove once CRUD is supported
1002 assumeFalse(operAa == null);
1004 assertNotNull(operAa);
1005 assertEquals(testSystemName, operAa.getSystemName());
1006 bridge = getBridge(connectionInfo);
1007 Uuid aaUuid = new Uuid(operAa.getAutoattachUuid().getValue());
1008 assertEquals(aaUuid, bridge.getAutoAttach());
1010 // UPDATE: Update mappings column of AutoAttach table that was created
1011 Map<MappingsKey, Mappings> mappings = BindingMap.of(new MappingsBuilder()
1012 .setMappingsKey(Uint32.valueOf(100))
1013 .setMappingsValue(Uint16.valueOf(200))
1015 Autoattach updatedAa = new AutoattachBuilder()
1016 .setAutoattachId(new Uri(testAutoattachId))
1017 .setMappings(mappings)
1019 InstanceIdentifier<Autoattach> iid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
1020 .augmentation(OvsdbNodeAugmentation.class)
1021 .child(Autoattach.class, updatedAa.key());
1022 final NotifyingDataChangeListener aaOperationalListener =
1023 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, iid);
1024 aaOperationalListener.registerDataChangeListener();
1025 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, iid, updatedAa));
1026 aaOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
1028 // UPDATE: Update external_ids column of AutoAttach table that was created
1029 BindingMap.Builder<AutoattachExternalIdsKey, AutoattachExternalIds> externalIds = BindingMap.builder();
1030 externalIds.add(new AutoattachExternalIdsBuilder()
1031 .setAutoattachExternalIdKey(testAutoattachExternalKey)
1032 .setAutoattachExternalIdValue(testAutoattachExternalValue)
1034 updatedAa = new AutoattachBuilder()
1035 .setAutoattachId(new Uri(testAutoattachId))
1036 .setAutoattachExternalIds(externalIds.build())
1038 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, iid, updatedAa));
1039 aaOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
1041 // READ: Read the updated AutoAttach table for latest mappings and external_ids column value
1042 ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
1043 LogicalDatastoreType.OPERATIONAL);
1044 operAa = getAutoAttach(ovsdbNodeAugmentation, new Uri(testAutoattachId));
1045 assertNotNull(operAa);
1046 Map<MappingsKey, Mappings> operMappingsList = operAa.getMappings();
1047 for (Mappings operMappings : operMappingsList.values()) {
1048 assertTrue(mappings.containsValue(operMappings));
1050 Map<AutoattachExternalIdsKey, AutoattachExternalIds> operExternalIds =
1051 operAa.getAutoattachExternalIds();
1052 final Collection<AutoattachExternalIds> ids = externalIds.add(new AutoattachExternalIdsBuilder()
1053 .setAutoattachExternalIdKey(SouthboundConstants.AUTOATTACH_ID_EXTERNAL_ID_KEY)
1054 .setAutoattachExternalIdValue(operAa.getAutoattachId().getValue())
1058 for (AutoattachExternalIds operExternalId : operExternalIds.values()) {
1059 assertTrue(ids.contains(operExternalId));
1062 // DELETE: Delete AutoAttach table
1063 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, iid));
1064 aaOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
1065 ovsdbNodeAugmentation = getOvsdbNode(connectionInfo, LogicalDatastoreType.OPERATIONAL);
1066 operAa = getAutoAttach(ovsdbNodeAugmentation, new Uri(testAutoattachId));
1068 } catch (AssumptionViolatedException e) {
1069 LOG.warn("Skipped test for Autoattach due to unsupported schema", e);
1074 private static Autoattach getAutoAttach(final OvsdbNodeAugmentation ovsdbNodeAugmentation, final Uri uri) {
1075 for (Autoattach aa : ovsdbNodeAugmentation.nonnullAutoattach().values()) {
1076 if (aa.key().getAutoattachId().equals(uri)) {
1083 private static class TestQos implements AutoCloseable {
1084 private final ConnectionInfo connectionInfo;
1085 private final Uri qosId;
1088 * Creates a test qos entry which can be automatically removed when no longer necessary.
1090 * @param connectionInfo The connection information.
1091 * @param qosId The Qos identifier.
1092 * @param qosType The qos type.
1093 * @param externalIds The external identifiers if any.
1094 * @param otherConfigs The other configuration items if any.
1096 TestQos(final ConnectionInfo connectionInfo,
1098 final Class<? extends QosTypeBase> qosType,
1099 final @Nullable Map<QosExternalIdsKey, QosExternalIds> externalIds,
1100 final @Nullable Map<QosOtherConfigKey, QosOtherConfig> otherConfigs) {
1101 this.connectionInfo = connectionInfo;
1104 QosEntries qosEntry = new QosEntriesBuilder()
1106 .setQosType(qosType)
1107 .setQosExternalIds(externalIds)
1108 .setQosOtherConfig(otherConfigs)
1110 InstanceIdentifier<QosEntries> qeIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
1111 .augmentation(OvsdbNodeAugmentation.class)
1112 .child(QosEntries.class, qosEntry.key());
1113 final NotifyingDataChangeListener qosOperationalListener =
1114 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, qeIid);
1115 qosOperationalListener.registerDataChangeListener();
1117 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, qeIid, qosEntry));
1120 qosOperationalListener.waitForCreation(OVSDB_ROUNDTRIP_TIMEOUT);
1121 } catch (InterruptedException e) {
1122 LOG.warn("Sleep interrupted while waiting for queue {}", qeIid, e);
1128 public void close() {
1129 final InstanceIdentifier<QosEntries> qeIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
1130 .augmentation(OvsdbNodeAugmentation.class)
1131 .child(QosEntries.class, new QosEntriesKey(qosId));
1132 final NotifyingDataChangeListener qosOperationalListener =
1133 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, qeIid);
1134 qosOperationalListener.registerDataChangeListener();
1136 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, qeIid));
1138 qosOperationalListener.waitForDeletion(OVSDB_ROUNDTRIP_TIMEOUT);
1139 } catch (InterruptedException e) {
1140 LOG.warn("Sleep interrupted while waiting for qos deletion (qos {})", qeIid, e);
1145 private static class TestQueue implements AutoCloseable {
1146 private final ConnectionInfo connectionInfo;
1147 private final Uri queueId;
1148 private final InstanceIdentifier<Queues> queueIid;
1151 * Creates a test queue entry which can be automatically removed when no longer necessary.
1153 * @param connectionInfo The connection information.
1154 * @param queueId The Queue identifier.
1155 * @param queueDscp The queue dscp value.
1156 * @param externalIds The external identifiers if any.
1157 * @param otherConfigs The other configuration items if any.
1159 TestQueue(final ConnectionInfo connectionInfo, final Uri queueId, final Uint8 queueDscp,
1160 final @Nullable Map<QueuesExternalIdsKey, QueuesExternalIds> externalIds,
1161 final @Nullable Map<QueuesOtherConfigKey, QueuesOtherConfig> otherConfigs) {
1162 this.connectionInfo = connectionInfo;
1163 this.queueId = queueId;
1165 Queues queue = new QueuesBuilder()
1166 .setQueueId(queueId)
1168 .setQueuesExternalIds(externalIds)
1169 .setQueuesOtherConfig(otherConfigs)
1171 queueIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
1172 .augmentation(OvsdbNodeAugmentation.class)
1173 .child(Queues.class, queue.key());
1174 final NotifyingDataChangeListener queueOperationalListener =
1175 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, queueIid);
1176 queueOperationalListener.registerDataChangeListener();
1178 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, queueIid, queue));
1181 queueOperationalListener.waitForCreation(OVSDB_ROUNDTRIP_TIMEOUT);
1182 } catch (InterruptedException e) {
1183 LOG.warn("Sleep interrupted while waiting for queue {}", queueId, e);
1187 public InstanceIdentifier<Queues> getInstanceIdentifier() {
1192 public void close() {
1193 InstanceIdentifier<Queues> queuesIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
1194 .augmentation(OvsdbNodeAugmentation.class)
1195 .child(Queues.class, new QueuesKey(queueId));
1196 final NotifyingDataChangeListener queueOperationalListener =
1197 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, queuesIid);
1198 queueOperationalListener.registerDataChangeListener();
1200 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, queuesIid));
1202 queueOperationalListener.waitForDeletion(OVSDB_ROUNDTRIP_TIMEOUT);
1203 } catch (InterruptedException e) {
1204 LOG.warn("Sleep interrupted while waiting for queue deletion (queue {})", queueId, e);
1209 private static OvsdbNodeAugmentation getOvsdbNode(final ConnectionInfo connectionInfo,
1210 final LogicalDatastoreType store) {
1211 InstanceIdentifier<Node> nodeIid = SouthboundUtils.createInstanceIdentifier(connectionInfo);
1212 Node node = mdsalUtils.read(store, nodeIid);
1213 assertNotNull(node);
1214 OvsdbNodeAugmentation ovsdbNodeAugmentation = node.augmentation(OvsdbNodeAugmentation.class);
1215 assertNotNull(ovsdbNodeAugmentation);
1216 return ovsdbNodeAugmentation;
1219 private static OvsdbBridgeAugmentation getBridge(final ConnectionInfo connectionInfo) {
1220 return getBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME);
1224 * Extract the <code>store</code> type data store contents for the particular bridge identified by
1225 * <code>bridgeName</code>.
1227 * @param connectionInfo the connection information
1228 * @param bridgeName the bridge name
1229 * @param store defined by the <code>LogicalDatastoreType</code> enumeration
1230 * @return <code>store</code> type data store contents
1232 private static OvsdbBridgeAugmentation getBridge(final ConnectionInfo connectionInfo, final String bridgeName,
1233 final LogicalDatastoreType store) {
1234 Node bridgeNode = getBridgeNode(connectionInfo, bridgeName, store);
1235 assertNotNull(bridgeNode);
1236 OvsdbBridgeAugmentation ovsdbBridgeAugmentation = bridgeNode.augmentation(OvsdbBridgeAugmentation.class);
1237 assertNotNull(ovsdbBridgeAugmentation);
1238 return ovsdbBridgeAugmentation;
1242 * extract the <code>LogicalDataStoreType.OPERATIONAL</code> type data store contents for the particular bridge
1243 * identified by <code>bridgeName</code>.
1245 * @param connectionInfo the connection information
1246 * @param bridgeName the bridge name
1247 * @see SouthboundIT#getBridge(ConnectionInfo, String, LogicalDatastoreType)
1248 * @return <code>LogicalDatastoreType.OPERATIONAL</code> type data store contents
1250 private static OvsdbBridgeAugmentation getBridge(final ConnectionInfo connectionInfo, final String bridgeName) {
1251 return getBridge(connectionInfo, bridgeName, LogicalDatastoreType.OPERATIONAL);
1255 * Extract the node contents from <code>store</code> type data store for the
1256 * bridge identified by <code>bridgeName</code>.
1258 * @param connectionInfo the connection information
1259 * @param bridgeName the bridge name
1260 * @param store defined by the <code>LogicalDatastoreType</code> enumeration
1261 * @return <code>store</code> type data store contents
1263 private static Node getBridgeNode(final ConnectionInfo connectionInfo, final String bridgeName,
1264 final LogicalDatastoreType store) {
1265 InstanceIdentifier<Node> bridgeIid =
1266 SouthboundUtils.createInstanceIdentifier(connectionInfo, new OvsdbBridgeName(bridgeName));
1267 return mdsalUtils.read(store, bridgeIid);
1271 * Extract the node contents from <code>LogicalDataStoreType.OPERATIONAL</code> data store for the
1272 * bridge identified by <code>bridgeName</code>.
1274 * @param connectionInfo the connection information
1275 * @param bridgeName the bridge name
1276 * @return <code>LogicalDatastoreType.OPERATIONAL</code> type data store contents
1278 private static Node getBridgeNode(final ConnectionInfo connectionInfo, final String bridgeName) {
1279 return getBridgeNode(connectionInfo, bridgeName, LogicalDatastoreType.OPERATIONAL);
1283 public void testAddDeleteBridge() throws InterruptedException {
1284 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1286 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
1287 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1288 assertNotNull(bridge);
1289 LOG.info("bridge: {}", bridge);
1293 private static InstanceIdentifier<Node> getTpIid(final ConnectionInfo connectionInfo,
1294 final OvsdbBridgeAugmentation bridge) {
1295 return SouthboundUtils.createInstanceIdentifier(connectionInfo, bridge.getBridgeName());
1299 * Extracts the <code>TerminationPointAugmentation</code> for the <code>index</code> <code>TerminationPoint</code>
1300 * on <code>bridgeName</code>.
1302 * @param connectionInfo the connection information
1303 * @param bridgeName the bridge name
1304 * @param store defined by the <code>LogicalDatastoreType</code> enumeration
1305 * @param index the index we're interested in
1306 * @return the augmentation (or {@code null} if none)
1308 private static OvsdbTerminationPointAugmentation getOvsdbTerminationPointAugmentation(
1309 final ConnectionInfo connectionInfo, final String bridgeName, final LogicalDatastoreType store,
1312 Map<TerminationPointKey, TerminationPoint> tpList = getBridgeNode(connectionInfo, bridgeName, store)
1313 .getTerminationPoint();
1314 if (tpList == null) {
1317 return Iterables.get(tpList.values(), index).augmentation(OvsdbTerminationPointAugmentation.class);
1321 public void testCRUDTerminationPointIfIndex() throws InterruptedException {
1322 final boolean isOldSchema = schemaVersion.compareTo(IF_INDEX_FROM_VERSION) < 0;
1323 assumeFalse(isOldSchema);
1324 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1326 // Test create ifIndex
1327 try (TestBridge testBridge = new TestBridge(connectionInfo, null, SouthboundITConstants.BRIDGE_NAME, null, true,
1328 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"),
1329 true, SouthboundMapper.createDatapathType("netdev"), null, null, null)) {
1330 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1331 assertNotNull(bridge);
1332 LOG.info("bridge: {}", bridge);
1333 NodeId nodeId = SouthboundMapper.createManagedNodeId(SouthboundUtils.createInstanceIdentifier(
1334 connectionInfo, bridge.getBridgeName()));
1335 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1336 createGenericOvsdbTerminationPointAugmentationBuilder();
1337 String portName = "testIfIndex";
1338 ovsdbTerminationBuilder.setName(portName);
1340 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1341 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1342 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1343 assertNotNull(terminationPointNode);
1345 // Test read ifIndex
1346 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1347 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1348 terminationPoint.augmentation(OvsdbTerminationPointAugmentation.class);
1349 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1350 Long ifIndex = ovsdbTerminationPointAugmentation.getIfindex().toJava();
1351 assertNotNull(ifIndex);
1352 LOG.info("ifIndex: {} for the port:{}", ifIndex, portName);
1359 public void testCRDTerminationPointOfPort() throws InterruptedException {
1360 final Uint32 ofportExpected = Uint32.valueOf(45002);
1362 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1365 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
1366 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1367 assertNotNull(bridge);
1368 LOG.info("bridge: {}", bridge);
1369 NodeId nodeId = SouthboundMapper.createManagedNodeId(SouthboundUtils.createInstanceIdentifier(
1370 connectionInfo, bridge.getBridgeName()));
1371 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1372 createGenericOvsdbTerminationPointAugmentationBuilder();
1373 String portName = "testOfPort";
1374 ovsdbTerminationBuilder.setName(portName);
1376 ovsdbTerminationBuilder.setOfport(ofportExpected);
1377 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1378 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1379 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1380 assertNotNull(terminationPointNode);
1383 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1384 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1385 terminationPoint.augmentation(OvsdbTerminationPointAugmentation.class);
1386 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1387 Uint32 ofPort = ovsdbTerminationPointAugmentation.getOfport();
1388 // if ephemeral port 45002 is in use, ofPort is set to 1
1389 assertTrue(ofPort.equals(ofportExpected) || ofPort.equals(Uint32.ONE));
1390 LOG.info("ofPort: {}", ofPort);
1394 // UPDATE- Not Applicable. From the OpenVSwitch Documentation:
1395 // "A client should ideally set this column’s value in the same database transaction that it uses to
1396 // create the interface."
1398 // DELETE handled by TestBridge
1403 public void testCRDTerminationPointOfPortRequest() throws InterruptedException {
1404 final Uint32 ofportExpected = Uint32.valueOf(45008);
1405 final Uint32 ofportInput = Uint32.valueOf(45008);
1407 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1410 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
1411 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1412 assertNotNull(bridge);
1413 final NodeId nodeId = SouthboundUtils.createManagedNodeId(SouthboundUtils.createInstanceIdentifier(
1414 connectionInfo, bridge.getBridgeName()));
1415 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1416 createGenericOvsdbTerminationPointAugmentationBuilder();
1417 String portName = "testOfPortRequest";
1418 ovsdbTerminationBuilder.setName(portName);
1419 Uint16 ofPortRequestExpected = ofportExpected.toUint16();
1420 ovsdbTerminationBuilder.setOfport(ofportInput);
1421 ovsdbTerminationBuilder.setOfportRequest(ofPortRequestExpected);
1422 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1423 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1424 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1425 assertNotNull(terminationPointNode);
1428 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1429 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1430 terminationPoint.augmentation(OvsdbTerminationPointAugmentation.class);
1431 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1432 Uint32 ofPort = ovsdbTerminationPointAugmentation.getOfport();
1433 // if ephemeral port 45008 is in use, ofPort is set to 1
1434 assertTrue(ofPort.equals(ofportExpected) || ofPort.equals(Uint32.ONE));
1435 LOG.info("ofPort: {}", ofPort);
1437 Uint16 ofPortRequest = ovsdbTerminationPointAugmentation.getOfportRequest();
1438 assertEquals(ofPortRequestExpected, ofPortRequest);
1439 LOG.info("ofPortRequest: {}", ofPortRequest);
1443 // UPDATE- Not Applicable. From the OpenVSwitch documentation:
1444 // "A client should ideally set this column’s value in the same database transaction that it uses to
1445 // create the interface. "
1447 // DELETE handled by TestBridge
1451 private static <I extends Identifier<T>, T extends Identifiable<I>> void assertExpectedExist(
1452 final Map<I, T> expected, final Map<I, T> test) {
1453 if (expected != null && test != null) {
1454 for (T exp : expected.values()) {
1455 assertTrue("The retrieved values don't contain " + exp, test.containsValue(exp));
1460 private interface SouthboundTerminationPointHelper<I extends Identifier<T>, T extends Identifiable<I>> {
1461 void writeValues(OvsdbTerminationPointAugmentationBuilder builder, Map<I, T> values);
1463 Map<I, T> readValues(OvsdbTerminationPointAugmentation augmentation);
1467 * Tests the CRUD operations for <code>Port</code> <code>external_ids</code>.
1469 * @see <code>SouthboundIT.generatePortExternalIdsTestCases()</code> for specific test case information
1471 private static <I extends Identifier<T>, T extends Identifiable<I>> void testCRUDTerminationPoint(
1472 final KeyValueBuilder<T> builder, final String prefix, final SouthboundTerminationPointHelper<I, T> helper)
1473 throws InterruptedException {
1474 final int terminationPointTestIndex = 0;
1476 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1478 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
1479 // the update has been performed.
1480 List<SouthboundTestCase<I, T>> updateFromTestCases = generateKeyValueTestCases(builder, prefix + "From");
1481 List<SouthboundTestCase<I, T>> updateToTestCases = generateKeyValueTestCases(builder, prefix + "To");
1483 for (SouthboundTestCase<I, T> updateFromTestCase : updateFromTestCases) {
1484 for (SouthboundTestCase<I, T> updateToTestCase : updateToTestCases) {
1485 String testBridgeAndPortName = String.format("%s_%s", prefix, updateToTestCase.name);
1487 // CREATE: Create the test bridge
1488 try (TestBridge testBridge = new TestBridge(connectionInfo, null, testBridgeAndPortName, null, true,
1489 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"), true, null, null, null,
1491 NodeId testBridgeNodeId = SouthboundUtils.createManagedNodeId(
1492 SouthboundUtils.createInstanceIdentifier(connectionInfo,
1493 new OvsdbBridgeName(testBridgeAndPortName)));
1494 OvsdbTerminationPointAugmentationBuilder tpCreateAugmentationBuilder =
1495 createGenericOvsdbTerminationPointAugmentationBuilder();
1496 tpCreateAugmentationBuilder.setName(testBridgeAndPortName);
1497 helper.writeValues(tpCreateAugmentationBuilder, updateFromTestCase.inputValues);
1499 addTerminationPoint(testBridgeNodeId, testBridgeAndPortName, tpCreateAugmentationBuilder));
1501 // READ: Read the test port and ensure changes are propagated to the CONFIGURATION data store,
1502 // then repeat for OPERATIONAL data store
1503 OvsdbTerminationPointAugmentation updateFromConfigurationTerminationPointAugmentation =
1504 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeAndPortName,
1505 LogicalDatastoreType.CONFIGURATION, terminationPointTestIndex);
1506 if (updateFromConfigurationTerminationPointAugmentation != null) {
1507 Map<I, T> updateFromConfigurationValues =
1508 helper.readValues(updateFromConfigurationTerminationPointAugmentation);
1509 assertExpectedExist(updateFromTestCase.expectedValues, updateFromConfigurationValues);
1511 OvsdbTerminationPointAugmentation updateFromOperationalTerminationPointAugmentation =
1512 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeAndPortName,
1513 LogicalDatastoreType.OPERATIONAL, terminationPointTestIndex);
1514 if (updateFromOperationalTerminationPointAugmentation != null) {
1515 Map<I, T> updateFromOperationalValues =
1516 helper.readValues(updateFromOperationalTerminationPointAugmentation);
1517 assertExpectedExist(updateFromTestCase.expectedValues, updateFromOperationalValues);
1520 // UPDATE: update the values
1521 testBridgeNodeId = getBridgeNode(connectionInfo, testBridgeAndPortName).getNodeId();
1522 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1523 new OvsdbTerminationPointAugmentationBuilder();
1524 helper.writeValues(tpUpdateAugmentationBuilder, updateToTestCase.inputValues);
1525 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1526 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1527 NodeId portUpdateNodeId = SouthboundUtils.createManagedNodeId(portIid);
1528 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1529 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1530 tpUpdateBuilder.withKey(new TerminationPointKey(new TpId(testBridgeAndPortName)));
1531 tpUpdateBuilder.addAugmentation(tpUpdateAugmentationBuilder.build());
1532 portUpdateNodeBuilder.setTerminationPoint(BindingMap.of(tpUpdateBuilder.build()));
1533 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
1534 portIid, portUpdateNodeBuilder.build()));
1535 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1537 // READ: the test port and ensure changes are propagated to the CONFIGURATION data store,
1538 // then repeat for OPERATIONAL data store
1539 OvsdbTerminationPointAugmentation updateToConfigurationTerminationPointAugmentation =
1540 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeAndPortName,
1541 LogicalDatastoreType.CONFIGURATION, terminationPointTestIndex);
1542 if (updateToConfigurationTerminationPointAugmentation != null) {
1543 Map<I, T> updateToConfigurationValues =
1544 helper.readValues(updateToConfigurationTerminationPointAugmentation);
1545 assertExpectedExist(updateToTestCase.expectedValues, updateToConfigurationValues);
1546 assertExpectedExist(updateFromTestCase.expectedValues, updateToConfigurationValues);
1548 OvsdbTerminationPointAugmentation updateToOperationalTerminationPointAugmentation =
1549 getOvsdbTerminationPointAugmentation(connectionInfo, testBridgeAndPortName,
1550 LogicalDatastoreType.OPERATIONAL, terminationPointTestIndex);
1551 if (updateToOperationalTerminationPointAugmentation != null) {
1552 Map<I, T> updateToOperationalValues =
1553 helper.readValues(updateToOperationalTerminationPointAugmentation);
1554 if (updateFromTestCase.expectedValues != null) {
1555 assertExpectedExist(updateToTestCase.expectedValues, updateToOperationalValues);
1556 assertExpectedExist(updateFromTestCase.expectedValues, updateToOperationalValues);
1560 // DELETE handled by TestBridge
1567 * Tests the CRUD operations for <code>Port</code> <code>external_ids</code>.
1569 * @see <code>SouthboundIT.generatePortExternalIdsTestCases()</code> for specific test case information
1572 public void testCRUDTerminationPointPortExternalIds() throws InterruptedException {
1573 testCRUDTerminationPoint(new SouthboundPortExternalIdsBuilder(), "TPPortExternalIds",
1574 new PortExternalIdsSouthboundHelper());
1578 * Tests the CRUD operations for <code>Interface</code> <code>external_ids</code>.
1580 * @see <code>SouthboundIT.generateInterfaceExternalIdsTestCases()</code> for specific test case information
1583 public void testCRUDTerminationPointInterfaceExternalIds() throws InterruptedException {
1584 testCRUDTerminationPoint(new SouthboundInterfaceExternalIdsBuilder(), "TPInterfaceExternalIds",
1585 new InterfaceExternalIdsSouthboundHelper());
1589 * Tests the CRUD operations for <code>Interface</code> <code>lldp</code>.
1591 * @see <code>SouthboundIT.generateInterfaceLldpTestCases()</code> for specific test case information
1594 public void testCRUDTerminationPointInterfaceLldp() throws InterruptedException {
1595 testCRUDTerminationPoint(new SouthboundInterfaceLldpBuilder(), "TPInterfaceLldp",
1596 new InterfaceLldpSouthboundHelper());
1600 * Tests the CRUD operations for <code>TerminationPoint</code> <code>options</code>.
1602 * @see <code>SouthboundIT.generateTerminationPointOptions()</code> for specific test case information
1605 public void testCRUDTerminationPointOptions() throws InterruptedException {
1606 testCRUDTerminationPoint(new SouthboundOptionsBuilder(), "TPOptions", new OptionsSouthboundHelper());
1610 * Tests the CRUD operations for <code>Interface</code> <code>other_configs</code>.
1612 * @see <code>SouthboundIT.generateInterfaceExternalIdsTestCases()</code> for specific test case information
1615 public void testCRUDTerminationPointInterfaceOtherConfigs() throws InterruptedException {
1616 testCRUDTerminationPoint(new SouthboundInterfaceOtherConfigsBuilder(), "TPInterfaceOtherConfigs",
1617 new InterfaceOtherConfigsSouthboundHelper());
1621 * Tests the CRUD operations for <code>Port</code> <code>other_configs</code>.
1623 * @see <code>SouthboundIT.generatePortExternalIdsTestCases()</code> for specific test case information
1626 public void testCRUDTerminationPointPortOtherConfigs() throws InterruptedException {
1627 testCRUDTerminationPoint(new SouthboundPortOtherConfigsBuilder(), "TPPortOtherConfigs",
1628 new PortOtherConfigsSouthboundHelper());
1632 public void testCRUDTerminationPoints() throws InterruptedException {
1633 String port1 = "vx1";
1634 String port2 = "vxlanport";
1635 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1637 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
1638 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME);
1639 assertNotNull(bridge);
1640 NodeId nodeId = SouthboundUtils.createManagedNodeId(SouthboundUtils.createInstanceIdentifier(
1641 connectionInfo, bridge.getBridgeName()));
1642 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1643 createGenericOvsdbTerminationPointAugmentationBuilder();
1645 // add and delete a single port
1646 String portName = port1;
1647 ovsdbTerminationBuilder.setName(portName);
1648 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1649 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1650 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1651 assertNotNull(terminationPointNode);
1653 SouthboundUtils.createInstanceIdentifier(connectionInfo,
1654 new OvsdbBridgeName(SouthboundITConstants.BRIDGE_NAME));
1656 InstanceIdentifier<TerminationPoint> nodePath =
1657 SouthboundUtils.createInstanceIdentifier(connectionInfo,
1658 new OvsdbBridgeName(SouthboundITConstants.BRIDGE_NAME))
1659 .child(TerminationPoint.class, new TerminationPointKey(new TpId(portName)));
1661 assertTrue("failed to delete port " + portName,
1662 mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, nodePath));
1663 LOG.info("shague: waiting for delete {}", portName);
1665 TerminationPoint terminationPoint = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, nodePath);
1666 assertNull(terminationPoint);
1668 // add two ports, then delete them
1670 ovsdbTerminationBuilder.setName(portName);
1671 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1672 terminationPointIid = getTpIid(connectionInfo, bridge);
1673 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1674 assertNotNull(terminationPointNode);
1677 ovsdbTerminationBuilder.setName(portName);
1678 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1679 terminationPointIid = getTpIid(connectionInfo, bridge);
1680 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1681 assertNotNull(terminationPointNode);
1683 SouthboundUtils.createInstanceIdentifier(connectionInfo,
1684 new OvsdbBridgeName(SouthboundITConstants.BRIDGE_NAME));
1687 SouthboundUtils.createInstanceIdentifier(connectionInfo,
1688 new OvsdbBridgeName(SouthboundITConstants.BRIDGE_NAME))
1689 .child(TerminationPoint.class, new TerminationPointKey(new TpId(portName)));
1691 assertTrue("failed to delete port " + portName,
1692 mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, nodePath));
1693 LOG.info("shague: waiting for delete {}", portName);
1695 terminationPoint = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, nodePath);
1696 assertNull(terminationPoint);
1699 nodePath = SouthboundUtils.createInstanceIdentifier(connectionInfo,
1700 new OvsdbBridgeName(SouthboundITConstants.BRIDGE_NAME))
1701 .child(TerminationPoint.class, new TerminationPointKey(new TpId(portName)));
1703 assertTrue("failed to delete port " + portName,
1704 mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, nodePath));
1705 LOG.info("shague: waiting for delete {}", portName);
1707 terminationPoint = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, nodePath);
1708 assertNull(terminationPoint);
1710 // DELETE handled by TestBridge
1715 public void testCRUDTerminationPointVlan() throws InterruptedException {
1716 final Uint16 createdVlanId = Uint16.valueOf(4000);
1717 final Uint16 updatedVlanId = Uint16.valueOf(4001);
1719 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1722 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
1723 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME);
1724 assertNotNull(bridge);
1725 NodeId nodeId = SouthboundUtils.createManagedNodeId(SouthboundUtils.createInstanceIdentifier(
1726 connectionInfo, bridge.getBridgeName()));
1727 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1728 createGenericOvsdbTerminationPointAugmentationBuilder();
1729 String portName = "testTerminationPointVlanId";
1730 ovsdbTerminationBuilder.setName(portName);
1731 ovsdbTerminationBuilder.setVlanTag(new VlanId(createdVlanId));
1732 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1733 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1734 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1735 assertNotNull(terminationPointNode);
1738 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation;
1739 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1740 ovsdbTerminationPointAugmentation = terminationPoint.augmentation(
1741 OvsdbTerminationPointAugmentation.class);
1742 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1743 VlanId actualVlanId = ovsdbTerminationPointAugmentation.getVlanTag();
1744 assertNotNull(actualVlanId);
1745 assertEquals(createdVlanId, actualVlanId.getValue());
1750 NodeId testBridgeNodeId = getBridgeNode(connectionInfo, SouthboundITConstants.BRIDGE_NAME).getNodeId();
1751 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1752 new OvsdbTerminationPointAugmentationBuilder();
1753 tpUpdateAugmentationBuilder.setVlanTag(new VlanId(updatedVlanId));
1754 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1755 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1756 NodeId portUpdateNodeId = SouthboundUtils.createManagedNodeId(portIid);
1757 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1758 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1759 tpUpdateBuilder.withKey(new TerminationPointKey(new TpId(portName)));
1760 tpUpdateBuilder.addAugmentation(tpUpdateAugmentationBuilder.build());
1761 tpUpdateBuilder.setTpId(new TpId(portName));
1762 portUpdateNodeBuilder.setTerminationPoint(BindingMap.of(tpUpdateBuilder.build()));
1764 mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, portIid, portUpdateNodeBuilder.build()));
1765 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1767 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1768 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1769 ovsdbTerminationPointAugmentation = terminationPoint.augmentation(
1770 OvsdbTerminationPointAugmentation.class);
1771 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1772 VlanId actualVlanId = ovsdbTerminationPointAugmentation.getVlanTag();
1773 assertNotNull(actualVlanId);
1774 assertEquals(updatedVlanId, actualVlanId.getValue());
1778 // DELETE handled by TestBridge
1783 public void testCRUDTerminationPointVlanModes() throws InterruptedException {
1784 final VlanMode updatedVlanMode = VlanMode.Access;
1785 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1786 VlanMode []vlanModes = VlanMode.values();
1787 for (VlanMode vlanMode : vlanModes) {
1789 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
1790 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1791 assertNotNull(bridge);
1792 NodeId nodeId = SouthboundUtils.createManagedNodeId(SouthboundUtils.createInstanceIdentifier(
1793 connectionInfo, bridge.getBridgeName()));
1794 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1795 createGenericOvsdbTerminationPointAugmentationBuilder();
1796 String portName = "testTerminationPointVlanMode" + vlanMode.toString();
1797 ovsdbTerminationBuilder.setName(portName);
1798 ovsdbTerminationBuilder.setVlanMode(vlanMode);
1799 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1800 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1801 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1802 assertNotNull(terminationPointNode);
1805 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1806 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1807 terminationPoint.augmentation(OvsdbTerminationPointAugmentation.class);
1808 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1810 assertTrue(ovsdbTerminationPointAugmentation.getVlanMode().equals(vlanMode));
1815 NodeId testBridgeNodeId = getBridgeNode(connectionInfo, SouthboundITConstants.BRIDGE_NAME).getNodeId();
1816 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1817 new OvsdbTerminationPointAugmentationBuilder();
1818 tpUpdateAugmentationBuilder.setVlanMode(updatedVlanMode);
1819 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1820 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1821 NodeId portUpdateNodeId = SouthboundUtils.createManagedNodeId(portIid);
1822 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1823 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1824 tpUpdateBuilder.withKey(new TerminationPointKey(new TpId(portName)));
1825 tpUpdateBuilder.addAugmentation(tpUpdateAugmentationBuilder.build());
1826 tpUpdateBuilder.setTpId(new TpId(portName));
1827 portUpdateNodeBuilder.setTerminationPoint(BindingMap.of(tpUpdateBuilder.build()));
1829 mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, portIid, portUpdateNodeBuilder.build()));
1830 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1832 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1833 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1834 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1835 terminationPoint.augmentation(OvsdbTerminationPointAugmentation.class);
1836 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1838 assertEquals(updatedVlanMode, ovsdbTerminationPointAugmentation.getVlanMode());
1842 // DELETE handled by TestBridge
1847 private static List<Set<Uint16>> generateVlanSets() {
1850 return Lists.newArrayList(
1851 Collections.<Uint16>emptySet(),
1852 Collections.singleton(Uint16.valueOf(2222)),
1853 Sets.newHashSet(Uint16.valueOf(min), Uint16.valueOf(max), Uint16.valueOf(min + 1),
1854 Uint16.valueOf(max - 1), Uint16.valueOf((max - min) / 2)));
1857 private static List<Trunks> buildTrunkList(final Set<Uint16> trunkSet) {
1858 List<Trunks> trunkList = new ArrayList<>();
1859 for (Uint16 trunk : trunkSet) {
1860 trunkList.add(new TrunksBuilder().setTrunk(new VlanId(trunk)).build());
1866 public void testCRUDTerminationPointVlanTrunks() throws InterruptedException {
1867 final List<Trunks> updatedTrunks = buildTrunkList(Collections.singleton(Uint16.valueOf(2011)));
1868 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1869 Iterable<Set<Uint16>> vlanSets = generateVlanSets();
1871 for (Set<Uint16> vlanSet : vlanSets) {
1874 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME)) {
1875 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1876 assertNotNull(bridge);
1877 NodeId nodeId = SouthboundUtils.createManagedNodeId(connectionInfo, bridge.getBridgeName());
1878 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1879 createGenericOvsdbTerminationPointAugmentationBuilder();
1880 String portName = "testTerminationPointVlanTrunks" + testCase;
1881 ovsdbTerminationBuilder.setName(portName);
1882 List<Trunks> trunks = buildTrunkList(vlanSet);
1883 ovsdbTerminationBuilder.setTrunks(trunks);
1884 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1885 InstanceIdentifier<Node> terminationPointIid = getTpIid(connectionInfo, bridge);
1886 Node terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1887 assertNotNull(terminationPointNode);
1890 Collection<TerminationPoint> terminationPoints =
1891 terminationPointNode.nonnullTerminationPoint().values();
1892 for (TerminationPoint terminationPoint : terminationPoints) {
1893 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1894 terminationPoint.augmentation(OvsdbTerminationPointAugmentation.class);
1895 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1896 List<Trunks> actualTrunks = ovsdbTerminationPointAugmentation.getTrunks();
1897 for (Trunks trunk : trunks) {
1898 assertTrue(actualTrunks.contains(trunk));
1905 NodeId testBridgeNodeId = getBridgeNode(connectionInfo, SouthboundITConstants.BRIDGE_NAME).getNodeId();
1906 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1907 new OvsdbTerminationPointAugmentationBuilder();
1908 tpUpdateAugmentationBuilder.setTrunks(updatedTrunks);
1909 InstanceIdentifier<Node> portIid = SouthboundMapper.createInstanceIdentifier(testBridgeNodeId);
1910 NodeBuilder portUpdateNodeBuilder = new NodeBuilder();
1911 NodeId portUpdateNodeId = SouthboundUtils.createManagedNodeId(portIid);
1912 portUpdateNodeBuilder.setNodeId(portUpdateNodeId);
1913 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1914 tpUpdateBuilder.withKey(new TerminationPointKey(new TpId(portName)));
1915 tpUpdateBuilder.addAugmentation(tpUpdateAugmentationBuilder.build());
1916 tpUpdateBuilder.setTpId(new TpId(portName));
1917 portUpdateNodeBuilder.setTerminationPoint(BindingMap.of(tpUpdateBuilder.build()));
1919 mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, portIid, portUpdateNodeBuilder.build()));
1920 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1922 terminationPointNode = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, terminationPointIid);
1923 for (TerminationPoint terminationPoint : terminationPointNode.nonnullTerminationPoint().values()) {
1924 OvsdbTerminationPointAugmentation ovsdbTerminationPointAugmentation =
1925 terminationPoint.augmentation(OvsdbTerminationPointAugmentation.class);
1926 if (ovsdbTerminationPointAugmentation.getName().equals(portName)) {
1928 assertEquals(updatedTrunks, ovsdbTerminationPointAugmentation.getTrunks());
1932 // DELETE handled by TestBridge
1938 * Tests setting and deleting <code>qos</code> field in a <code>port</code>.
1941 public void testCRUDTerminationPointQos() throws InterruptedException {
1942 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1943 String testQosId = "testQosEntry";
1946 try (TestBridge testBridge = new TestBridge(connectionInfo, SouthboundITConstants.BRIDGE_NAME);
1947 TestQos testQos = new TestQos(connectionInfo, new Uri(testQosId),
1948 SouthboundMapper.createQosType(SouthboundConstants.QOS_LINUX_HFSC), null, null)) {
1949 OvsdbNodeAugmentation ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
1950 LogicalDatastoreType.OPERATIONAL);
1951 QosEntries operQos = getQos(new Uri(testQosId), ovsdbNodeAugmentation);
1952 assertNotNull(operQos);
1953 OvsdbBridgeAugmentation bridge = getBridge(connectionInfo);
1954 assertNotNull(bridge);
1955 NodeId nodeId = SouthboundUtils.createManagedNodeId(connectionInfo, bridge.getBridgeName());
1956 OvsdbTerminationPointAugmentationBuilder ovsdbTerminationBuilder =
1957 createGenericOvsdbTerminationPointAugmentationBuilder();
1958 String portName = "testTerminationPointQos";
1959 ovsdbTerminationBuilder.setName(portName);
1960 assertTrue(addTerminationPoint(nodeId, portName, ovsdbTerminationBuilder));
1963 // READ and check that qos uuid has been added to the port
1964 InstanceIdentifier<TerminationPoint> tpEntryIid = getTpIid(connectionInfo, bridge)
1965 .child(TerminationPoint.class, new TerminationPointKey(new TpId(portName)));
1966 TerminationPoint terminationPoint = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, tpEntryIid);
1967 assertNotNull(terminationPoint);
1969 // UPDATE - remove the qos entry from the port
1970 OvsdbTerminationPointAugmentationBuilder tpUpdateAugmentationBuilder =
1971 new OvsdbTerminationPointAugmentationBuilder();
1972 tpUpdateAugmentationBuilder.setName(portName);
1973 TerminationPointBuilder tpUpdateBuilder = new TerminationPointBuilder();
1974 tpUpdateBuilder.withKey(new TerminationPointKey(new TpId(portName)));
1975 tpUpdateBuilder.addAugmentation(tpUpdateAugmentationBuilder.build());
1976 tpUpdateBuilder.setTpId(new TpId(portName));
1979 mdsalUtils.put(LogicalDatastoreType.CONFIGURATION, tpEntryIid, tpUpdateBuilder.build()));
1980 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
1982 // READ and verify that qos uuid has been removed from port
1983 TerminationPoint terminationPointUpdate = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, tpEntryIid);
1984 assertNotNull(terminationPointUpdate);
1986 // DELETE handled by TestBridge
1991 public void testGetOvsdbNodes() throws InterruptedException {
1992 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
1993 InstanceIdentifier<Topology> topologyPath = InstanceIdentifier
1994 .create(NetworkTopology.class)
1995 .child(Topology.class, new TopologyKey(SouthboundConstants.OVSDB_TOPOLOGY_ID));
1997 Topology topology = mdsalUtils.read(LogicalDatastoreType.OPERATIONAL, topologyPath);
1998 InstanceIdentifier<Node> expectedNodeIid = SouthboundUtils.createInstanceIdentifier(connectionInfo);
1999 NodeId expectedNodeId = expectedNodeIid.firstKeyOf(Node.class).getNodeId();
2000 Node foundNode = null;
2001 assertNotNull("Expected to find topology: " + topologyPath, topology);
2002 assertNotNull("Expected to find some nodes" + topology.getNode());
2003 LOG.info("expectedNodeId: {}, getNode: {}", expectedNodeId, topology.getNode());
2004 for (Node node : topology.nonnullNode().values()) {
2005 if (node.getNodeId().getValue().equals(expectedNodeId.getValue())) {
2010 assertNotNull("Expected to find Node: " + expectedNodeId, foundNode);
2014 * @see <code>SouthboundIT.generateBridgeOtherConfigsTestCases()</code> for specific test case information.
2017 public void testCRUDBridgeOtherConfigs() throws InterruptedException {
2018 testCRUDBridge("BridgeOtherConfigs", new SouthboundBridgeOtherConfigsBuilder(),
2019 new BridgeOtherConfigsSouthboundHelper());
2022 private interface SouthboundBridgeHelper<I extends Identifier<T>, T extends Identifiable<I>> {
2023 void writeValues(OvsdbBridgeAugmentationBuilder builder, Map<I, T> values);
2025 Map<I, T> readValues(OvsdbBridgeAugmentation augmentation);
2028 private static <I extends Identifier<T>, T extends Identifiable<I>> void testCRUDBridge(final String prefix,
2029 final KeyValueBuilder<T> builder, final SouthboundBridgeHelper<I, T> helper) throws InterruptedException {
2030 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
2031 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
2032 // the update has been performed.
2033 List<SouthboundTestCase<I, T>> updateFromTestCases = generateKeyValueTestCases(builder, prefix + "From");
2034 List<SouthboundTestCase<I, T>> updateToTestCases = generateKeyValueTestCases(builder, prefix + "To");
2035 for (SouthboundTestCase<I, T> updateFromTestCase : updateFromTestCases) {
2036 for (SouthboundTestCase<I, T> updateToTestCase : updateToTestCases) {
2037 String testBridgeName = String.format("%s_%s", prefix, updateToTestCase.name);
2039 // CREATE: Create the test bridge
2040 final OvsdbBridgeName ovsdbBridgeName = new OvsdbBridgeName(testBridgeName);
2041 final InstanceIdentifier<Node> bridgeIid =
2042 SouthboundUtils.createInstanceIdentifier(connectionInfo, ovsdbBridgeName);
2043 final NodeId bridgeNodeId = SouthboundMapper.createManagedNodeId(bridgeIid);
2044 final NodeBuilder bridgeCreateNodeBuilder = new NodeBuilder();
2045 bridgeCreateNodeBuilder.setNodeId(bridgeNodeId);
2046 OvsdbBridgeAugmentationBuilder bridgeCreateAugmentationBuilder = new OvsdbBridgeAugmentationBuilder();
2047 bridgeCreateAugmentationBuilder.setBridgeName(ovsdbBridgeName);
2048 bridgeCreateAugmentationBuilder.setProtocolEntry(createMdsalProtocols());
2049 bridgeCreateAugmentationBuilder.setFailMode(
2050 SouthboundConstants.OVSDB_FAIL_MODE_MAP.inverse().get("secure"));
2051 setManagedBy(bridgeCreateAugmentationBuilder, connectionInfo);
2052 helper.writeValues(bridgeCreateAugmentationBuilder, updateFromTestCase.inputValues);
2053 bridgeCreateNodeBuilder.addAugmentation(bridgeCreateAugmentationBuilder.build());
2054 LOG.debug("Built with the intent to store bridge data {}", bridgeCreateAugmentationBuilder);
2055 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, bridgeIid,
2056 bridgeCreateNodeBuilder.build()));
2057 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
2059 // READ: Read the test bridge and ensure changes are propagated to the CONFIGURATION data store,
2060 // then repeat for OPERATIONAL data store
2061 Map<I, T> updateFromConfigurationExternalIds = helper.readValues(getBridge(connectionInfo,
2062 testBridgeName, LogicalDatastoreType.CONFIGURATION));
2063 assertExpectedExist(updateFromTestCase.expectedValues, updateFromConfigurationExternalIds);
2064 Map<I, T> updateFromOperationalExternalIds = helper.readValues(getBridge(connectionInfo,
2066 assertExpectedExist(updateFromTestCase.expectedValues, updateFromOperationalExternalIds);
2068 // UPDATE: update the values
2069 final OvsdbBridgeAugmentationBuilder bridgeUpdateAugmentationBuilder =
2070 new OvsdbBridgeAugmentationBuilder();
2071 helper.writeValues(bridgeUpdateAugmentationBuilder, updateToTestCase.inputValues);
2072 final NodeBuilder bridgeUpdateNodeBuilder = new NodeBuilder();
2073 final Node bridgeNode = getBridgeNode(connectionInfo, testBridgeName);
2074 bridgeUpdateNodeBuilder.setNodeId(bridgeNode.getNodeId());
2075 bridgeUpdateNodeBuilder.withKey(bridgeNode.key());
2076 bridgeUpdateNodeBuilder.addAugmentation(bridgeUpdateAugmentationBuilder.build());
2077 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION, bridgeIid,
2078 bridgeUpdateNodeBuilder.build()));
2079 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
2081 // READ: the test bridge and ensure changes are propagated to the CONFIGURATION data store,
2082 // then repeat for OPERATIONAL data store
2083 Map<I, T> updateToConfigurationExternalIds = helper.readValues(getBridge(connectionInfo, testBridgeName,
2084 LogicalDatastoreType.CONFIGURATION));
2085 assertExpectedExist(updateToTestCase.expectedValues, updateToConfigurationExternalIds);
2086 assertExpectedExist(updateFromTestCase.expectedValues, updateToConfigurationExternalIds);
2087 Map<I, T> updateToOperationalExternalIds = helper.readValues(getBridge(connectionInfo, testBridgeName));
2088 if (updateFromTestCase.expectedValues != null) {
2089 assertExpectedExist(updateToTestCase.expectedValues, updateToOperationalExternalIds);
2090 assertExpectedExist(updateFromTestCase.expectedValues, updateToOperationalExternalIds);
2094 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, bridgeIid));
2095 Thread.sleep(OVSDB_UPDATE_TIMEOUT);
2101 * @see <code>SouthboundIT.generateBridgeExternalIdsTestCases()</code> for specific test case information
2104 public void testCRUDBridgeExternalIds() throws InterruptedException {
2105 testCRUDBridge("BridgeExternalIds", new SouthboundBridgeExternalIdsBuilder(),
2106 new BridgeExternalIdsSouthboundHelper());
2110 public void testAddDeleteQos() throws InterruptedException {
2111 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
2112 OvsdbNodeAugmentation ovsdbNodeAugmentation;
2113 Uri qosUri = new Uri("QOS-ROW");
2114 List<String> typeList = new ArrayList<>();
2115 typeList.add(SouthboundConstants.QOS_LINUX_HTB);
2116 typeList.add(SouthboundConstants.QOS_LINUX_HFSC);
2118 for (String qosType : typeList) {
2119 try (TestQos testQos = new TestQos(connectionInfo, qosUri, SouthboundMapper.createQosType(qosType),
2121 ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2122 LogicalDatastoreType.OPERATIONAL);
2123 QosEntries operQosHtb = getQos(qosUri, ovsdbNodeAugmentation);
2124 assertNotNull(operQosHtb);
2126 ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2127 LogicalDatastoreType.OPERATIONAL);
2128 QosEntries operQosHtb = getQos(qosUri, ovsdbNodeAugmentation);
2129 assertNull(operQosHtb);
2134 public void testAddDeleteQueue() throws InterruptedException {
2135 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
2136 Uri queueUri = new Uri("QUEUE-A1");
2138 try (TestQueue testQueue = new TestQueue(connectionInfo, queueUri, Uint8.valueOf(25), null, null)) {
2139 OvsdbNodeAugmentation ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2140 LogicalDatastoreType.OPERATIONAL);
2141 Queues operQueue = getQueue(queueUri, ovsdbNodeAugmentation);
2142 assertNotNull(operQueue);
2144 OvsdbNodeAugmentation ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2145 LogicalDatastoreType.OPERATIONAL);
2146 Queues operQueue = getQueue(queueUri, ovsdbNodeAugmentation);
2147 assertNull(operQueue);
2150 private static class SouthboundQueuesExternalIdsHelper
2151 implements SouthboundQueueHelper<QueuesExternalIdsKey, QueuesExternalIds> {
2153 public void writeValues(final QueuesBuilder builder,
2154 final Map<QueuesExternalIdsKey, QueuesExternalIds> values) {
2155 builder.setQueuesExternalIds(values);
2159 public Map<QueuesExternalIdsKey, QueuesExternalIds> readValues(final Queues queue) {
2160 return queue.getQueuesExternalIds();
2164 private static class SouthboundQueuesOtherConfigHelper
2165 implements SouthboundQueueHelper<QueuesOtherConfigKey, QueuesOtherConfig> {
2167 public void writeValues(final QueuesBuilder builder,
2168 final Map<QueuesOtherConfigKey, QueuesOtherConfig> values) {
2169 builder.setQueuesOtherConfig(values);
2173 public Map<QueuesOtherConfigKey, QueuesOtherConfig> readValues(final Queues queue) {
2174 return queue.getQueuesOtherConfig();
2178 private interface SouthboundQueueHelper<I extends Identifier<T>, T extends Identifiable<I>> {
2179 void writeValues(QueuesBuilder builder, Map<I, T> values);
2181 Map<I, T> readValues(Queues queue);
2184 private static Queues getQueue(final Uri queueId, final OvsdbNodeAugmentation node) {
2185 for (Queues queue : node.nonnullQueues().values()) {
2186 if (queue.key().getQueueId().getValue().equals(queueId.getValue())) {
2193 private static class SouthboundQosExternalIdsHelper
2194 implements SouthboundQosHelper<QosExternalIdsKey, QosExternalIds> {
2196 public void writeValues(final QosEntriesBuilder builder, final Map<QosExternalIdsKey, QosExternalIds> values) {
2197 builder.setQosExternalIds(values);
2201 public Map<QosExternalIdsKey, QosExternalIds> readValues(final QosEntries qos) {
2202 return qos.getQosExternalIds();
2206 private static class SouthboundQosOtherConfigHelper
2207 implements SouthboundQosHelper<QosOtherConfigKey, QosOtherConfig> {
2209 public void writeValues(final QosEntriesBuilder builder, final Map<QosOtherConfigKey, QosOtherConfig> values) {
2210 builder.setQosOtherConfig(values);
2214 public Map<QosOtherConfigKey, QosOtherConfig> readValues(final QosEntries qos) {
2215 return qos.getQosOtherConfig();
2219 private interface SouthboundQosHelper<I extends Identifier<T>, T extends Identifiable<I>> {
2220 void writeValues(QosEntriesBuilder builder, Map<I, T> values);
2222 Map<I, T> readValues(QosEntries qos);
2225 private static QosEntries getQos(final Uri qosId, final OvsdbNodeAugmentation node) {
2226 for (QosEntries qos : node.nonnullQosEntries().values()) {
2227 if (qos.key().getQosId().equals(qosId)) {
2234 private static <I extends Identifier<T>, T extends Identifiable<I>> void testCRUDQueue(
2235 final KeyValueBuilder<T> builder, final String prefix, final SouthboundQueueHelper<I, T> helper)
2236 throws InterruptedException {
2238 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
2240 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
2241 // the update has been performed.
2242 List<SouthboundTestCase<I, T>> updateFromTestCases = generateKeyValueTestCases(builder, prefix + "From");
2243 List<SouthboundTestCase<I, T>> updateToTestCases = generateKeyValueTestCases(builder, prefix + "To");
2245 for (SouthboundTestCase<I, T> updateFromTestCase : updateFromTestCases) {
2246 for (SouthboundTestCase<I, T> updateToTestCase : updateToTestCases) {
2247 String testQueueId = String.format("%s_%s", prefix, updateToTestCase.name);
2249 // CREATE: and update the test queue with starting values.
2250 try (TestQueue testQueue = new TestQueue(connectionInfo, new Uri(testQueueId),
2251 Uint8.valueOf(45), null, null)) {
2252 QueuesBuilder queuesBuilder = new QueuesBuilder();
2253 queuesBuilder.setQueueId(new Uri(testQueueId));
2254 InstanceIdentifier<Queues> queueIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
2255 .augmentation(OvsdbNodeAugmentation.class)
2256 .child(Queues.class, queuesBuilder.build().key());
2257 final NotifyingDataChangeListener queueConfigurationListener =
2258 new NotifyingDataChangeListener(LogicalDatastoreType.CONFIGURATION, queueIid);
2259 queueConfigurationListener.registerDataChangeListener();
2260 final NotifyingDataChangeListener queueOperationalListener =
2261 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, queueIid);
2262 queueOperationalListener.registerDataChangeListener();
2264 helper.writeValues(queuesBuilder, updateFromTestCase.inputValues);
2265 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
2266 queueIid, queuesBuilder.build()));
2267 queueConfigurationListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2269 // READ: Read the test queue and ensure changes are propagated to the CONFIGURATION data store,
2270 // then repeat for OPERATIONAL data store
2271 OvsdbNodeAugmentation updateFromConfigurationOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2272 LogicalDatastoreType.CONFIGURATION);
2273 Queues queueFromConfig =
2274 getQueue(new Uri(testQueueId), updateFromConfigurationOvsdbNodeAugmentation);
2275 if (queueFromConfig != null) {
2276 assertExpectedExist(updateFromTestCase.expectedValues, helper.readValues(queueFromConfig));
2279 queueOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2280 OvsdbNodeAugmentation updateFromOperationalOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2281 LogicalDatastoreType.OPERATIONAL);
2282 Queues queueFromOper = getQueue(new Uri(testQueueId), updateFromOperationalOvsdbNodeAugmentation);
2283 if (queueFromOper != null) {
2284 assertExpectedExist(updateFromTestCase.expectedValues, helper.readValues(queueFromOper));
2287 // UPDATE: update the values
2288 QueuesBuilder queuesUpdateBuilder = new QueuesBuilder();
2289 queuesUpdateBuilder.setQueueId(new Uri(testQueueId));
2290 helper.writeValues(queuesUpdateBuilder, updateToTestCase.inputValues);
2291 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
2292 queueIid, queuesUpdateBuilder.build()));
2293 queueConfigurationListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2295 // READ: the test queue and ensure changes are propagated to the CONFIGURATION data store,
2296 // then repeat for OPERATIONAL data store
2297 OvsdbNodeAugmentation updateToConfigurationOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2298 LogicalDatastoreType.CONFIGURATION);
2299 Queues queueToConfig = getQueue(new Uri(testQueueId), updateToConfigurationOvsdbNodeAugmentation);
2300 if (queueToConfig != null) {
2301 assertExpectedExist(updateToTestCase.expectedValues, helper.readValues(queueToConfig));
2304 queueOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2305 OvsdbNodeAugmentation updateToOperationalOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2306 LogicalDatastoreType.OPERATIONAL);
2307 Queues queueToOper = getQueue(new Uri(testQueueId), updateToOperationalOvsdbNodeAugmentation);
2308 if (queueToOper != null) {
2309 assertExpectedExist(updateToTestCase.expectedValues, helper.readValues(queueToOper));
2312 // DELETE handled by TestQueue
2319 public void testCRUDQueueExternalIds() throws InterruptedException {
2320 testCRUDQueue(new SouthboundQueuesExternalIdsBuilder(), "QueueExternalIds",
2321 new SouthboundQueuesExternalIdsHelper());
2325 public void testCRUDQueueOtherConfig() throws InterruptedException {
2326 testCRUDQueue(new SouthboundQueuesOtherConfigBuilder(), "QueueOtherConfig",
2327 new SouthboundQueuesOtherConfigHelper());
2331 public void testCRUDQueueDscp() throws InterruptedException {
2332 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
2333 String testQueueId = "testQueueDscp";
2335 // CREATE: and update the test queue with starting values.
2336 try (TestQueue testQueue = new TestQueue(connectionInfo, new Uri(testQueueId), Uint8.ZERO, null, null)) {
2337 for (short dscp = 1; dscp < 64; dscp++) {
2338 QueuesBuilder queuesBuilder = new QueuesBuilder();
2339 queuesBuilder.setQueueId(new Uri(testQueueId));
2340 InstanceIdentifier<Queues> queueIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
2341 .augmentation(OvsdbNodeAugmentation.class)
2342 .child(Queues.class, queuesBuilder.build().key());
2343 final NotifyingDataChangeListener queueOperationalListener =
2344 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, queueIid);
2345 queueOperationalListener.registerDataChangeListener();
2347 queuesBuilder.setDscp(Uint8.valueOf(dscp));
2348 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
2349 queueIid, queuesBuilder.build()));
2350 queueOperationalListener.waitForUpdate(OVSDB_ROUNDTRIP_TIMEOUT);
2352 // READ: Read the test queue and ensure changes are propagated to the OPERATIONAL data store
2353 // assumption is that CONFIGURATION was updated if OPERATIONAL is correct
2354 OvsdbNodeAugmentation ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2355 LogicalDatastoreType.OPERATIONAL);
2356 Queues operQueue = getQueue(new Uri(testQueueId), ovsdbNodeAugmentation);
2357 assertNotNull(operQueue);
2358 assertEquals(dscp, operQueue.getDscp().toJava());
2361 // DELETE handled by TestQueue
2366 private static <I extends Identifier<T>, T extends Identifiable<I>> void testCRUDQos(
2367 final KeyValueBuilder<T> builder, final String prefix, final SouthboundQosHelper<I, T> helper)
2368 throws InterruptedException {
2370 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
2372 // updateFromTestCases represent the original test case value. updateToTestCases represent the new value after
2373 // the update has been performed.
2374 List<SouthboundTestCase<I, T>> updateFromTestCases = generateKeyValueTestCases(builder, prefix + "From");
2375 List<SouthboundTestCase<I, T>> updateToTestCases = generateKeyValueTestCases(builder, prefix + "To");
2377 for (SouthboundTestCase<I, T> updateFromTestCase : updateFromTestCases) {
2378 for (SouthboundTestCase<I, T> updateToTestCase : updateToTestCases) {
2379 String testQosId = String.format("%s_%s", prefix, updateToTestCase.name);
2381 // CREATE: and update the test qos with starting values.
2382 try (TestQos testQos = new TestQos(connectionInfo, new Uri(testQosId),
2383 SouthboundMapper.createQosType(SouthboundConstants.QOS_LINUX_HTB), null, null)) {
2384 QosEntriesBuilder qosBuilder = new QosEntriesBuilder();
2385 qosBuilder.setQosId(new Uri(testQosId));
2386 InstanceIdentifier<QosEntries> qosIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
2387 .augmentation(OvsdbNodeAugmentation.class)
2388 .child(QosEntries.class, qosBuilder.build().key());
2389 final NotifyingDataChangeListener qosConfigurationListener =
2390 new NotifyingDataChangeListener(LogicalDatastoreType.CONFIGURATION, qosIid);
2391 qosConfigurationListener.registerDataChangeListener();
2392 final NotifyingDataChangeListener qosOperationalListener =
2393 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, qosIid);
2394 qosOperationalListener.registerDataChangeListener();
2396 helper.writeValues(qosBuilder, updateFromTestCase.inputValues);
2397 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
2398 qosIid, qosBuilder.build()));
2399 qosConfigurationListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2401 // READ: Read the test queue and ensure changes are propagated to the CONFIGURATION data store,
2402 // then repeat for OPERATIONAL data store
2403 OvsdbNodeAugmentation updateFromConfigurationOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2404 LogicalDatastoreType.CONFIGURATION);
2405 QosEntries qosFromConfig = getQos(new Uri(testQosId), updateFromConfigurationOvsdbNodeAugmentation);
2406 if (qosFromConfig != null) {
2407 assertExpectedExist(updateFromTestCase.expectedValues, helper.readValues(qosFromConfig));
2410 qosOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2411 OvsdbNodeAugmentation updateFromOperationalOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2412 LogicalDatastoreType.OPERATIONAL);
2413 QosEntries qosFromOper = getQos(new Uri(testQosId), updateFromOperationalOvsdbNodeAugmentation);
2414 if (qosFromOper != null) {
2415 assertExpectedExist(updateFromTestCase.expectedValues, helper.readValues(qosFromOper));
2418 // UPDATE: update the values
2419 QosEntriesBuilder qosUpdateBuilder = new QosEntriesBuilder();
2420 qosUpdateBuilder.setQosId(new Uri(testQosId));
2421 helper.writeValues(qosUpdateBuilder, updateToTestCase.inputValues);
2422 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
2423 qosIid, qosUpdateBuilder.build()));
2424 qosConfigurationListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2426 // READ: the test queue and ensure changes are propagated to the CONFIGURATION data store,
2427 // then repeat for OPERATIONAL data store
2428 OvsdbNodeAugmentation updateToConfigurationOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2429 LogicalDatastoreType.CONFIGURATION);
2430 QosEntries qosToConfig = getQos(new Uri(testQosId), updateToConfigurationOvsdbNodeAugmentation);
2431 if (qosToConfig != null) {
2432 assertExpectedExist(updateToTestCase.expectedValues, helper.readValues(qosToConfig));
2435 qosOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2436 OvsdbNodeAugmentation updateToOperationalOvsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2437 LogicalDatastoreType.OPERATIONAL);
2438 QosEntries qosToOper = getQos(new Uri(testQosId), updateToOperationalOvsdbNodeAugmentation);
2439 if (qosToOper != null) {
2440 assertExpectedExist(updateToTestCase.expectedValues, helper.readValues(qosToOper));
2443 // DELETE handled by TestQueue
2450 public void testCRUDQosExternalIds() throws InterruptedException {
2451 testCRUDQos(new SouthboundQosExternalIdsBuilder(), "QosExternalIds",
2452 new SouthboundQosExternalIdsHelper());
2456 public void testCRUDQosOtherConfig() throws InterruptedException {
2457 testCRUDQos(new SouthboundQosOtherConfigBuilder(), "QosOtherConfig",
2458 new SouthboundQosOtherConfigHelper());
2462 public void testCRUDQosQueues() throws InterruptedException {
2463 ConnectionInfo connectionInfo = getConnectionInfo(addressStr, portNumber);
2464 String testQosId = "testQosQueues";
2466 // CREATE: and update the test queue with starting values.
2467 try (TestQos testQos = new TestQos(connectionInfo, new Uri(testQosId),
2468 SouthboundMapper.createQosType(SouthboundConstants.QOS_LINUX_HTB), null, null);
2469 TestQueue testQueue1 = new TestQueue(connectionInfo, new Uri("queue1"), Uint8.valueOf(12), null,
2471 TestQueue testQueue2 = new TestQueue(connectionInfo, new Uri("queue2"), Uint8.valueOf(35), null,
2473 QosEntriesBuilder qosBuilder = new QosEntriesBuilder();
2474 qosBuilder.setQosId(new Uri(testQosId));
2475 InstanceIdentifier<QosEntries> qosIid = SouthboundUtils.createInstanceIdentifier(connectionInfo)
2476 .augmentation(OvsdbNodeAugmentation.class)
2477 .child(QosEntries.class, qosBuilder.build().key());
2478 final NotifyingDataChangeListener qosOperationalListener =
2479 new NotifyingDataChangeListener(LogicalDatastoreType.OPERATIONAL, qosIid);
2480 qosOperationalListener.registerDataChangeListener();
2482 // READ, UPDATE: Read the UUIDs of the Queue rows and add them to the
2483 // configuration of the Qos row.
2484 OvsdbNodeAugmentation ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2485 LogicalDatastoreType.OPERATIONAL);
2487 Queues operQueue1 = getQueue(new Uri("queue1"), ovsdbNodeAugmentation);
2489 assertNotNull(operQueue1);
2491 InstanceIdentifier<Queues> queue1Iid = testQueue1.getInstanceIdentifier();
2492 OvsdbQueueRef queue1Ref = new OvsdbQueueRef(queue1Iid);
2494 Queues operQueue2 = getQueue(new Uri("queue2"), ovsdbNodeAugmentation);
2495 assertNotNull(operQueue2);
2496 InstanceIdentifier<Queues> queue2Iid = testQueue2.getInstanceIdentifier();
2497 OvsdbQueueRef queue2Ref = new OvsdbQueueRef(queue2Iid);
2499 Map<QueueListKey, QueueList> queueList = BindingMap.of(
2500 new QueueListBuilder().setQueueNumber(Uint32.ONE).setQueueRef(queue1Ref).build(),
2501 new QueueListBuilder().setQueueNumber(Uint32.TWO).setQueueRef(queue2Ref).build());
2503 qosBuilder.setQueueList(queueList);
2505 assertTrue(mdsalUtils.merge(LogicalDatastoreType.CONFIGURATION,
2506 qosIid, qosBuilder.build()));
2507 qosOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2509 // READ: Read the test qos and ensure changes are propagated to the OPERATIONAL data store
2510 // assumption is that CONFIGURATION was updated if OPERATIONAL is correct
2511 ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2512 LogicalDatastoreType.OPERATIONAL);
2513 QosEntries operQos = getQos(new Uri(testQosId), ovsdbNodeAugmentation);
2514 assertNotNull(operQos);
2515 Map<QueueListKey, QueueList> operQueueList = operQos.getQueueList();
2516 assertNotNull(operQueueList);
2517 for (QueueList queueEntry : queueList.values()) {
2518 assertTrue(isQueueInList(operQueueList, queueEntry));
2521 // DELETE one queue from queue list and check that one remains
2522 KeyedInstanceIdentifier<QueueList, QueueListKey> qosQueueIid = qosIid
2523 .child(QueueList.class, new QueueListKey(Uint32.ONE));
2524 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, qosQueueIid));
2525 qosOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2527 // READ: Read the test qos and ensure changes are propagated to the OPERATIONAL data store
2528 // assumption is that CONFIGURATION was updated if OPERATIONAL is correct
2529 ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2530 LogicalDatastoreType.OPERATIONAL);
2531 operQos = getQos(new Uri(testQosId), ovsdbNodeAugmentation);
2532 assertNotNull(operQos);
2533 operQueueList = operQos.getQueueList();
2534 assertNotNull(operQueueList);
2536 for (QueueList queueEntry : queueList.values()) {
2537 if (queueEntry.getQueueRef().equals(queue2Ref)) {
2538 assertTrue(isQueueInList(operQueueList, queueEntry));
2539 } else if (queueEntry.getQueueRef().equals(queue1Ref)) {
2540 assertFalse(isQueueInList(operQueueList, queueEntry));
2542 assertTrue("Unknown queue entry in qos queue list", false);
2546 // DELETE queue list and check that list is empty
2547 qosQueueIid = qosIid
2548 .child(QueueList.class, new QueueListKey(Uint32.ONE));
2549 assertTrue(mdsalUtils.delete(LogicalDatastoreType.CONFIGURATION, qosQueueIid));
2550 qosOperationalListener.waitForUpdate(OVSDB_UPDATE_TIMEOUT);
2552 ovsdbNodeAugmentation = getOvsdbNode(connectionInfo,
2553 LogicalDatastoreType.OPERATIONAL);
2554 operQos = getQos(new Uri(testQosId), ovsdbNodeAugmentation);
2555 assertNotNull(operQos);
2556 operQueueList = operQos.getQueueList();
2557 assertNotNull(operQueueList);
2558 assertTrue(operQueueList.isEmpty());
2564 private static Boolean isQueueInList(final Map<QueueListKey, QueueList> queueList, final QueueList queue) {
2565 for (QueueList queueEntry : queueList.values()) {
2566 if (queueEntry.getQueueNumber().equals(queue.getQueueNumber())
2567 && queueEntry.getQueueRef().equals(queue.getQueueRef())) {
2576 * Representation of a southbound test case. Each test case has a name, a list of input values and a list of
2577 * expected values. The input values are provided to the augmentation builder, and the expected values are checked
2578 * against the output of the resulting augmentation.
2581 * Instances of this class are immutable.
2584 * @param <T> The type of data used for the test case.
2586 private static final class SouthboundTestCase<I extends Identifier<T>, T extends Identifiable<I>> {
2587 private final String name;
2588 private final Map<I, T> inputValues;
2589 private final Map<I, T> expectedValues;
2592 * Creates an instance of a southbound test case.
2594 * @param name The test case's name.
2595 * @param inputValues The input values (provided as input to the underlying augmentation builder).
2596 * @param expectedValues The expected values (checked against the output of the underlying augmentation).
2598 SouthboundTestCase(final String name, final List<T> inputValues, final List<T> expectedValues) {
2600 this.inputValues = BindingMap.ordered(inputValues);
2601 this.expectedValues = BindingMap.of(expectedValues);
2606 * Southbound test case builder.
2608 * @param <T> The type of data used for the test case.
2610 private static final class SouthboundTestCaseBuilder<I extends Identifier<T>, T extends Identifiable<I>> {
2611 private String name;
2612 private List<T> inputValues;
2613 private List<T> expectedValues;
2616 * Creates a builder. Builders may be reused, the generated immutable instances are independent of the
2617 * builders. There are no default values.
2619 SouthboundTestCaseBuilder() {
2624 * Sets the test case's name.
2626 * @param value The test case's name.
2627 * @return The builder.
2629 public SouthboundTestCaseBuilder<I, T> name(final String value) {
2635 * Sets the input values.
2637 * @param values The input values.
2638 * @return The builder.
2641 public final SouthboundTestCaseBuilder<I, T> input(final T... values) {
2642 this.inputValues = Lists.newArrayList(values);
2647 * Indicates that the provided input values should be expected as output values.
2649 * @return The builder.
2651 public SouthboundTestCaseBuilder<I, T> expectInputAsOutput() {
2652 this.expectedValues = this.inputValues;
2657 * Indicates that no output should be expected.
2659 * @return The builder.
2661 public SouthboundTestCaseBuilder<I, T> expectNoOutput() {
2662 this.expectedValues = null;
2667 * Builds an immutable instance representing the test case.
2669 * @return The test case.
2671 public SouthboundTestCase<I, T> build() {
2672 return new SouthboundTestCase<>(name, inputValues, expectedValues);
2676 private abstract static class KeyValueBuilder<T> {
2677 private static final int COUNTER_START = 0;
2678 private int counter = COUNTER_START;
2680 protected abstract boolean isValueMandatory();
2682 public final T build(final String testName, final String key, final String value) {
2684 return build(key == null ? null : String.format(FORMAT_STR, testName, key, counter),
2685 value != null ? null : String.format(FORMAT_STR, testName, value, counter));
2688 abstract @NonNull T build(@Nullable String key, @Nullable String value);
2690 public final void reset() {
2691 counter = COUNTER_START;
2695 private static final class SouthboundQueuesExternalIdsBuilder extends KeyValueBuilder<QueuesExternalIds> {
2697 QueuesExternalIds build(final String key, final String value) {
2698 return new QueuesExternalIdsBuilder()
2699 .setQueuesExternalIdKey(key)
2700 .setQueuesExternalIdValue(value)
2705 protected boolean isValueMandatory() {
2710 private static final class SouthboundQueuesOtherConfigBuilder extends KeyValueBuilder<QueuesOtherConfig> {
2712 QueuesOtherConfig build(final String key, final String value) {
2713 return new QueuesOtherConfigBuilder()
2714 .setQueueOtherConfigKey(key)
2715 .setQueueOtherConfigValue(value)
2720 protected boolean isValueMandatory() {
2725 private static final class SouthboundQosExternalIdsBuilder extends KeyValueBuilder<QosExternalIds> {
2727 QosExternalIds build(final String key, final String value) {
2728 return new QosExternalIdsBuilder()
2729 .setQosExternalIdKey(key)
2730 .setQosExternalIdValue(value)
2735 protected boolean isValueMandatory() {
2740 private static final class SouthboundQosOtherConfigBuilder extends KeyValueBuilder<QosOtherConfig> {
2742 QosOtherConfig build(final String key, final String value) {
2743 return new QosOtherConfigBuilder()
2744 .setOtherConfigKey(key)
2745 .setOtherConfigValue(value)
2750 protected boolean isValueMandatory() {
2755 private static final class SouthboundPortExternalIdsBuilder extends KeyValueBuilder<PortExternalIds> {
2757 PortExternalIds build(final String key, final String value) {
2758 return new PortExternalIdsBuilder()
2759 .setExternalIdKey(key)
2760 .setExternalIdValue(value)
2765 protected boolean isValueMandatory() {
2770 private static final class SouthboundInterfaceExternalIdsBuilder extends KeyValueBuilder<InterfaceExternalIds> {
2772 InterfaceExternalIds build(final String key, final String value) {
2773 return new InterfaceExternalIdsBuilder()
2774 .setExternalIdKey(key)
2775 .setExternalIdValue(value)
2780 protected boolean isValueMandatory() {
2785 private static final class SouthboundInterfaceLldpBuilder extends KeyValueBuilder<InterfaceLldp> {
2787 InterfaceLldp build(final String key, final String value) {
2788 return new InterfaceLldpBuilder()
2790 .setLldpValue(value)
2795 protected boolean isValueMandatory() {
2800 private static final class SouthboundOptionsBuilder extends KeyValueBuilder<Options> {
2802 Options build(final String key, final String value) {
2803 return new OptionsBuilder()
2810 protected boolean isValueMandatory() {
2815 private static final class SouthboundInterfaceOtherConfigsBuilder extends KeyValueBuilder<InterfaceOtherConfigs> {
2817 InterfaceOtherConfigs build(final String key, final String value) {
2818 return new InterfaceOtherConfigsBuilder()
2819 .setOtherConfigKey(key)
2820 .setOtherConfigValue(value)
2825 protected boolean isValueMandatory() {
2830 private static final class SouthboundPortOtherConfigsBuilder extends KeyValueBuilder<PortOtherConfigs> {
2832 PortOtherConfigs build(final String key, final String value) {
2833 return new PortOtherConfigsBuilder()
2834 .setOtherConfigKey(key)
2835 .setOtherConfigValue(value)
2840 protected boolean isValueMandatory() {
2845 private static final class SouthboundBridgeOtherConfigsBuilder extends KeyValueBuilder<BridgeOtherConfigs> {
2847 BridgeOtherConfigs build(final String key, final String value) {
2848 return new BridgeOtherConfigsBuilder()
2849 .setBridgeOtherConfigKey(key)
2850 .setBridgeOtherConfigValue(value)
2855 protected boolean isValueMandatory() {
2860 private static final class SouthboundBridgeExternalIdsBuilder extends KeyValueBuilder<BridgeExternalIds> {
2862 BridgeExternalIds build(final String key, final String value) {
2863 return new BridgeExternalIdsBuilder()
2864 .setBridgeExternalIdKey(key)
2865 .setBridgeExternalIdValue(value)
2870 protected boolean isValueMandatory() {
2876 * Generates the test cases involved in testing key-value-based data. See inline comments for descriptions of
2877 * the particular cases considered.
2879 private static <I extends Identifier<T>, T extends Identifiable<I>> List<SouthboundTestCase<I, T>>
2880 generateKeyValueTestCases(final KeyValueBuilder<T> builder, final String testName) {
2881 List<SouthboundTestCase<I, T>> testCases = new ArrayList<>();
2883 final String goodKey = "GoodKey";
2884 final String goodValue = "GoodValue";
2885 final String noValueForKey = "NoValueForKey";
2887 final String idKey = testName + "Key";
2888 final String idValue = testName + "Value";
2890 // Test Case 1: TestOne
2891 // Test Type: Positive
2892 // Description: Create a termination point with one value
2893 // Expected: A port is created with the single value specified below
2894 final String testOneName = "TestOne" + testName;
2895 testCases.add(new SouthboundTestCaseBuilder<I, T>()
2897 .input(builder.build(testOneName, idKey, idValue))
2898 .expectInputAsOutput()
2902 // Test Case 2: TestFive
2903 // Test Type: Positive
2904 // Description: Create a termination point with multiple (five) values
2905 // Expected: A port is created with the five values specified below
2906 final String testFiveName = "TestFive" + testName;
2907 testCases.add(new SouthboundTestCaseBuilder<I, T>()
2910 builder.build(testFiveName, idKey, idValue),
2911 builder.build(testFiveName, idKey, idValue),
2912 builder.build(testFiveName, idKey, idValue),
2913 builder.build(testFiveName, idKey, idValue),
2914 builder.build(testFiveName, idKey, idValue))
2915 .expectInputAsOutput()
2919 if (!builder.isValueMandatory()) {
2920 // Test Case 3: TestOneGoodOneMalformedValue
2921 // Test Type: Negative
2923 // One perfectly fine input
2924 // (TestOneGoodOneMalformedValue_GoodKey_1,
2925 // TestOneGoodOneMalformedValue_GoodValue_1)
2926 // and one malformed input which only has key specified
2927 // (TestOneGoodOneMalformedValue_NoValueForKey_2,
2929 // Expected: A port is created without any values
2930 final String testOneGoodOneMalformedValueName = "TestOneGoodOneMalformedValue" + testName;
2931 testCases.add(new SouthboundTestCaseBuilder<I, T>()
2932 .name(testOneGoodOneMalformedValueName)
2934 builder.build(testOneGoodOneMalformedValueName, goodKey, goodValue),
2935 builder.build(testOneGoodOneMalformedValueName, noValueForKey, null))
2940 LOG.info("generateKeyValueTestCases: skipping test case 3 for {}", builder.getClass().getSimpleName());
2946 private static class PortExternalIdsSouthboundHelper
2947 implements SouthboundTerminationPointHelper<PortExternalIdsKey, PortExternalIds> {
2949 public void writeValues(final OvsdbTerminationPointAugmentationBuilder builder,
2950 final Map<PortExternalIdsKey, PortExternalIds> values) {
2951 builder.setPortExternalIds(values);
2955 public Map<PortExternalIdsKey, PortExternalIds> readValues(
2956 final OvsdbTerminationPointAugmentation augmentation) {
2957 return augmentation.getPortExternalIds();
2961 private static class InterfaceExternalIdsSouthboundHelper
2962 implements SouthboundTerminationPointHelper<InterfaceExternalIdsKey, InterfaceExternalIds> {
2964 public void writeValues(final OvsdbTerminationPointAugmentationBuilder builder,
2965 final Map<InterfaceExternalIdsKey, InterfaceExternalIds> values) {
2966 builder.setInterfaceExternalIds(values);
2970 public Map<InterfaceExternalIdsKey, InterfaceExternalIds> readValues(
2971 final OvsdbTerminationPointAugmentation augmentation) {
2972 return augmentation.getInterfaceExternalIds();
2976 private static class InterfaceLldpSouthboundHelper
2977 implements SouthboundTerminationPointHelper<InterfaceLldpKey, InterfaceLldp> {
2979 public void writeValues(final OvsdbTerminationPointAugmentationBuilder builder,
2980 final Map<InterfaceLldpKey, InterfaceLldp> values) {
2981 builder.setInterfaceLldp(values);
2985 public Map<InterfaceLldpKey, InterfaceLldp> readValues(final OvsdbTerminationPointAugmentation augmentation) {
2986 return augmentation.getInterfaceLldp();
2990 private static class OptionsSouthboundHelper implements SouthboundTerminationPointHelper<OptionsKey, Options> {
2992 public void writeValues(final OvsdbTerminationPointAugmentationBuilder builder,
2993 final Map<OptionsKey, Options> values) {
2994 builder.setOptions(values);
2998 public Map<OptionsKey, Options> readValues(final OvsdbTerminationPointAugmentation augmentation) {
2999 return augmentation.getOptions();
3003 private static class InterfaceOtherConfigsSouthboundHelper
3004 implements SouthboundTerminationPointHelper<InterfaceOtherConfigsKey, InterfaceOtherConfigs> {
3006 public void writeValues(final OvsdbTerminationPointAugmentationBuilder builder,
3007 final Map<InterfaceOtherConfigsKey, InterfaceOtherConfigs> values) {
3008 builder.setInterfaceOtherConfigs(values);
3012 public Map<InterfaceOtherConfigsKey, InterfaceOtherConfigs> readValues(
3013 final OvsdbTerminationPointAugmentation augmentation) {
3014 return augmentation.getInterfaceOtherConfigs();
3018 private static class PortOtherConfigsSouthboundHelper implements
3019 SouthboundTerminationPointHelper<PortOtherConfigsKey, PortOtherConfigs> {
3021 public void writeValues(final OvsdbTerminationPointAugmentationBuilder builder,
3022 final Map<PortOtherConfigsKey, PortOtherConfigs> values) {
3023 builder.setPortOtherConfigs(values);
3027 public Map<PortOtherConfigsKey, PortOtherConfigs> readValues(
3028 final OvsdbTerminationPointAugmentation augmentation) {
3029 return augmentation.getPortOtherConfigs();
3033 private static class BridgeExternalIdsSouthboundHelper
3034 implements SouthboundBridgeHelper<BridgeExternalIdsKey, BridgeExternalIds> {
3036 public void writeValues(final OvsdbBridgeAugmentationBuilder builder,
3037 final Map<BridgeExternalIdsKey, BridgeExternalIds> values) {
3038 builder.setBridgeExternalIds(values);
3042 public Map<BridgeExternalIdsKey, BridgeExternalIds> readValues(final OvsdbBridgeAugmentation augmentation) {
3043 return augmentation.getBridgeExternalIds();
3047 private static class BridgeOtherConfigsSouthboundHelper
3048 implements SouthboundBridgeHelper<BridgeOtherConfigsKey, BridgeOtherConfigs> {
3050 public void writeValues(final OvsdbBridgeAugmentationBuilder builder,
3051 final Map<BridgeOtherConfigsKey, BridgeOtherConfigs> values) {
3052 builder.setBridgeOtherConfigs(values);
3056 public Map<BridgeOtherConfigsKey, BridgeOtherConfigs> readValues(final OvsdbBridgeAugmentation augmentation) {
3057 return augmentation.getBridgeOtherConfigs();