Validate primary and secondary nodes for iads network

cherry-pick from ab64655f05c6085cc21f5e45cb0e06aca66365ca
This commit is contained in:
RndName 2022-11-17 19:55:28 +01:00
parent 9ba717fd82
commit bfed69573f
3 changed files with 44 additions and 33 deletions

View File

@ -34,8 +34,13 @@ class IadsConnectionJs(BaseModel):
iads_connections = [] iads_connections = []
tgo = network_node.group.ground_object tgo = network_node.group.ground_object
for id, connection in network_node.connections.items(): for id, connection in network_node.connections.items():
if connection.ground_object.is_friendly(True) != tgo.is_friendly(True): if (
continue # Skip connections which are not from same coalition not connection.iads_role.is_secondary_node
or connection.ground_object.is_friendly(True) != tgo.is_friendly(True)
):
# Skip connections to non secondary nodes (for example PD)
# and connections which are not from same coalition
continue
iads_connections.append( iads_connections.append(
IadsConnectionJs( IadsConnectionJs(
id=id, id=id,
@ -67,10 +72,8 @@ class IadsNetworkJs(BaseModel):
@staticmethod @staticmethod
def from_network(network: IadsNetwork) -> IadsNetworkJs: def from_network(network: IadsNetwork) -> IadsNetworkJs:
iads_connections = [] iads_connections = []
for connection in network.nodes: for primary_node in network.nodes:
if not connection.group.iads_role.participate: iads_connections.extend(IadsConnectionJs.connections_for_node(primary_node))
continue # Skip
iads_connections.extend(IadsConnectionJs.connections_for_node(connection))
return IadsNetworkJs( return IadsNetworkJs(
advanced=network.advanced_iads, connections=iads_connections advanced=network.advanced_iads, connections=iads_connections
) )

View File

@ -79,10 +79,10 @@ class IadsNetworkNode:
def __str__(self) -> str: def __str__(self) -> str:
return self.group.group_name return self.group.group_name
def add_connection_for_tgo(self, tgo: TheaterGroundObject) -> None: def add_secondary_node(self, tgo: TheaterGroundObject) -> None:
"""Add all possible connections for the given TGO to the node""" """Add all possible connections for the given secondary node to this node"""
for group in tgo.groups: for group in tgo.groups:
if isinstance(group, IadsGroundGroup) and group.iads_role.participate: if isinstance(group, IadsGroundGroup) and group.iads_role.is_secondary_node:
self.add_connection_for_group(group) self.add_connection_for_group(group)
def add_connection_for_group(self, group: IadsGroundGroup) -> None: def add_connection_for_group(self, group: IadsGroundGroup) -> None:
@ -193,34 +193,27 @@ class IadsNetwork:
for primary_node in primary_nodes: for primary_node in primary_nodes:
self.update_tgo(primary_node, events) self.update_tgo(primary_node, events)
def node_for_group(self, group: IadsGroundGroup) -> IadsNetworkNode:
"""Get existing node from the iads network or create a new node"""
for cn in self.nodes:
if cn.group == group:
return cn
node = IadsNetworkNode(group)
self.nodes.append(node)
return node
def node_for_tgo(self, tgo: TheaterGroundObject) -> Optional[IadsNetworkNode]: def node_for_tgo(self, tgo: TheaterGroundObject) -> Optional[IadsNetworkNode]:
"""Get existing node from the iads network or create a new node""" """Create Primary node for the TGO or return existing one"""
for cn in self.nodes: for cn in self.nodes:
if cn.group.ground_object == tgo: if cn.group.ground_object == tgo:
return cn return cn
return self._new_node_for_tgo(tgo) return self._new_node_for_tgo(tgo)
def _new_node_for_tgo(self, tgo: TheaterGroundObject) -> Optional[IadsNetworkNode]: def _new_node_for_tgo(self, tgo: TheaterGroundObject) -> Optional[IadsNetworkNode]:
# Create new connection_node if none exists """Create a new primary node for the given TGO.
Will return None if the given TGO is not capable of being a primary node.
This will also add any PointDefense of this TGO to the primary node"""
node: Optional[IadsNetworkNode] = None node: Optional[IadsNetworkNode] = None
for group in tgo.groups: for group in tgo.groups:
# TODO Cleanup
if isinstance(group, IadsGroundGroup): if isinstance(group, IadsGroundGroup):
# The first IadsGroundGroup is always the primary Group # The first IadsGroundGroup is always the primary Group
if not node and group.iads_role.participate: if node is None and group.iads_role.is_primary_node:
# Primary Node # Create Primary Node
node = self.node_for_group(group) node = IadsNetworkNode(group)
elif node and group.iads_role == IadsRole.POINT_DEFENSE: self.nodes.append(node)
elif node is not None and group.iads_role == IadsRole.POINT_DEFENSE:
# Point Defense Node for this TGO # Point Defense Node for this TGO
node.add_connection_for_group(group) node.add_connection_for_group(group)
@ -282,7 +275,13 @@ class IadsNetwork:
connections = self.iads_config[primary_node] connections = self.iads_config[primary_node]
for secondary_node in connections: for secondary_node in connections:
try: try:
node.add_connection_for_tgo(self.ground_objects[secondary_node]) nearby_go = self.ground_objects[secondary_node]
if IadsRole.for_category(nearby_go.category).is_secondary_node:
node.add_secondary_node(nearby_go)
else:
logging.error(
f"IADS: {secondary_node} is not a valid secondary node"
)
except KeyError: except KeyError:
logging.exception( logging.exception(
f"IADS: No ground object found for connection {secondary_node}" f"IADS: No ground object found for connection {secondary_node}"
@ -298,15 +297,11 @@ class IadsNetwork:
continue continue
nearby_iads_role = IadsRole.for_category(nearby_go.category) nearby_iads_role = IadsRole.for_category(nearby_go.category)
if ( if (
nearby_iads_role nearby_iads_role.is_secondary_node
in [
IadsRole.POWER_SOURCE,
IadsRole.CONNECTION_NODE,
]
and nearby_go.position.distance_to_point(primary_tgo.position) and nearby_go.position.distance_to_point(primary_tgo.position)
<= nearby_iads_role.connection_range.meters <= nearby_iads_role.connection_range.meters
): ):
node.add_connection_for_tgo(nearby_go) node.add_secondary_node(nearby_go)
def initialize_network_from_range(self) -> None: def initialize_network_from_range(self) -> None:
"""Initialize the IADS Network by range""" """Initialize the IADS Network by range"""

View File

@ -79,3 +79,16 @@ class IadsRole(Enum):
IadsRole.NO_BEHAVIOR, IadsRole.NO_BEHAVIOR,
IadsRole.POINT_DEFENSE, IadsRole.POINT_DEFENSE,
] ]
@property
def is_primary_node(self) -> bool:
return self in [
IadsRole.SAM,
IadsRole.SAM_AS_EWR,
IadsRole.EWR,
IadsRole.COMMAND_CENTER,
]
@property
def is_secondary_node(self) -> bool:
return self in [IadsRole.CONNECTION_NODE, IadsRole.POWER_SOURCE]