CORD-1172: Brought Metronet service over to xproto

Change-Id: I4e9d14b0b5cd7a2fe9ce8efdde432566fc5d7f9d
diff --git a/README.md b/README.md
index b2730be..8ee75a1 100644
--- a/README.md
+++ b/README.md
@@ -5,4 +5,3 @@
 Sub-directories
 
 * xos: A service definition for the Metronetwork. This follows the XOS component design for onboarding.
-
diff --git a/xos/attic/bandwidthprofile_model.py b/xos/attic/bandwidthprofile_model.py
new file mode 100644
index 0000000..3fd623e
--- /dev/null
+++ b/xos/attic/bandwidthprofile_model.py
@@ -0,0 +1 @@
+def __unicode__(self):  return u'%s' % (self.name)
diff --git a/xos/attic/header.py b/xos/attic/header.py
new file mode 100644
index 0000000..f4db591
--- /dev/null
+++ b/xos/attic/header.py
@@ -0,0 +1,14 @@
+# models.py -  Metro Network Service
+
+from django.db import models
+from django.db.models import *
+from core.models import Service
+from core.models import PlCoreBase
+from core.models import Site
+
+METRONETWORK_KIND = "metronetwork"
+SERVICE_NAME = 'metronetwork'
+SERVICE_NAME_ELINE_VERBOSE = 'E-Line Service'
+SERVICE_NAME_ELAN_VERBOSE = 'E-LAN Service'
+SERVICE_NAME_ETREE_VERBOSE = 'E-Tree Service'
+
diff --git a/xos/attic/metronetworksystem_model.py b/xos/attic/metronetworksystem_model.py
new file mode 100644
index 0000000..358cf8d
--- /dev/null
+++ b/xos/attic/metronetworksystem_model.py
@@ -0,0 +1,15 @@
+def __init__(self, *args, **kwargs):
+    super(MetroNetworkSystem, self).__init__(*args, **kwargs)
+
+def getAdminstrativeState(self):
+     return self.administrativeState
+
+def setAdminstrativeState(self, value):
+    self.administrativeState = value
+
+def getOperationalState(self):
+    return self.operationalState
+
+def getRestUrl(self):
+    return self.restUrl
+
diff --git a/xos/attic/networkedgeport_model.py b/xos/attic/networkedgeport_model.py
new file mode 100644
index 0000000..52f17fe
--- /dev/null
+++ b/xos/attic/networkedgeport_model.py
@@ -0,0 +1,22 @@
+def __unicode__(self):
+    return u'%s' % (self.pid)
+
+def save(self, *args, **kwargs):
+
+    if self.latlng:
+        try:
+            latlng_value = getattr(self, 'latlng').strip()
+            if (latlng_value.startswith('[') and latlng_value.endswith(']') and latlng_value.index(',') > 0):
+                lat = latlng_value[1: latlng_value.index(',')].strip()
+                lng = latlng_value[latlng_value.index(',') + 1: len(latlng_value) - 1].strip()
+
+                #If lat and lng are not floats, the code below should result in an error.
+                lat_validation = float(lat)
+                lng_validation = float(lng)
+            else:
+                raise ValueError("The lat/lng value is not formatted correctly.")
+        except:
+            raise ValueError("The lat/lng value is not formatted correctly.")
+
+    super(NetworkEdgePort, self).save(*args, **kwargs)
+
diff --git a/xos/attic/remoteport_model.py b/xos/attic/remoteport_model.py
new file mode 100644
index 0000000..3fd623e
--- /dev/null
+++ b/xos/attic/remoteport_model.py
@@ -0,0 +1 @@
+def __unicode__(self):  return u'%s' % (self.name)
diff --git a/xos/attic/servicespoke_model.py b/xos/attic/servicespoke_model.py
new file mode 100644
index 0000000..3fd623e
--- /dev/null
+++ b/xos/attic/servicespoke_model.py
@@ -0,0 +1 @@
+def __unicode__(self):  return u'%s' % (self.name)
diff --git a/xos/attic/usernetworkinterfaces_model.py b/xos/attic/usernetworkinterfaces_model.py
new file mode 100644
index 0000000..92d2700
--- /dev/null
+++ b/xos/attic/usernetworkinterfaces_model.py
@@ -0,0 +1,20 @@
+def __unicode__(self):  return u'%s' % (self.name)
+
+def save(self, *args, **kwargs):
+
+    if self.latlng:
+        try:
+            latlng_value = getattr(self, 'latlng').strip()
+            if (latlng_value.startswith('[') and latlng_value.endswith(']') and latlng_value.index(',') > 0):
+                lat = latlng_value[1: latlng_value.index(',')].strip()
+                lng = latlng_value[latlng_value.index(',') + 1: len(latlng_value) - 1].strip()
+
+                # If lat and lng are not floats, the code below should result in an error.
+                lat_validation = float(lat)
+                lng_validation = float(lng)
+            else:
+                raise ValueError("The lat/lng value is not formatted correctly.")
+        except:
+            raise ValueError("The lat/lng value is not formatted correctly.")
+
+    super(UserNetworkInterface, self).save(*args, **kwargs)
diff --git a/xos/header.py b/xos/header.py
new file mode 120000
index 0000000..721b5c0
--- /dev/null
+++ b/xos/header.py
@@ -0,0 +1 @@
+attic/header.py
\ No newline at end of file
diff --git a/xos/metronet.xproto b/xos/metronet.xproto
new file mode 100644
index 0000000..4094bf4
--- /dev/null
+++ b/xos/metronet.xproto
@@ -0,0 +1,136 @@
+option name = "metronetwork";
+
+message MetroNetworkSystem (PlCoreBase){
+     option verbose_name = "Metro Network System";
+
+     required string name = 1 [db_index = False, max_length = 256, null = False, blank = False];
+     required string description = 2 [db_index = False, max_length = 1024, null = False, blank = False];
+     required string restUrl = 3 [db_index = False, max_length = 256, null = False, blank = False];
+     required string administrativeState = 4 [default = "disabled", choices = "(('enabled', 'Enabled'), ('disabled', 'Disabled'))", max_length = 16, blank = False, null = False, db_index = False];
+     required string operationalState = 5 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('active', 'Active'), ('inactive', 'Inactive'))"];
+}
+
+message NetworkDevice (PlCoreBase){
+     option verbose_name = "Network Device";
+
+     optional string name = 1 [help_text = "Device friendly name", max_length = 20, null = True, db_index = False, blank = True];
+     required string restCtrlUrl = 2 [db_index = False, max_length = 256, null = False, blank = False];
+     required string authType = 3 [blank = False, max_length = 16, null = False, db_index = False, choices = "(('basic', 'Basic'), ('key', 'Key'), ('oauth', 'OAuth'))"];
+     required string username = 4 [db_index = False, max_length = 32, null = False, blank = True];
+     required string password = 5 [db_index = False, max_length = 32, null = False, blank = True];
+     required string administrativeState = 6 [default = "disabled", choices = "(('enabled', 'Enabled'), ('disabled', 'Disabled'), ('syncrequested', 'SyncRequested'), ('syncinprogress', 'SyncInProgress'))", max_length = 16, blank = False, null = False, db_index = False];
+}
+
+message NetworkEdgePort (PlCoreBase){
+     option verbose_name = "Network Edge Port";
+
+     required manytoone element->NetworkDevice:networkedgeport = 1 [db_index = True, null = False, blank = False];
+     required string pid = 2 [db_index = False, max_length = 256, null = False, blank = False];
+     required int32 bwpCfgCbs = 3 [db_index = False, null = False, blank = True];
+     required int32 bwpCfgEbs = 4 [db_index = False, null = False, blank = True];
+     required int32 bwpCfgCir = 5 [db_index = False, null = False, blank = True];
+     required int32 bwpCfgEir = 6 [db_index = False, null = False, blank = True];
+     required string name = 7 [db_index = False, max_length = 256, null = False, blank = True];
+     required string location = 8 [db_index = False, max_length = 256, null = False, blank = True];
+     required string latlng = 9 [db_index = False, max_length = 50, null = False, blank = True];
+}
+
+
+message NetworkEdgeToEdgePointConnection (Service){
+     option verbose_name = "E-Line Service";
+
+     required string sid = 1 [db_index = False, max_length = 256, null = False, blank = True];
+     required string type = 2 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('direct', 'Direct'), ('tunnel', 'Tunnel'), ('optical', 'Optical'), ('virtual', 'Virtual'), ('Point_To_Point', 'Point To Point'))"];
+     required string vlanid = 3 [db_index = False, max_length = 64, null = False, blank = False];
+     required manytoone uni1->NetworkEdgePort:EdgePointToEdgePointSrc = 4 [db_index = True, null = False, blank = False];
+     required manytoone uni2->NetworkEdgePort:EdgePointToEdgePointDst = 5 [db_index = True, null = False, blank = False];
+     required string operstate = 6 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('active', 'Active'), ('inactive', 'Inactive'))"];
+     required string adminstate = 7 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('disabled', 'Disabled'), ('activationrequested', 'ActivationRequested'), ('enabled', 'Enabled'), ('invalid', 'Invalid'), ('deactivationrequested', 'DeactivationRequested'))"];
+}
+
+
+message NetworkEdgeToMultipointConnection (Service){
+     option verbose_name = "E-Line Service";
+
+     required string sid = 1 [db_index = False, max_length = 256, null = False, blank = True];
+     required string type = 2 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('vlan', 'VLAN'), ('ip', 'IP'), ('ethernet', 'Ethernet'), ('Root_Multipoint', 'Root Multipoint'))"];
+     required string vlanid = 3 [db_index = False, max_length = 64, null = False, blank = False];
+     required manytoone root->NetworkEdgePort:EdgeToMultipointRoot = 4 [db_index = True, null = False, blank = False];
+     required string operstate = 5 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('active', 'Active'), ('inactive', 'Inactive'))"];
+     required string adminstate = 6 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('disabled', 'Disabled'), ('activationrequested', 'ActivationRequested'), ('enabled', 'Enabled'), ('invalid', 'Invalid'), ('deactivationrequested', 'DeactivationRequested'))"];
+     required manytomany eps->NetworkEdgePort/NetworkMultipointToMultipointConnection_eps:networkedgetomultipointconnection_eps = 7 [db_index = False, null = False, blank = False];
+}
+
+
+message NetworkMultipointToMultipointConnection (Service){
+     option verbose_name = "E-LAN Service";
+
+     required string sid = 1 [db_index = False, max_length = 256, null = False, blank = True];
+     required string type = 2 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('vlan', 'VLAN'), ('ip', 'IP'), ('ethernet', 'Ethernet'), ('Multipoint_To_Multipoint', 'Multipoint To Multipoint'))"];
+     required string vlanid = 3 [db_index = False, max_length = 64, null = False, blank = False];
+     required string operstate = 4 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('active', 'Active'), ('inactive', 'Inactive'))"];
+     required string adminstate = 5 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('disabled', 'Disabled'), ('activationrequested', 'ActivationRequested'), ('enabled', 'Enabled'), ('invalid', 'Invalid'), ('deactivationrequested', 'DeactivationRequested'))"];
+     required manytomany eps->NetworkEdgePort/NetworkMultipointToMultipointConnection_eps:networkmultipointtomultipointconnection_eps = 6 [db_index = False, null = False, blank = False];
+}
+
+message BandwidthProfile (PlCoreBase){
+     option verbose_name = "Bandwidth Profile";
+
+     required int32 bwpcfgcbs = 1 [db_index = False, null = False, blank = False];
+     required int32 bwpcfgebs = 2 [db_index = False, null = False, blank = False];
+     required int32 bwpcfgcir = 3 [db_index = False, null = False, blank = False];
+     required int32 bwpcfgeir = 4 [db_index = False, null = False, blank = False];
+     required string name = 5 [db_index = False, max_length = 256, null = False, blank = False];
+}
+
+message RemotePort (PlCoreBase){
+     option verbose_name = "Remote Port";
+
+     required manytoone remoteportsite->Site:RemotePortSite = 1 [db_index = True, null = False, blank = False];
+     required manytoone edgeport->NetworkEdgePort:RemotePortEdgePort = 2 [db_index = True, null = False, blank = False];
+     required string name = 3 [db_index = False, max_length = 256, null = False, blank = False];
+}
+
+
+message ServiceSpoke (PlCoreBase){
+     option verbose_name = "Service Spoke";
+
+     required manytoone vnodlocalsite->Site:VnodLocalSite = 1 [db_index = True, null = False, blank = False];
+     required manytoone vnodlocalport->RemotePort:VnodLocalPort = 2 [db_index = True, null = False, blank = False];
+     required string name = 3 [db_index = False, max_length = 256, null = False, blank = False];
+     required string remotesubscriber = 4 [db_index = False, max_length = 256, null = False, blank = True];
+     required string remotevnodid = 5 [db_index = False, max_length = 256, null = False, blank = True];
+     required bool autoattached = 6 [default = False, null = False, db_index = False, blank = True];
+     required string operstate = 7 [default = "inactive", choices = "(('active', 'Active'), ('inactive', 'Inactive'))", max_length = 256, blank = False, null = False, db_index = False];
+     required string adminstate = 8 [default = "disabled", choices = "(('disabled', 'Disabled'), ('configured', 'Configured'), ('impaired', 'Impaired'), ('enabled', 'Enabled'))", max_length = 64, blank = False, null = False, db_index = False];
+}
+
+message VnodGlobalService (Service){
+     option verbose_name = "Virtual Network On Demand Global Service"; 
+
+     required string servicehandle = 1 [db_index = False, max_length = 64, null = False, blank = False];
+     required string vlanid = 2 [db_index = False, max_length = 64, null = False, blank = False];
+     required string type = 3 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('eline', 'E-Line Service'), ('elan', 'E-LAN Service'), ('etree', 'E-Tree Service'))"];
+     optional manytoone metronetworkroottomultipoint->NetworkEdgeToMultipointConnection:EtreeService = 4 [db_index = True, null = True, blank = False];
+     optional manytoone metronetworkmultipoint->NetworkMultipointToMultipointConnection:ElanService = 5 [db_index = True, null = True, blank = False];
+     optional manytoone metronetworkpointtopoint->NetworkEdgeToEdgePointConnection:ElineService = 6 [db_index = True, null = True, blank = False];
+     required string operstate = 7 [blank = False, max_length = 256, null = False, db_index = False, choices = "(('active', 'Active'), ('inactive', 'Inactive'))"];
+     required string adminstate = 8 [default = "enabled", choices = "(('disabled', 'Disabled'), ('activationrequested', 'ActivationRequested'), ('enabled', 'Enabled'), ('invalid', 'Invalid'), ('deactivationrequested', 'DeactivationRequested'))", max_length = 256, blank = False, null = False, db_index = False];
+     required manytoone bandwidthProfile->BandwidthProfile:BandwidthProfile = 9 [db_index = True, null = False, blank = False];
+     required manytomany spokes->ServiceSpoke/VnodGlobalService_spokes:ServiceSpokes = 10 [db_index = False, null = False, blank = False];
+}
+
+message UserNetworkInterface (PlCoreBase){
+     option verbose_name = "User Network Interface"; 
+
+     required int32 enabled = 1 [db_index = False, null = False, blank = False];
+     required int32 capacity = 2 [db_index = False, null = False, blank = False];
+     required int32 bw_used = 3 [db_index = False, null = False, blank = False];
+     required string vlanIds = 4 [db_index = False, max_length = 256, null = False, blank = False];
+     required string location = 5 [db_index = False, max_length = 256, null = False, blank = True];
+     required string latlng = 6 [db_index = False, max_length = 50, null = False, blank = True];
+     required string name = 7 [db_index = False, max_length = 256, null = False, blank = False];
+}
+
+
+
diff --git a/xos/metronetwork-onboard.yaml b/xos/metronetwork-onboard.yaml
index 93dfff2..e4ecb69 100644
--- a/xos/metronetwork-onboard.yaml
+++ b/xos/metronetwork-onboard.yaml
@@ -13,10 +13,10 @@
           base_url: file:///opt/xos_services/metro-net/xos/
           # The following will concatenate with base_url automatically, if
           # base_url is non-null.
-          models: models.py
+          xproto: ./
           admin: admin.py
           rest_service: subdirectory:metronetworkservice api/service/metronetworkservice/metronetworkservice.py
           synchronizer: synchronizer/manifest
           synchronizer_run: metronetworkervice-synchronizer.py
           tosca_resource: tosca/resources/metronetservice.py
-          tosca_custom_types: metronet.yaml
\ No newline at end of file
+          tosca_custom_types: metronet.yaml
diff --git a/xos/models.py b/xos/models.py
deleted file mode 100644
index 580bb4f..0000000
--- a/xos/models.py
+++ /dev/null
@@ -1,503 +0,0 @@
-# models.py -  Metro Network Service
-
-from django.db import models
-from core.models import Service
-from core.models import PlCoreBase
-from core.models import Site
-
-METRONETWORK_KIND = "metronetwork"
-SERVICE_NAME = 'metronetwork'
-SERVICE_NAME_ELINE_VERBOSE = 'E-Line Service'
-SERVICE_NAME_ELAN_VERBOSE = 'E-LAN Service'
-SERVICE_NAME_ETREE_VERBOSE = 'E-Tree Service'
-
-class MetroNetworkSystem(PlCoreBase):
-
-    class Meta:
-        app_label = METRONETWORK_KIND
-        verbose_name = "Metro Network System"
-
-    ADMINISTRATIVE_STATE = (
-        ('enabled', 'Enabled'),
-        ('disabled', 'Disabled')
-    )
-
-    OPERATIONALSTATE = (
-        ('active', 'Active'),
-        ('inactive', 'Inactive')
-    )
-
-    name = models.CharField(unique=True,
-                           verbose_name="Name",
-                           max_length=256,
-                           editable=True)
-
-    description = models.CharField(verbose_name="Description",
-                                   max_length=1024,
-                                   editable=True)
-
-    restUrl = models.CharField(verbose_name="Rest URL",
-                               max_length=256,
-                               editable=True)
-
-    administrativeState = models.CharField(choices=ADMINISTRATIVE_STATE,
-                                           default='disabled',
-                                           verbose_name="AdministrativeState",
-                                           max_length=16,
-                                           editable=True)
-
-    operationalState = models.CharField(choices=OPERATIONALSTATE,
-                                        verbose_name="OperationalState",
-                                        max_length=256,
-                                        editable=True)
-
-    def __init__(self, *args, **kwargs):
-        super(MetroNetworkSystem, self).__init__(*args, **kwargs)
-
-    def getAdminstrativeState(self):
-         return self.administrativeState
-
-    def setAdminstrativeState(self, value):
-        self.administrativeState = value
-
-    def getOperationalState(self):
-        return self.operationalState
-
-    def getRestUrl(self):
-        return self.restUrl
-
-
-class NetworkDevice(PlCoreBase):
-
-    class Meta:
-        app_label = METRONETWORK_KIND
-        verbose_name = "Network Device"
-
-    ADMINISTRATIVE_STATE = (
-        ('enabled', 'Enabled'),
-        ('disabled', 'Disabled'),
-        ('syncrequested', 'SyncRequested'),
-        ('syncinprogress', 'SyncInProgress')
-    )
-
-    AUTH_TYPE = (
-        ('basic', 'Basic'),
-        ('key', 'Key'),
-        ('oauth', 'OAuth')
-    )
-
-    # Leaving out the attributes below for now - not clear we will need them
-    # type = models.CharField(choices=TYPE, verbose_name="Type", max_length=256, editable=False)
-    # manufacturer = models.CharField(unique=False, verbose_name="Manufacturer", max_length=256, editable=False)
-    # serialNumber = models.CharField(unique=True, verbose_name="Serial Number", max_length=256, editable=False)
-    # chassisId = models.CharField(unique=False, verbose_name="Chassis ID", max_length=256, editable=False)
-
-    name = models.CharField(max_length=20, help_text="Device friendly name", null=True, blank=True)
-    restCtrlUrl = models.CharField(unique=True,
-                               verbose_name="RestCtrlURL",
-                               max_length=256,
-                               editable=True)
-    authType = models.CharField(choices=AUTH_TYPE, verbose_name='Auth Type', max_length=16, editable=True)
-    username = models.CharField(verbose_name='Username', max_length=32, editable=True, blank=True)
-    password = models.CharField(max_length=32, verbose_name='Password', editable=True, blank=True)
-    administrativeState = models.CharField(choices=ADMINISTRATIVE_STATE,
-                                           default='disabled',
-                                           verbose_name="AdministrativeState",
-                                           max_length=16,
-                                           editable=True)
-    id = models.CharField(unique=True,
-                          verbose_name="Element Id",
-                          primary_key=True,
-                          max_length=256,
-                          editable=True)
-
-    def __init__(self, *args, **kwargs):
-        super(NetworkDevice, self).__init__(*args, **kwargs)
-
-class NetworkEdgePort(PlCoreBase):
-
-    class Meta:
-        app_label = METRONETWORK_KIND
-        verbose_name = "Network Edge Port"
-
-    element = models.ForeignKey(NetworkDevice, on_delete=models.CASCADE)
-    id = models.AutoField(verbose_name="id", primary_key=True, editable=False)
-    pid = models.CharField(unique=True, verbose_name="Port ID", max_length=256, editable=False)
-    bwpCfgCbs = models.IntegerField(verbose_name="Committed Burst Size", editable=False, blank=True)
-    bwpCfgEbs = models.IntegerField(verbose_name="Excess Burst Size", editable=False, blank=True)
-    bwpCfgCir = models.IntegerField(verbose_name="Committed Information Rate", editable=False, blank=True)
-    bwpCfgEir = models.IntegerField(verbose_name="Excess Information Rate", editable=False, blank=True)
-    name = models.CharField(verbose_name="Name", max_length=256, editable=True, blank=True)
-    location = models.CharField(verbose_name="Location", max_length=256, editable=True, blank=True)
-    latlng = models.CharField(verbose_name="Latitude/Longitude", max_length=50, editable=True, blank=True)
-
-    def __init__(self, *args, **kwargs):
-        super(NetworkEdgePort, self).__init__(*args, **kwargs)
-
-    def __unicode__(self):
-        return u'%s' % (self.pid)
-
-    def save(self, *args, **kwargs):
-
-        if self.latlng:
-            try:
-                latlng_value = getattr(self, 'latlng').strip()
-                if (latlng_value.startswith('[') and latlng_value.endswith(']') and latlng_value.index(',') > 0):
-                    lat = latlng_value[1: latlng_value.index(',')].strip()
-                    lng = latlng_value[latlng_value.index(',') + 1: len(latlng_value) - 1].strip()
-
-                    #If lat and lng are not floats, the code below should result in an error.
-                    lat_validation = float(lat)
-                    lng_validation = float(lng)
-                else:
-                    raise ValueError("The lat/lng value is not formatted correctly.")
-            except:
-                raise ValueError("The lat/lng value is not formatted correctly.")
-
-        super(NetworkEdgePort, self).save(*args, **kwargs)
-
-#E-Line Service
-class NetworkEdgeToEdgePointConnection(Service):
-
-    class Meta:
-        app_label = SERVICE_NAME
-        verbose_name = SERVICE_NAME_ELINE_VERBOSE
-
-    TYPE = (
-        ('direct', 'Direct'),
-        ('tunnel', 'Tunnel'),
-        ('optical', 'Optical'),
-        ('virtual', 'Virtual'),
-        ('Point_To_Point', 'Point To Point')
-    )
-
-    OPERATIONALSTATE = (
-        ('active', 'Active'),
-        ('inactive', 'Inactive')
-    )
-
-    ADMINISTRATIVESTATE = (
-        ('disabled', 'Disabled'),
-        ('activationrequested', 'ActivationRequested'),
-        ('enabled', 'Enabled'),
-        ('invalid', 'Invalid'),
-        ('deactivationrequested', 'DeactivationRequested')
-    )
-
-    sid = models.CharField(verbose_name="Service ID", max_length=256, editable=True, blank=True)
-    type = models.CharField(choices=TYPE, verbose_name="Type", max_length=256, editable=True)
-    vlanid = models.CharField(verbose_name="Vlanid", max_length=64, editable=True)
-    uni1 = models.ForeignKey(NetworkEdgePort,
-                            related_name='EdgePointToEdgePointSrc',
-                            verbose_name="UNI 1",
-                            editable=True,
-                            on_delete=models.CASCADE)
-    uni2 = models.ForeignKey(NetworkEdgePort,
-                             related_name='EdgePointToEdgePointDst',
-                             verbose_name="UNI 2",
-                             editable=True,
-                             on_delete=models.CASCADE)
-    operstate = models.CharField(choices=OPERATIONALSTATE, verbose_name="OperationalState", max_length=256, editable=True)
-    adminstate = models.CharField(choices=ADMINISTRATIVESTATE, verbose_name="AdministrativeState", max_length=256, editable=True)
-
-    #uni1_createbuffer = models.CharField(max_length=256, default="{}", null=True)
-    #uni2_createbuffer = models.CharField(max_length=256, default="{}", null=True)
-
-    def __init__(self, *args, **kwargs):
-        super(NetworkEdgeToEdgePointConnection, self).__init__(*args, **kwargs)
-
-#E-Tree Service
-class NetworkEdgeToMultipointConnection(Service):
-
-    class Meta:
-        app_label = SERVICE_NAME
-        verbose_name = SERVICE_NAME_ETREE_VERBOSE
-
-    TYPE = (
-        ('vlan', 'VLAN'),
-        ('ip', 'IP'),
-        ('ethernet', 'Ethernet'),
-        ('Root_Multipoint', 'Root Multipoint')
-    )
-
-    OPERATIONALSTATE = (
-        ('active', 'Active'),
-        ('inactive', 'Inactive')
-    )
-
-    ADMINISTRATIVESTATE = (
-        ('disabled', 'Disabled'),
-        ('activationrequested', 'ActivationRequested'),
-        ('enabled', 'Enabled'),
-        ('invalid', 'Invalid'),
-        ('deactivationrequested', 'DeactivationRequested')
-    )
-
-    sid = models.CharField(verbose_name="Service ID", max_length=256, editable=True, blank=True)
-    type = models.CharField(choices=TYPE, verbose_name="Type", max_length=256, editable=True)
-    vlanid = models.CharField(verbose_name="Vlanid", max_length=64, editable=True)
-    root = models.ForeignKey(NetworkEdgePort,
-                            related_name='EdgeToMultipointRoot',
-                            verbose_name="Root",
-                            editable=True,
-                            on_delete=models.CASCADE)
-    eps = models.ManyToManyField(NetworkEdgePort,
-                                 related_name='%(class)s_eps',
-                                 verbose_name="Endpoints",
-                                 editable=True)
-    operstate = models.CharField(choices=OPERATIONALSTATE, verbose_name="OperationalState", max_length=256,
-                                 editable=True)
-    adminstate = models.CharField(choices=ADMINISTRATIVESTATE, verbose_name="AdministrativeState", max_length=256,
-                                  editable=True)
-
-    # Scratch Area to help deal with the Many to Many relationship with the eps
-    #eps_createbuffer = models.CharField(max_length=1024, default="{}", null=True)
-
-    def __init__(self, *args, **kwargs):
-        super(NetworkEdgeToMultipointConnection, self).__init__(*args, **kwargs)
-
-#E-LAN Service
-class NetworkMultipointToMultipointConnection(Service):
-
-    class Meta:
-        app_label = SERVICE_NAME
-        verbose_name = SERVICE_NAME_ELAN_VERBOSE
-
-    TYPE = (
-        ('vlan', 'VLAN'),
-        ('ip', 'IP'),
-        ('ethernet', 'Ethernet'),
-        ('Multipoint_To_Multipoint', 'Multipoint To Multipoint')
-    )
-
-    OPERATIONALSTATE = (
-        ('active', 'Active'),
-        ('inactive', 'Inactive')
-    )
-
-    ADMINISTRATIVESTATE = (
-        ('disabled', 'Disabled'),
-        ('activationrequested', 'ActivationRequested'),
-        ('enabled', 'Enabled'),
-        ('invalid', 'Invalid'),
-        ('deactivationrequested', 'DeactivationRequested')
-    )
-
-    sid = models.CharField(verbose_name="Service ID", max_length=256, editable=True, blank=True)
-    type = models.CharField(choices=TYPE, verbose_name="Type", max_length=256, editable=True)
-    vlanid = models.CharField(verbose_name="Vlanid", max_length=64, editable=True)
-    eps = models.ManyToManyField(NetworkEdgePort,
-                                 related_name='%(class)s_eps',
-                                 verbose_name="Endpoints",
-                                 editable=True)
-
-    operstate = models.CharField(choices=OPERATIONALSTATE, verbose_name="OperationalState", max_length=256,
-                                 editable=True)
-    adminstate = models.CharField(choices=ADMINISTRATIVESTATE, verbose_name="AdministrativeState", max_length=256,
-                              editable=True)
-
-    # Scratch Area to help deal with the Many to Many relationship with the eps
-    #eps_createbuffer = models.CharField(max_length=1024, default="{}", null=True)
-
-    def __init__(self, *args, **kwargs):
-        super(NetworkMultipointToMultipointConnection, self).__init__(*args, **kwargs)
-
-class BandwidthProfile(PlCoreBase):
-
-    class Meta:
-        app_label = METRONETWORK_KIND
-        verbose_name = "Bandwidth Profile"
-
-    id = models.AutoField(verbose_name="id", primary_key=True, editable=False)
-    bwpcfgcbs = models.IntegerField(verbose_name="Committed Burst Size", editable=True)
-    bwpcfgebs = models.IntegerField(verbose_name="Excess Burst Size", editable=True)
-    bwpcfgcir = models.IntegerField(verbose_name="Committed Information Rate", editable=True)
-    bwpcfgeir = models.IntegerField(verbose_name="Excess Information Rate", editable=True)
-    name = models.CharField(unique=True, verbose_name="Name", max_length=256, editable=True)
-
-    def __init__(self, *args, **kwargs):
-        super(BandwidthProfile, self).__init__(*args, **kwargs)
-
-    def __unicode__(self):  return u'%s' % (self.name)
-
-# VNoD Global Objects - model is included in metro-net for simplicity
-
-class RemotePort(PlCoreBase):
-    class Meta:
-        app_label = METRONETWORK_KIND
-        verbose_name = "Remote Port"
-
-    remoteportsite = models.ForeignKey(Site,
-                                       related_name='RemotePortSite',
-                                       verbose_name="RemotePortSite",
-                                       editable=True,
-                                       on_delete=models.CASCADE)
-
-    edgeport = models.ForeignKey(NetworkEdgePort,
-                                 related_name='RemotePortEdgePort',
-                                 verbose_name="RemotePortEdgePort",
-                                 editable=True,
-                                 on_delete=models.CASCADE)
-
-    id = models.AutoField(verbose_name="id", primary_key=True, editable=False)
-    name = models.CharField(unique=True, verbose_name="Name", max_length=256, editable=True)
-
-    def __init__(self, *args, **kwargs):
-        super(RemotePort, self).__init__(*args, **kwargs)
-
-    def __unicode__(self):  return u'%s' % (self.name)
-
-class ServiceSpoke(PlCoreBase):
-
-    class Meta:
-        app_label = METRONETWORK_KIND
-        verbose_name = "Service Spoke"
-
-    OPERATIONALSTATE = (
-        ('active', 'Active'),
-        ('inactive', 'Inactive')
-    )
-
-    ADMINISTRATIVE_STATE = (
-        ('disabled', 'Disabled'),
-        ('configured', 'Configured'),
-        ('impaired', 'Impaired'),
-        ('enabled', 'Enabled')
-    )
-
-    vnodlocalsite = models.ForeignKey(Site,
-                      related_name='VnodLocalSite',
-                      verbose_name="VnodLocalSite",
-                      editable=True,
-                      on_delete=models.CASCADE)
-
-    vnodlocalport = models.ForeignKey(RemotePort,
-                                      related_name='VnodLocalPort',
-                                      verbose_name="VnodLocalPort",
-                                      editable=True,
-                                      on_delete=models.CASCADE)
-
-    id = models.AutoField(verbose_name="id", primary_key=True, editable=False)
-    name = models.CharField(unique=True, verbose_name="Name", max_length=256, editable=True)
-    remotesubscriber = models.CharField(verbose_name="RemoteSubscriber", max_length=256, blank=True, editable=False)
-    remotevnodid = models.CharField(verbose_name="RemoteVnodId", max_length=256, blank=True, editable=False)
-    autoattached = models.BooleanField(verbose_name="Auto-Attached", default=False, editable=True)
-    operstate = models.CharField(choices=OPERATIONALSTATE, verbose_name="OperationalState", max_length=256,
-                                 editable=True, default='inactive')
-    adminstate = models.CharField(choices=ADMINISTRATIVE_STATE, default='disabled', verbose_name="AdministrativeState",
-                                           max_length=64, editable=True)
-
-    def __init__(self, *args, **kwargs):
-        super(ServiceSpoke, self).__init__(*args, **kwargs)
-
-    def __unicode__(self):  return u'%s' % (self.name)
-
-class VnodGlobalService(Service):
-
-    class Meta:
-        app_label = SERVICE_NAME
-        verbose_name = "Virtual Network On Demand Global Service"
-
-    TYPE = (
-        ('eline', SERVICE_NAME_ELINE_VERBOSE),
-        ('elan', SERVICE_NAME_ELAN_VERBOSE),
-        ('etree', SERVICE_NAME_ETREE_VERBOSE),
-    )
-
-    OPERATIONALSTATE = (
-        ('active', 'Active'),
-        ('inactive', 'Inactive')
-    )
-
-    ADMINISTRATIVESTATE = (
-        ('disabled', 'Disabled'),
-        ('activationrequested', 'ActivationRequested'),
-        ('enabled', 'Enabled'),
-        ('invalid', 'Invalid'),
-        ('deactivationrequested', 'DeactivationRequested')
-    )
-
-    servicehandle = models.CharField(unique=True, verbose_name="Servicehandle", max_length=64, editable=True)
-    vlanid = models.CharField(verbose_name="Vlanid", max_length=64, editable=True)
-    type = models.CharField(choices=TYPE, verbose_name="Type", max_length=256, editable=True)
-
-    metronetworkroottomultipoint = models.ForeignKey(NetworkEdgeToMultipointConnection,
-                            related_name='EtreeService',
-                            verbose_name="EtreeService",
-                            null=True,
-                            editable=True,
-                            on_delete=models.CASCADE)
-
-    metronetworkmultipoint = models.ForeignKey(NetworkMultipointToMultipointConnection,
-                                                     related_name='ElanService',
-                                                     verbose_name="ElanService",
-                                                     null=True,
-                                                     editable=True,
-                                                     on_delete=models.CASCADE)
-
-    metronetworkpointtopoint = models.ForeignKey(NetworkEdgeToEdgePointConnection,
-                                               related_name='ElineService',
-                                               verbose_name="ElineService",
-                                               null=True,
-                                               editable=True,
-                                               on_delete=models.CASCADE)
-
-    operstate = models.CharField(choices=OPERATIONALSTATE, verbose_name="OperationalState", max_length=256,
-                                 editable=True)
-
-    adminstate = models.CharField(choices=ADMINISTRATIVESTATE, verbose_name="AdministrativeState", max_length=256,
-                                  editable=True, default='enabled')
-
-    spokes = models.ManyToManyField(ServiceSpoke,
-                                 related_name='ServiceSpokes',
-                                 verbose_name="Spokes",
-                                 editable=True)
-
-    bandwidthProfile = models.ForeignKey(BandwidthProfile,
-                                               related_name='BandwidthProfile',
-                                               verbose_name="BandwidthProfile",
-                                               editable=True,
-                                               on_delete=models.CASCADE)
-
-    def __init__(self, *args, **kwargs):
-        super(VnodGlobalService, self).__init__(*args, **kwargs)
-
-
-class UserNetworkInterface(PlCoreBase):
-
-    class Meta:
-        app_label = METRONETWORK_KIND
-        verbose_name = "User Network Interface"
-
-    id = models.AutoField(verbose_name="id", primary_key=True, editable=False)
-    enabled = models.IntegerField(verbose_name="State of UNI", editable=True)
-    capacity = models.IntegerField(verbose_name="UNI Capacity", editable=True)
-    bw_used = models.IntegerField(verbose_name="UNI bandwidth used", editable=True)
-    vlanIds = models.CharField(verbose_name="VlanIds in this UNI", max_length=256, editable=True)
-    location = models.CharField(verbose_name="Location", max_length=256, editable=True, blank=True)
-    latlng = models.CharField(verbose_name="Latitude/Longitude", max_length=50, editable=True, blank=True)
-    name = models.CharField(unique=True, verbose_name="Name", max_length=256, editable=True)
-
-    def __init__(self, *args, **kwargs):
-        super(UserNetworkInterface, self).__init__(*args, **kwargs)
-
-    def __unicode__(self):  return u'%s' % (self.name)
-
-    def save(self, *args, **kwargs):
-
-        if self.latlng:
-            try:
-                latlng_value = getattr(self, 'latlng').strip()
-                if (latlng_value.startswith('[') and latlng_value.endswith(']') and latlng_value.index(',') > 0):
-                    lat = latlng_value[1: latlng_value.index(',')].strip()
-                    lng = latlng_value[latlng_value.index(',') + 1: len(latlng_value) - 1].strip()
-
-                    # If lat and lng are not floats, the code below should result in an error.
-                    lat_validation = float(lat)
-                    lng_validation = float(lng)
-                else:
-                    raise ValueError("The lat/lng value is not formatted correctly.")
-            except:
-                raise ValueError("The lat/lng value is not formatted correctly.")
-
-        super(UserNetworkInterface, self).save(*args, **kwargs)
\ No newline at end of file