Skip to content

Commit

Permalink
Support for multiple service chains between same pair of networks
Browse files Browse the repository at this point in the history
Added schema transformer support for multiple service chains
between same pair of networks. See the bug for limitations.

Change-Id: I3fa84219ad30c991398680a06d03226b0ad7edcf
Closes-Bug: 1505023
  • Loading branch information
Sachin Bansal committed Nov 4, 2015
1 parent 5f8f6b4 commit 7769a77
Show file tree
Hide file tree
Showing 2 changed files with 115 additions and 93 deletions.
46 changes: 42 additions & 4 deletions src/config/schema-transformer/config_db.py
Expand Up @@ -194,6 +194,7 @@ def __init__(self, name, obj=None, acl_dict=None):
self.routing_instances = set()
self.acl = None
self.dynamic_acl = None
self.multi_policy_service_chains_enabled = None
for acl in self.obj.get_access_control_lists() or []:
if acl_dict:
acl_obj = acl_dict[acl['uuid']]
Expand Down Expand Up @@ -234,6 +235,7 @@ def __init__(self, name, obj=None, acl_dict=None):
self._default_ri_name = ':'.join(default_ri_fq_name)
self.update(self.obj)
self.update_multiple_refs('virtual_machine_interface', self.obj)
self.multi_policy_service_chains_status_changed = False
# end __init__

def update(self, obj=None):
Expand Down Expand Up @@ -268,8 +270,37 @@ def update(self, obj=None):
) or VirtualNetworkType()
self.set_properties(prop)
self.set_route_target_list(self.obj.get_route_target_list())
mpsce = self.obj.get_multi_policy_service_chains_enabled()
if mpsce != self.multi_policy_service_chains_enabled:
self.multi_policy_service_chains_enabled = mpsce
self.multi_policy_service_chains_status_changed = True
# end update

def check_multi_policy_service_chain_status(self):
if not self.multi_policy_service_chains_status_changed:
return
self.multi_policy_service_chains_status_changed = False
for sc_list in self.service_chains.values():
for sc in sc_list:
if sc is None or not sc.created:
continue
if sc.left_vn == self.name:
si_name = sc.service_list[0]
elif sc.right_vn == self.name:
sc_name = sc.service_list[-1]
else:
continue
primary_ri = self.get_primary_routing_instance()
service_ri_name = self.get_service_name(sc.name, si_name)
service_ri = RoutingInstanceST.get(service_ri_name)
if (self.multi_policy_service_chains_enabled and
service_ri_name in primary_ri.connections):
primary_ri.delete_connection(service_ri)
elif (not self.multi_policy_service_chains_enabled and
service_ri_name not in primary_ri.connections):
primary_ri.add_connection(service_ri)
# end check_multi_policy_service_chain_status

def delete_obj(self):
for policy_name in self.network_policys:
policy = NetworkPolicyST.get(policy_name)
Expand Down Expand Up @@ -1165,6 +1196,7 @@ def evaluate(self):

self.update_route_table()
self.update_pnf_presence()
self.check_multi_policy_service_chain_status()
# end evaluate

def get_prefixes(self, ip_version):
Expand Down Expand Up @@ -2184,18 +2216,23 @@ def _create(self, si_info):
self.log_error("vn1_obj or vn2_obj is None")
return

service_ri2 = vn1_obj.get_primary_routing_instance()
if not vn1_obj.multi_policy_service_chains_enabled:
service_ri2 = vn1_obj.get_primary_routing_instance()
if service_ri2 is None:
self.log_error("primary ri is None for " + self.left_vn)
return
first_node = True
for service in self.service_list:
service_name1 = vn1_obj.get_service_name(self.name, service)
service_name2 = vn2_obj.get_service_name(self.name, service)
has_pnf = (si_info[service]['virtualization_type'] == 'physical-device')
ri_obj = RoutingInstanceST.create(service_name1, vn1_obj, has_pnf)
service_ri1 = RoutingInstanceST.locate(service_name1, ri_obj)
if service_ri1 is None or service_ri2 is None:
if service_ri1 is None:
self.log_error("service_ri1 or service_ri2 is None")
return
service_ri2.add_connection(service_ri1)
if service_ri2 is not None:
service_ri2.add_connection(service_ri1)
ri_obj = RoutingInstanceST.create(service_name2, vn2_obj, has_pnf)
service_ri2 = RoutingInstanceST.locate(service_name2, ri_obj)
if service_ri2 is None:
Expand Down Expand Up @@ -2248,7 +2285,8 @@ def _create(self, si_info):
rt_list.add(vn2_obj.get_route_target())
service_ri2.update_route_target_list(rt_list, import_export='export')

service_ri2.add_connection(vn2_obj.get_primary_routing_instance())
if not vn2_obj.multi_policy_service_chains_enabled:
service_ri2.add_connection(vn2_obj.get_primary_routing_instance())

if not transparent and len(self.service_list) == 1:
for vn in VirtualNetworkST.values():
Expand Down

0 comments on commit 7769a77

Please sign in to comment.