Reading s_tag from the subscriber

Change-Id: Id0be35c520dfa0316885d84f7089ef045e58dc70
diff --git a/xos/synchronizer/models/convenience/voltserviceinstance.py b/xos/synchronizer/models/convenience/voltserviceinstance.py
index fdae09e..6c59ef6 100644
--- a/xos/synchronizer/models/convenience/voltserviceinstance.py
+++ b/xos/synchronizer/models/convenience/voltserviceinstance.py
@@ -21,45 +21,6 @@
 
 class ORMWrapperVOLTServiceInstance(ORMWrapperServiceInstance):
 
-    @property
-    def vsg(self):
-        log.warning('VOLTServiceInstance.vsg is DEPRECATED, use get_westbound_service_instance_properties instead')
-        links = self.stub.ServiceInstanceLink.objects.filter(subscriber_service_instance_id = self.id)
-        for link in links:
-            # cast from ServiceInstance to VSGTenant
-            vsgs = self.stub.VSGServiceInstance.objects.filter(id = link.provider_service_instance.id)
-            if vsgs:
-                return vsgs[0]
-        return None
-
-    # DEPRECATED
-    @property
-    def vcpe(self):
-        log.warning('VOLTServiceInstance.vcpe is DEPRECATED, use VOLTServiceInstance.vsg instead')
-        return self.vsg
-
-    @property
-    def subscriber(self):
-        log.warning(
-            'VOLTServiceInstance.subscriber is DEPRECATED, use get_westbound_service_instance_properties instead')
-        # NOTE this assume that each VOLT has just 1 subscriber, is that right?
-        try:
-            links = self.stub.ServiceInstanceLink.objects.filter(provider_service_instance_id = self.id)
-            for link in links:
-                subs = self.stub.ServiceInstance.objects.filter(id=link.subscriber_service_instance_id)
-                if subs:
-                    return subs[0].leaf_model
-            return None
-        except Exception, e:
-            log.warning('Error while locating subscriber for vOLTServiceInstance with id %s: %s' % (self.id, e.message))
-            return None
-
-    @property
-    def c_tag(self):
-        log.warning(
-            'VOLTServiceInstance.c_tag is DEPRECATED, use get_westbound_service_instance_properties instead')
-        return self.subscriber.c_tag
-
     def get_olt_device_by_subscriber(self):
         pon_port = self.get_pon_port_by_subscriber()
         return pon_port.olt_device
@@ -71,18 +32,6 @@
         return onu.pon_port
 
     @property
-    def s_tag(self):
-        try:
-            pon_port = self.get_pon_port_by_subscriber()
-
-            if pon_port:
-                return pon_port.s_tag
-            return None
-        except Exception, e:
-            log.exception('Error while reading s_tag: %s' % e.message)
-            return None
-
-    @property
     def switch_datapath_id(self):
         try:
             olt_device = self.get_olt_device_by_subscriber()
diff --git a/xos/synchronizer/models/models.py b/xos/synchronizer/models/models.py
index 046e744..4d5b8b8 100644
--- a/xos/synchronizer/models/models.py
+++ b/xos/synchronizer/models/models.py
@@ -92,39 +92,6 @@
     class Meta:
         proxy = True
 
-    def generate_tag(self):
-        # NOTE this method will loop if available c_tags are ended
-        tag = random.randint(16, 4096)
-        if tag in self.get_used_s_tags():
-            return self.generate_tag()
-        return tag
-
-    def get_used_s_tags(self):
-        same_olt_device = OLTDevice.objects.filter(device_id=self.olt_device)
-        return [s.c_tag for s in same_olt_device]
-
-    def save(self, *args, **kwargs):
-        # validate s_tag
-        if hasattr(self, 's_tag') and self.s_tag is not None:
-            is_update_with_same_tag = False
-
-            if not self.is_new:
-                # if it is an update, but the tag is the same, skip validation
-                existing = PONPort.objects.filter(s_tag=self.s_tag)
-
-                if len(existing) > 0 and existing[0].s_tag == self.s_tag and existing[0].id == self.id:
-                    is_update_with_same_tag = True
-
-            if self.s_tag in self.get_used_s_tags() and not is_update_with_same_tag:
-                raise XOSValidationError(
-                    "The s_tag you specified (%s) has already been used on device %s" % (self.s_tag, self.onu_device))
-
-        if not hasattr(self, "s_tag") or self.s_tag is None:
-            self.s_tag = self.generate_tag()
-
-        super(PONPort, self).save(*args, **kwargs)
-
-
 class NNIPort(NNIPort_decl):
     class Meta:
         proxy = True
diff --git a/xos/synchronizer/models/volt.xproto b/xos/synchronizer/models/volt.xproto
index de66517..6871a3b 100644
--- a/xos/synchronizer/models/volt.xproto
+++ b/xos/synchronizer/models/volt.xproto
@@ -52,11 +52,10 @@
 }
 
 message PONPort (PortBase){
-    option verbose_name = "OLT PON Port";
-    option description="OLT Side PON Port";
+    option verbose_name = "PON Port";
+    option description="PON Port";
 
     required manytoone olt_device->OLTDevice:pon_ports = 1 [db_index = True, null = False, blank = False];
-    required int32 s_tag = 2 [help_text = "S Tag", null = False, db_index = False, blank = False];
 }
 
 message NNIPort (PortBase) {
@@ -80,8 +79,8 @@
 }
 
 message PONONUPort (PortBase) {
-    option verbose_name = "ONU PON Port";
-    option description="ONU Side PON Port";
+    option verbose_name = "ANI Port";
+    option description="ANI Port";
     required manytoone onu_device->ONUDevice:pononu_ports = 1 [db_index = True, null = False, blank = False];
 }
 
diff --git a/xos/synchronizer/steps/sync_olt_device.py b/xos/synchronizer/steps/sync_olt_device.py
index 5eeeafd..056a62c 100644
--- a/xos/synchronizer/steps/sync_olt_device.py
+++ b/xos/synchronizer/steps/sync_olt_device.py
@@ -131,13 +131,6 @@
         onos_voltha = Helpers.get_onos_voltha_info(model.volt_service)
         onos_voltha_basic_auth = HTTPBasicAuth(onos_voltha['user'], onos_voltha['pass'])
 
-        try:
-            # NOTE For now, we assume that each OLT has only one pon port
-            vlan = model.pon_ports.all()[0].s_tag
-        except Exception as e:
-            raise DeferredException("Waiting for pon_ports to come up")
-
-
         # Add device info to onos-voltha
         data = {
           "devices": {
@@ -147,7 +140,7 @@
               },
               "accessDevice": {
                 "uplink": model.uplink,
-                "vlan": vlan
+                "vlan": 1
               }
             }
           }
diff --git a/xos/synchronizer/steps/sync_volt_service_instance.py b/xos/synchronizer/steps/sync_volt_service_instance.py
index 9f005bd..10091cf 100644
--- a/xos/synchronizer/steps/sync_volt_service_instance.py
+++ b/xos/synchronizer/steps/sync_volt_service_instance.py
@@ -33,6 +33,10 @@
 
     def sync_record(self, o):
 
+        if o.policy_code != 1:
+            raise DeferredException("Waiting for ModelPolicy to complete")
+
+
         volt_service = VOLTService.objects.get(id=o.owner_id)
 
         si = ServiceInstance.objects.get(id=o.id)
@@ -40,17 +44,23 @@
         log.info("Synching OLTServiceInstance", object=str(o), **o.tologdict())
 
         c_tag = si.get_westbound_service_instance_properties("c_tag")
+        s_tag = si.get_westbound_service_instance_properties("s_tag")
 
         olt_device = o.onu_device.pon_port.olt_device
 
-        # NOTE each ONU has only one UNI port!
-        uni_port_id = o.onu_device.uni_ports.first().port_no
+        try:
+            # NOTE each ONU has only one UNI port!
+            uni_port_id = o.onu_device.uni_ports.first().port_no
+        except AttributeError:
+            # This is because the ONUDevice is set by model_policy
+            raise DeferredException("Waiting for ONUDevice %s " % olt_device.name)
 
         if not olt_device.dp_id:
             raise DeferredException("Waiting for OLTDevice %s to be synchronized" % olt_device.name)
 
         log.debug("Adding subscriber with info",
                  c_tag = c_tag,
+                 s_tag = s_tag,
                  uni_port_id = uni_port_id,
                  dp_id = olt_device.dp_id)
 
@@ -58,11 +68,18 @@
         onos_voltha = Helpers.get_onos_voltha_info(volt_service)
         onos_voltha_basic_auth = HTTPBasicAuth(onos_voltha['user'], onos_voltha['pass'])
 
-        full_url = "%s:%d/onos/olt/oltapp/%s/%s/%s" % (onos_voltha['url'], onos_voltha['port'], olt_device.dp_id, uni_port_id, c_tag)
+        full_url = "%s:%d/onos/olt/oltapp/subscribers" % (onos_voltha['url'], onos_voltha['port'])
 
-        log.info("Sending request to onos-voltha", url=full_url)
+        data = {
+            "deviceId" : olt_device.dp_id,
+            "port" : uni_port_id,
+            "sVlan" : s_tag,
+            "cVlan" : c_tag
+        }
 
-        request = requests.post(full_url, auth=onos_voltha_basic_auth)
+        log.info("Sending request to onos-voltha", url=full_url, data=data)
+
+        request = requests.post(full_url, auth=onos_voltha_basic_auth, json=data)
 
         if request.status_code != 200:
             raise Exception("Failed to add subscriber in onos-voltha: %s" % request.text)
diff --git a/xos/synchronizer/steps/test_sync_olt_device.py b/xos/synchronizer/steps/test_sync_olt_device.py
index a1ff08c..04cdd0b 100644
--- a/xos/synchronizer/steps/test_sync_olt_device.py
+++ b/xos/synchronizer/steps/test_sync_olt_device.py
@@ -48,7 +48,7 @@
     else:
         if not request['of:0000000ce2314000']['basic']['driver'] == 'voltha':
             return False
-        if not request['of:0000000ce2314000']['accessDevice']['vlan'] == "s_tag" or not request['of:0000000ce2314000']['accessDevice']['uplink'] == "129":
+        if not request['of:0000000ce2314000']['accessDevice']['vlan'] == 1 or not request['of:0000000ce2314000']['accessDevice']['uplink'] == "129":
             return False
     return True
 
@@ -87,7 +87,6 @@
 
         pon_port = Mock()
         pon_port.port_id = "00ff00"
-        pon_port.s_tag = "s_tag"
 
         # Create a mock OLTDevice
         o = Mock()
@@ -310,16 +309,5 @@
 
         # We don't need to assert here if there are no exceptions happening
 
-    def test_deferred_for_port(self):
-        self.o.pon_ports.all.side_effect = Exception
-        with self.assertRaises(DeferredException) as e:
-            self.sync_step().configure_onos(self.o)
-        self.assertEqual(e.exception.message, "Waiting for pon_ports to come up")
-
-        self.o.pon_ports.all.return_value = []
-        with self.assertRaises(DeferredException) as e:
-            self.sync_step().configure_onos(self.o)
-        self.assertEqual(e.exception.message, "Waiting for pon_ports to come up")
-
 if __name__ == "__main__":
     unittest.main()
diff --git a/xos/synchronizer/steps/test_sync_volt_service_instance.py b/xos/synchronizer/steps/test_sync_volt_service_instance.py
index 2df696e..d7877f6 100644
--- a/xos/synchronizer/steps/test_sync_volt_service_instance.py
+++ b/xos/synchronizer/steps/test_sync_volt_service_instance.py
@@ -13,6 +13,7 @@
 # limitations under the License.
 
 import unittest
+import functools
 from mock import patch, call, Mock, PropertyMock
 import requests_mock
 
@@ -43,6 +44,12 @@
 def mock_get_westbound_service_instance_properties(prop):
     return prop
 
+def match_json(desired, req):
+    if desired!=req.json():
+        raise Exception("Got request %s, but body is not matching" % req.url)
+        return False
+    return True
+
 class TestSyncVOLTServiceInstance(unittest.TestCase):
     def setUp(self):
         global DeferredException
@@ -96,6 +103,7 @@
 
         # create a mock service instance
         o = Mock()
+        o.policy_code = 1
         o.id = 1
         o.owner_id = "volt_service"
         o.onu_device = onu_device
@@ -127,9 +135,17 @@
 
     @requests_mock.Mocker()
     def test_do_sync(self, m):
-        m.post("http://onos_voltha_url:4321/onos/olt/oltapp/of:dp_id/uni_port_id/c_tag", status_code=200, json={})
 
         self.onu_device.pon_port.olt_device.dp_id = "of:dp_id"
+        
+        expected_conf = {
+            "deviceId" : "of:dp_id",
+            "port" : "uni_port_id",
+            "sVlan" : "s_tag",
+            "cVlan" : "c_tag"
+        }
+
+        m.post("http://onos_voltha_url:4321/onos/olt/oltapp/subscribers", status_code=200, json={}, additional_matcher=functools.partial(match_json, expected_conf))
 
         with patch.object(ServiceInstance.objects, "get") as service_instance_mock, \
                 patch.object(VOLTService.objects, "get") as olt_service_mock:
@@ -141,7 +157,15 @@
 
     @requests_mock.Mocker()
     def test_do_sync_fail(self, m):
-        m.post("http://onos_voltha_url:4321/onos/olt/oltapp/of:dp_id/uni_port_id/c_tag", status_code=500, text="Mock Error")
+
+        expected_conf = {
+            "deviceId" : "of:dp_id",
+            "port" : "uni_port_id",
+            "sVlan" : "s_tag",
+            "cVlan" : "c_tag"
+        }
+
+        m.post("http://onos_voltha_url:4321/onos/olt/oltapp/subscribers", status_code=500, text="Mock Error", additional_matcher=functools.partial(match_json, expected_conf))
 
         self.onu_device.pon_port.olt_device.dp_id = "of:dp_id"