[ONOS-5682] Introduced VIRTUAL_PORT_* events for virtual network to virtual port mapping changes.
Change-Id: Ic1d39643b35601aa12c7e703a73cf9258bd04aa2
diff --git a/incubator/api/src/main/java/org/onosproject/incubator/net/virtual/VirtualNetworkEvent.java b/incubator/api/src/main/java/org/onosproject/incubator/net/virtual/VirtualNetworkEvent.java
index 7fde1e3..7234b70 100644
--- a/incubator/api/src/main/java/org/onosproject/incubator/net/virtual/VirtualNetworkEvent.java
+++ b/incubator/api/src/main/java/org/onosproject/incubator/net/virtual/VirtualNetworkEvent.java
@@ -57,10 +57,23 @@
/**
* Signifies that a virtual network device was removed.
*/
- VIRTUAL_DEVICE_REMOVED
+ VIRTUAL_DEVICE_REMOVED,
+ /**
+ * Signifies that a new virtual network port was added.
+ */
+ VIRTUAL_PORT_ADDED,
+ /**
+ * Signifies that a virtual network port was updated.
+ */
+ VIRTUAL_PORT_UPDATED,
+ /**
+ * Signifies that a virtual network port was removed.
+ */
+ VIRTUAL_PORT_REMOVED
}
private final VirtualDevice virtualDevice;
+ private final VirtualPort virtualPort;
/**
* Creates an event of a given type and for the specified subject.
@@ -69,7 +82,7 @@
* @param subject event subject
*/
public VirtualNetworkEvent(Type type, NetworkId subject) {
- this(type, subject, null);
+ this(type, subject, null, null);
}
/**
@@ -81,41 +94,108 @@
* @param virtualDevice virtual device
*/
public VirtualNetworkEvent(Type type, NetworkId subject, VirtualDevice virtualDevice) {
+ this(type, subject, virtualDevice, null);
+ }
+
+ /**
+ * Creates an event of a given type and for the specified subject and the
+ * virtual port.
+ *
+ * @param type event type
+ * @param subject event subject
+ * @param virtualPort virtual port
+ */
+ public VirtualNetworkEvent(Type type, NetworkId subject, VirtualPort virtualPort) {
+ this(type, subject, null, virtualPort);
+ }
+
+ /**
+ * Creates an event of a given type and for the specified subject, virtual device and
+ * virtual port.
+ *
+ * @param type event type
+ * @param subject event subject
+ * @param virtualDevice virtual device
+ * @param virtualPort virtual port
+ */
+ private VirtualNetworkEvent(Type type, NetworkId subject, VirtualDevice virtualDevice,
+ VirtualPort virtualPort) {
super(type, subject);
this.virtualDevice = virtualDevice;
+ this.virtualPort = virtualPort;
}
/**
* Creates an event of a given type and for the specified subject and time.
*
- * @param type device event type
+ * @param type event type
* @param subject event subject
* @param time occurrence time
*/
public VirtualNetworkEvent(Type type, NetworkId subject, long time) {
- this(type, subject, null, time);
+ this(type, subject, null, null, time);
}
/**
* Creates an event of a given type and for the specified subject, virtual device and time.
*
- * @param type device event type
+ * @param type event type
* @param subject event subject
* @param virtualDevice virtual device
* @param time occurrence time
*/
- public VirtualNetworkEvent(Type type, NetworkId subject, VirtualDevice virtualDevice, long time) {
+ public VirtualNetworkEvent(Type type, NetworkId subject, VirtualDevice virtualDevice,
+ long time) {
+ this(type, subject, virtualDevice, null, time);
+ }
+
+ /**
+ * Creates an event of a given type and for the specified subject, virtual port and time.
+ *
+ * @param type device event type
+ * @param subject event subject
+ * @param virtualPort virtual port
+ * @param time occurrence time
+ */
+ public VirtualNetworkEvent(Type type, NetworkId subject, VirtualPort virtualPort,
+ long time) {
+ this(type, subject, null, virtualPort, time);
+ }
+
+ /**
+ * Creates an event of a given type and for the specified subject, virtual device,
+ * virtual port and time.
+ *
+ * @param type device event type
+ * @param subject event subject
+ * @param virtualDevice virtual device
+ * @param virtualPort virtual port
+ * @param time occurrence time
+ */
+ private VirtualNetworkEvent(Type type, NetworkId subject, VirtualDevice virtualDevice,
+ VirtualPort virtualPort, long time) {
super(type, subject, time);
this.virtualDevice = virtualDevice;
+ this.virtualPort = virtualPort;
}
/**
* Returns virtual device affected by event - may be null (for events relating to
- * tenants and virtual networks).
+ * tenants, virtual networks and virtual ports).
*
* @return virtual device
*/
public VirtualDevice virtualDevice() {
return virtualDevice;
}
+
+ /**
+ * Returns virtual port affected by event - may be null (for events relating to
+ * tenants, virtual networks and virtual devices).
+ *
+ * @return virtual port
+ */
+ public VirtualPort virtualPort() {
+ return virtualPort;
+ }
}
diff --git a/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkManagerTest.java b/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkManagerTest.java
index 3a580eb..b9f259b 100644
--- a/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkManagerTest.java
+++ b/incubator/net/src/test/java/org/onosproject/incubator/net/virtual/impl/VirtualNetworkManagerTest.java
@@ -400,21 +400,28 @@
}
/**
- * Tests add and remove of virtual ports.
+ * Tests add, bind and remove of virtual ports.
*/
@Test
public void testAddRemoveVirtualPort() {
+ List<VirtualNetworkEvent.Type> expectedEventTypes = new ArrayList<>();
+
manager.registerTenantId(TenantId.tenantId(tenantIdValue1));
+ expectedEventTypes.add(VirtualNetworkEvent.Type.TENANT_REGISTERED);
VirtualNetwork virtualNetwork1 =
manager.createVirtualNetwork(TenantId.tenantId(tenantIdValue1));
+ expectedEventTypes.add(VirtualNetworkEvent.Type.NETWORK_ADDED);
VirtualDevice virtualDevice =
manager.createVirtualDevice(virtualNetwork1.id(), DID1);
+ expectedEventTypes.add(VirtualNetworkEvent.Type.VIRTUAL_DEVICE_ADDED);
ConnectPoint cp = new ConnectPoint(virtualDevice.id(), PortNumber.portNumber(1));
manager.createVirtualPort(virtualNetwork1.id(),
virtualDevice.id(), PortNumber.portNumber(1), cp);
+ expectedEventTypes.add(VirtualNetworkEvent.Type.VIRTUAL_PORT_ADDED);
manager.createVirtualPort(virtualNetwork1.id(),
virtualDevice.id(), PortNumber.portNumber(2), cp);
+ expectedEventTypes.add(VirtualNetworkEvent.Type.VIRTUAL_PORT_ADDED);
Set<VirtualPort> virtualPorts = manager.getVirtualPorts(virtualNetwork1.id(), virtualDevice.id());
assertNotNull("The virtual port set should not be null", virtualPorts);
@@ -423,6 +430,7 @@
for (VirtualPort virtualPort : virtualPorts) {
manager.removeVirtualPort(virtualNetwork1.id(),
(DeviceId) virtualPort.element().id(), virtualPort.number());
+ expectedEventTypes.add(VirtualNetworkEvent.Type.VIRTUAL_PORT_REMOVED);
// attempt to remove the same virtual port again.
manager.removeVirtualPort(virtualNetwork1.id(),
(DeviceId) virtualPort.element().id(), virtualPort.number());
@@ -434,10 +442,22 @@
VirtualPort virtualPort =
manager.createVirtualPort(virtualNetwork1.id(), virtualDevice.id(),
PortNumber.portNumber(1), cp);
+ expectedEventTypes.add(VirtualNetworkEvent.Type.VIRTUAL_PORT_ADDED);
+
+ ConnectPoint newCp = new ConnectPoint(DID2, PortNumber.portNumber(2));
+ manager.bindVirtualPort(virtualNetwork1.id(), virtualDevice.id(),
+ PortNumber.portNumber(1), newCp);
+ expectedEventTypes.add(VirtualNetworkEvent.Type.VIRTUAL_PORT_UPDATED);
+
manager.removeVirtualPort(virtualNetwork1.id(),
(DeviceId) virtualPort.element().id(), virtualPort.number());
+ expectedEventTypes.add(VirtualNetworkEvent.Type.VIRTUAL_PORT_REMOVED);
virtualPorts = manager.getVirtualPorts(virtualNetwork1.id(), virtualDevice.id());
assertTrue("The virtual port set should be empty.", virtualPorts.isEmpty());
+
+ // Validate that the events were all received in the correct order.
+ validateEvents((Enum[]) expectedEventTypes.toArray(
+ new VirtualNetworkEvent.Type[expectedEventTypes.size()]));
}
/**
diff --git a/incubator/store/src/main/java/org/onosproject/incubator/store/virtual/impl/DistributedVirtualNetworkStore.java b/incubator/store/src/main/java/org/onosproject/incubator/store/virtual/impl/DistributedVirtualNetworkStore.java
index 967504c..17d8dcb 100644
--- a/incubator/store/src/main/java/org/onosproject/incubator/store/virtual/impl/DistributedVirtualNetworkStore.java
+++ b/incubator/store/src/main/java/org/onosproject/incubator/store/virtual/impl/DistributedVirtualNetworkStore.java
@@ -74,6 +74,7 @@
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
+import java.util.concurrent.atomic.AtomicBoolean;
import java.util.function.BiFunction;
import static com.google.common.base.Preconditions.checkNotNull;
@@ -558,6 +559,8 @@
portNumber, realizedBy);
virtualPortSet.add(virtualPort);
networkIdVirtualPortSetMap.put(networkId, virtualPortSet);
+ notifyDelegate(new VirtualNetworkEvent(VirtualNetworkEvent.Type.VIRTUAL_PORT_ADDED,
+ networkId, virtualPort));
return virtualPort;
}
@@ -581,6 +584,8 @@
vPort = new DefaultVirtualPort(networkId, device, portNumber, realizedBy);
virtualPortSet.add(vPort);
networkIdVirtualPortSetMap.put(networkId, virtualPortSet);
+ notifyDelegate(new VirtualNetworkEvent(VirtualNetworkEvent.Type.VIRTUAL_PORT_UPDATED,
+ networkId, vPort));
}
@Override
@@ -594,14 +599,22 @@
}
});
- if (virtualPortSet != null) {
+ if (!virtualPortSet.isEmpty()) {
+ AtomicBoolean portRemoved = new AtomicBoolean(false);
networkIdVirtualPortSetMap.compute(networkId, (id, existingVirtualPorts) -> {
if (existingVirtualPorts == null || existingVirtualPorts.isEmpty()) {
return new HashSet<>();
} else {
+ portRemoved.set(true);
return new HashSet<>(Sets.difference(existingVirtualPorts, virtualPortSet));
}
});
+ if (portRemoved.get()) {
+ virtualPortSet.forEach(virtualPort -> notifyDelegate(
+ new VirtualNetworkEvent(VirtualNetworkEvent.Type.VIRTUAL_PORT_REMOVED,
+ networkId, virtualPort)
+ ));
+ }
}
}