]> review.fuel-infra Code Review - openstack-build/neutron-build.git/commitdiff
blueprint operational-status-ovs-plugin
authorDan Wendlandt <dan@nicira.com>
Tue, 13 Dec 2011 20:54:02 +0000 (12:54 -0800)
committerDan Wendlandt <dan@nicira.com>
Tue, 13 Dec 2011 20:55:01 +0000 (12:55 -0800)
Implements operational status API for OVS plugin.   Uses existing
database model for operational status.  For network, status is always
up.  For a port, status is down unless there is an agent that
indicates that the port is active on its compute host.

Updated: use Salvatore's config hook to set default op-status for OVS
in OVS run_tests.py

Updated: fixed issue in _make_port_dict() found by Brad.

Change-Id: I0560cbde9dc69bd4211d9aaf12cef204df2f7664

quantum/plugins/openvswitch/agent/ovs_quantum_agent.py
quantum/plugins/openvswitch/ovs_quantum_plugin.py
quantum/plugins/openvswitch/run_tests.py

index de39ad9bda8eeef3c701058ec0e77996f42ad740..6609a687486eb33199dd9e20ddfad028f8d8ea69 100755 (executable)
@@ -25,9 +25,12 @@ import time
 import signal
 
 from optparse import OptionParser
+from sqlalchemy.ext.sqlsoup import SqlSoup
 from subprocess import *
 
-from sqlalchemy.ext.sqlsoup import SqlSoup
+
+OP_STATUS_UP = "UP"
+OP_STATUS_DOWN = "DOWN"
 
 
 # A class to represent a VIF (i.e., a port that has 'iface-id' and 'vif-mac'
@@ -199,7 +202,7 @@ class OVSQuantumAgent:
             except:
                 ports = []
             for port in ports:
-                all_bindings[port.interface_id] = port.network_id
+                all_bindings[port.interface_id] = port
 
             vlan_bindings = {}
             try:
@@ -215,7 +218,8 @@ class OVSQuantumAgent:
             for p in vif_ports:
                 new_vif_ports[p.vif_id] = p
                 if p.vif_id in all_bindings:
-                    new_local_bindings[p.vif_id] = all_bindings[p.vif_id]
+                    net_id = all_bindings[p.vif_id].network_id
+                    new_local_bindings[p.vif_id] = net_id
                 else:
                     # no binding, put him on the 'dead vlan'
                     self.int_br.set_db_attribute("Port", p.port_name, "tag",
@@ -231,23 +235,31 @@ class OVSQuantumAgent:
                         LOG.info("Removing binding to net-id = %s for %s"
                           % (old_b, str(p)))
                         self.port_unbound(p, True)
+                        if p.vif_id in all_bindings:
+                            all_bindings[p.vif_id].op_status = OP_STATUS_DOWN
                     if new_b is not None:
                         # If we don't have a binding we have to stick it on
                         # the dead vlan
-                        vlan_id = vlan_bindings.get(all_bindings[p.vif_id],
-                          "4095")
+                        net_id = all_bindings[p.vif_id].network_id
+                        vlan_id = vlan_bindings.get(net_id, "4095")
                         self.port_bound(p, vlan_id)
+                        if p.vif_id in all_bindings:
+                            all_bindings[p.vif_id].op_status = OP_STATUS_UP
                         LOG.info("Adding binding to net-id = %s " \
                              "for %s on vlan %s" % (new_b, str(p), vlan_id))
+
             for vif_id in old_vif_ports.keys():
                 if vif_id not in new_vif_ports:
                     LOG.info("Port Disappeared: %s" % vif_id)
                     if vif_id in old_local_bindings:
                         old_b = old_local_bindings[vif_id]
                         self.port_unbound(old_vif_ports[vif_id], False)
+                    if vif_id in all_bindings:
+                        all_bindings[vif_id].op_status = OP_STATUS_DOWN
 
             old_vif_ports = new_vif_ports
             old_local_bindings = new_local_bindings
+            db.commit()
             time.sleep(2)
 
 if __name__ == "__main__":
index 3b882e5f95647672b86a1e2011c1bdb6c9b4ee74..d87b17a726b885a65e96f8546721f32d41d19502 100644 (file)
@@ -23,6 +23,7 @@ from optparse import OptionParser
 import os
 import sys
 
+from quantum.api.api_common import OperationalStatus
 from quantum.common import exceptions as q_exc
 from quantum.common.config import find_config_file
 from quantum.quantum_plugin_base import QuantumPluginBase
@@ -102,22 +103,26 @@ class OVSQuantumPlugin(QuantumPluginBase):
         nets = []
         for x in db.network_list(tenant_id):
             LOG.debug("Adding network: %s" % x.uuid)
-            nets.append(self._make_net_dict(str(x.uuid), x.name, None))
+            nets.append(self._make_net_dict(str(x.uuid), x.name,
+                                            None, x.op_status))
         return nets
 
-    def _make_net_dict(self, net_id, net_name, ports):
+    def _make_net_dict(self, net_id, net_name, ports, op_status):
         res = {'net-id': net_id,
-                'net-name': net_name}
+                'net-name': net_name,
+                'net-op-status': op_status}
         if ports:
             res['net-ports'] = ports
         return res
 
     def create_network(self, tenant_id, net_name, **kwargs):
-        net = db.network_create(tenant_id, net_name)
+        net = db.network_create(tenant_id, net_name,
+                          op_status=OperationalStatus.UP)
         LOG.debug("Created network: %s" % net)
         vlan_id = self.vmap.acquire(str(net.uuid))
         ovs_db.add_vlan_binding(vlan_id, str(net.uuid))
-        return self._make_net_dict(str(net.uuid), net.name, [])
+        return self._make_net_dict(str(net.uuid), net.name, [],
+                                        net.op_status)
 
     def delete_network(self, tenant_id, net_id):
         net = db.network_get(net_id)
@@ -129,43 +134,46 @@ class OVSQuantumPlugin(QuantumPluginBase):
         net = db.network_destroy(net_id)
         ovs_db.remove_vlan_binding(net_id)
         self.vmap.release(net_id)
-        return self._make_net_dict(str(net.uuid), net.name, [])
+        return self._make_net_dict(str(net.uuid), net.name, [],
+                                        net.op_status)
 
     def get_network_details(self, tenant_id, net_id):
         net = db.network_get(net_id)
         ports = self.get_all_ports(tenant_id, net_id)
-        return self._make_net_dict(str(net.uuid), net.name, ports)
+        return self._make_net_dict(str(net.uuid), net.name,
+                                    ports, net.op_status)
 
     def update_network(self, tenant_id, net_id, **kwargs):
         net = db.network_update(net_id, tenant_id, **kwargs)
-        return self._make_net_dict(str(net.uuid), net.name, None)
+        return self._make_net_dict(str(net.uuid), net.name,
+                                        None, net.op_status)
 
-    def _make_port_dict(self, port_id, port_state, net_id, attachment):
-        return {'port-id': port_id,
-                'port-state': port_state,
-                'net-id': net_id,
-                'attachment': attachment}
+    def _make_port_dict(self, port):
+        if port.state == "ACTIVE":
+            op_status = port.op_status
+        else:
+            op_status = OperationalStatus.DOWN
+
+        return {'port-id': str(port.uuid),
+                'port-state': port.state,
+                'port-op-status': op_status,
+                'net-id': port.network_id,
+                'attachment': port.interface_id}
 
     def get_all_ports(self, tenant_id, net_id):
         ids = []
         ports = db.port_list(net_id)
-        for p in ports:
-            LOG.debug("Appending port: %s" % p.uuid)
-            d = self._make_port_dict(str(p.uuid), p.state, p.network_id,
-                                                    p.interface_id)
-            ids.append(d)
-        return ids
+        return [{'port-id': str(p.uuid)} for p in ports]
 
     def create_port(self, tenant_id, net_id, port_state=None, **kwargs):
         LOG.debug("Creating port with network_id: %s" % net_id)
-        port = db.port_create(net_id, port_state)
-        return self._make_port_dict(str(port.uuid), port.state,
-                                        port.network_id, port.interface_id)
+        port = db.port_create(net_id, port_state,
+                                op_status=OperationalStatus.DOWN)
+        return self._make_port_dict(port)
 
     def delete_port(self, tenant_id, net_id, port_id):
         port = db.port_destroy(port_id, net_id)
-        return self._make_port_dict(str(port.uuid), port.state,
-                                        port.network_id, port.interface_id)
+        return self._make_port_dict(port)
 
     def update_port(self, tenant_id, net_id, port_id, **kwargs):
         """
@@ -174,19 +182,18 @@ class OVSQuantumPlugin(QuantumPluginBase):
         LOG.debug("update_port() called\n")
         port = db.port_get(port_id, net_id)
         db.port_update(port_id, net_id, **kwargs)
-        return self._make_port_dict(str(port.uuid), port.state,
-                                        port.network_id, port.interface_id)
+        return self._make_port_dict(port)
 
     def get_port_details(self, tenant_id, net_id, port_id):
         port = db.port_get(port_id, net_id)
-        return self._make_port_dict(str(port.uuid), port.state,
-                                port.network_id, port.interface_id)
+        return self._make_port_dict(port)
 
     def plug_interface(self, tenant_id, net_id, port_id, remote_iface_id):
         db.port_set_attachment(port_id, net_id, remote_iface_id)
 
     def unplug_interface(self, tenant_id, net_id, port_id):
         db.port_set_attachment(port_id, net_id, "")
+        db.port_update(port_id, net_id, op_status=OperationalStatus.DOWN)
 
     def get_interface_details(self, tenant_id, net_id, port_id):
         res = db.port_get(port_id, net_id)
index 9649efa0d8723db19aa31982f1a258d7854eac03..b01ba765d6fcd531c3822f8983e297cc4cc0e6d3 100644 (file)
@@ -37,9 +37,10 @@ from nose import core
 sys.path.append(os.getcwd())
 sys.path.append(os.path.dirname(__file__))
 
-import quantum.tests.unit
 
+from quantum.api.api_common import OperationalStatus
 from quantum.common.test_lib import run_tests, test_config
+import quantum.tests.unit
 from tests.unit.test_vlan_map import VlanMapTest
 
 if __name__ == '__main__':
@@ -49,12 +50,9 @@ if __name__ == '__main__':
     # we should only invoked the tests once
     invoke_once = len(sys.argv) > 1
 
-    # NOTE (salvatore-orlando):
-    # please update default values for operational status according to
-    # the plugin behavior.
     test_config['plugin_name'] = "ovs_quantum_plugin.OVSQuantumPlugin"
-    test_config['default_net_op_status'] = "UNKNOWN"
-    test_config['default_port_op_status'] = "UNKNOWN"
+    test_config['default_net_op_status'] = OperationalStatus.UP
+    test_config['default_port_op_status'] = OperationalStatus.DOWN
 
     cwd = os.getcwd()
     c = config.Config(stream=sys.stdout,