diff --git a/gso/workflows/iptrunk/modify_trunk_interface.py b/gso/workflows/iptrunk/modify_trunk_interface.py index 6d82090c56d539c3456344ec6c08b1580d33dcf4..e947fd52b4569506d452629b3d2a1fd547468ef1 100644 --- a/gso/workflows/iptrunk/modify_trunk_interface.py +++ b/gso/workflows/iptrunk/modify_trunk_interface.py @@ -216,6 +216,29 @@ def check_ip_trunk_lldp(subscription: Iptrunk, callback_route: str) -> State: return {"subscription": subscription} +def update_side_members(subscription: Iptrunk, side_index: int, new_members: list[dict]) -> None: + """Update the AE members for a given side without removing unchanged members.""" + # Prepare a dictionary for quick lookup of existing members by name + current_members = subscription.iptrunk.iptrunk_sides[side_index].iptrunk_side_ae_members + existing_members_dict = {member.interface_name: member for member in current_members} + + # Iterate over new members and update or add them + for new_member in new_members: + interface_name = new_member["interface_name"] + if interface_name in existing_members_dict: + # Member exists, update details but keep the same subscription ID + existing_member = existing_members_dict[interface_name] + existing_member.interface_description = new_member["interface_description"] + else: + # New member, create a new subscription ID + current_members.append(IptrunkInterfaceBlock.new(subscription_id=uuid4(), **new_member)) + + # Remove members that are no longer in the new members list + subscription.iptrunk.iptrunk_sides[side_index].iptrunk_side_ae_members = [ + member for member in current_members if member.interface_name in [m["interface_name"] for m in new_members] + ] + + @step("Update subscription") def modify_iptrunk_subscription( subscription: Iptrunk, @@ -242,12 +265,16 @@ def modify_iptrunk_subscription( for side in subscription.iptrunk.iptrunk_sides ] removed_ae_members = [] - + # Compare previous and current members to determine which ones were removed for side_index in range(2): previous_members = previous_ae_members[side_index] current_members = side_a_ae_members if side_index == 0 else side_b_ae_members - removed_ae_members.append([ae_member for ae_member in previous_members if ae_member not in current_members]) - + removed_ae_members.append([ + ae_member + for ae_member in previous_members + if ae_member["interface_name"] not in [m["interface_name"] for m in current_members] + ]) + # Update the subscription subscription.iptrunk.geant_s_sid = geant_s_sid subscription.iptrunk.iptrunk_description = iptrunk_description subscription.iptrunk.iptrunk_type = iptrunk_type @@ -255,20 +282,9 @@ def modify_iptrunk_subscription( subscription.iptrunk.iptrunk_minimum_links = iptrunk_minimum_links subscription.iptrunk.iptrunk_sides[0].iptrunk_side_ae_geant_a_sid = side_a_ae_geant_a_sid - # Flush the old list of member interfaces - subscription.iptrunk.iptrunk_sides[0].iptrunk_side_ae_members.clear() - # And update the list to only include the new member interfaces - for member in side_a_ae_members: - subscription.iptrunk.iptrunk_sides[0].iptrunk_side_ae_members.append( - IptrunkInterfaceBlock.new(subscription_id=uuid4(), **member), - ) - + update_side_members(subscription, 0, side_a_ae_members) subscription.iptrunk.iptrunk_sides[1].iptrunk_side_ae_geant_a_sid = side_b_ae_geant_a_sid - subscription.iptrunk.iptrunk_sides[1].iptrunk_side_ae_members.clear() - for member in side_b_ae_members: - subscription.iptrunk.iptrunk_sides[1].iptrunk_side_ae_members.append( - IptrunkInterfaceBlock.new(subscription_id=uuid4(), **member), - ) + update_side_members(subscription, 1, side_b_ae_members) side_names = sorted([ subscription.iptrunk.iptrunk_sides[0].iptrunk_side_node.router_site.site_name,