mirror of
https://github.com/netbox-community/netbox.git
synced 2025-07-19 09:53:34 -06:00
Update connected_endpoint serializer field to support multiple objects
This commit is contained in:
parent
3a461d0279
commit
4c51dbba80
@ -51,32 +51,64 @@ class LinkTerminationSerializer(serializers.ModelSerializer):
|
|||||||
return obj._occupied
|
return obj._occupied
|
||||||
|
|
||||||
|
|
||||||
class ConnectedEndpointSerializer(serializers.ModelSerializer):
|
# class ConnectedEndpointSerializer(serializers.ModelSerializer):
|
||||||
connected_endpoint_type = serializers.SerializerMethodField(read_only=True)
|
# """
|
||||||
connected_endpoint = serializers.SerializerMethodField(read_only=True)
|
# Legacy serializer for pre-v3.3 connections
|
||||||
connected_endpoint_reachable = serializers.SerializerMethodField(read_only=True)
|
# """
|
||||||
|
# connected_endpoint_type = serializers.SerializerMethodField(read_only=True)
|
||||||
|
# connected_endpoint = serializers.SerializerMethodField(read_only=True)
|
||||||
|
# connected_endpoint_reachable = serializers.SerializerMethodField(read_only=True)
|
||||||
|
#
|
||||||
|
# def get_connected_endpoint_type(self, obj):
|
||||||
|
# if obj._path is not None and obj._path.destination is not None:
|
||||||
|
# return f'{obj._path.destination._meta.app_label}.{obj._path.destination._meta.model_name}'
|
||||||
|
# return None
|
||||||
|
#
|
||||||
|
# @swagger_serializer_method(serializer_or_field=serializers.DictField)
|
||||||
|
# def get_connected_endpoint(self, obj):
|
||||||
|
# """
|
||||||
|
# Return the appropriate serializer for the type of connected object.
|
||||||
|
# """
|
||||||
|
# if obj._path is not None and obj._path.destination is not None:
|
||||||
|
# serializer = get_serializer_for_model(obj._path.destination, prefix='Nested')
|
||||||
|
# context = {'request': self.context['request']}
|
||||||
|
# return serializer(obj._path.destination, context=context).data
|
||||||
|
# return None
|
||||||
|
#
|
||||||
|
# @swagger_serializer_method(serializer_or_field=serializers.BooleanField)
|
||||||
|
# def get_connected_endpoint_reachable(self, obj):
|
||||||
|
# if obj._path is not None:
|
||||||
|
# return obj._path.is_active
|
||||||
|
# return None
|
||||||
|
|
||||||
def get_connected_endpoint_type(self, obj):
|
|
||||||
if obj._path is not None and obj._path.destination is not None:
|
class ConnectedEndpointsSerializer(serializers.ModelSerializer):
|
||||||
return f'{obj._path.destination._meta.app_label}.{obj._path.destination._meta.model_name}'
|
"""
|
||||||
return None
|
Legacy serializer for pre-v3.3 connections
|
||||||
|
"""
|
||||||
|
connected_endpoints_type = serializers.SerializerMethodField(read_only=True)
|
||||||
|
connected_endpoints = serializers.SerializerMethodField(read_only=True)
|
||||||
|
connected_endpoints_reachable = serializers.SerializerMethodField(read_only=True)
|
||||||
|
|
||||||
|
def get_connected_endpoints_type(self, obj):
|
||||||
|
endpoints = obj.connected_endpoints
|
||||||
|
if endpoints:
|
||||||
|
return f'{endpoints[0]._meta.app_label}.{endpoints[0]._meta.model_name}'
|
||||||
|
|
||||||
@swagger_serializer_method(serializer_or_field=serializers.DictField)
|
@swagger_serializer_method(serializer_or_field=serializers.DictField)
|
||||||
def get_connected_endpoint(self, obj):
|
def get_connected_endpoints(self, obj):
|
||||||
"""
|
"""
|
||||||
Return the appropriate serializer for the type of connected object.
|
Return the appropriate serializer for the type of connected object.
|
||||||
"""
|
"""
|
||||||
if obj._path is not None and obj._path.destination is not None:
|
endpoints = obj.connected_endpoints
|
||||||
serializer = get_serializer_for_model(obj._path.destination, prefix='Nested')
|
if endpoints:
|
||||||
|
serializer = get_serializer_for_model(endpoints[0], prefix='Nested')
|
||||||
context = {'request': self.context['request']}
|
context = {'request': self.context['request']}
|
||||||
return serializer(obj._path.destination, context=context).data
|
return serializer(endpoints, many=True, context=context).data
|
||||||
return None
|
|
||||||
|
|
||||||
@swagger_serializer_method(serializer_or_field=serializers.BooleanField)
|
@swagger_serializer_method(serializer_or_field=serializers.BooleanField)
|
||||||
def get_connected_endpoint_reachable(self, obj):
|
def get_connected_endpoints_reachable(self, obj):
|
||||||
if obj._path is not None:
|
return obj._path and obj._path.is_complete and obj._path.is_active
|
||||||
return obj._path.is_active
|
|
||||||
return None
|
|
||||||
|
|
||||||
|
|
||||||
#
|
#
|
||||||
@ -659,7 +691,7 @@ class DeviceNAPALMSerializer(serializers.Serializer):
|
|||||||
# Device components
|
# Device components
|
||||||
#
|
#
|
||||||
|
|
||||||
class ConsoleServerPortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointSerializer):
|
class ConsoleServerPortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointsSerializer):
|
||||||
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:consoleserverport-detail')
|
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:consoleserverport-detail')
|
||||||
device = NestedDeviceSerializer()
|
device = NestedDeviceSerializer()
|
||||||
module = ComponentNestedModuleSerializer(
|
module = ComponentNestedModuleSerializer(
|
||||||
@ -682,12 +714,12 @@ class ConsoleServerPortSerializer(NetBoxModelSerializer, LinkTerminationSerializ
|
|||||||
model = ConsoleServerPort
|
model = ConsoleServerPort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'speed', 'description',
|
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'speed', 'description',
|
||||||
'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoint', 'connected_endpoint_type',
|
'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoints', 'connected_endpoints_type',
|
||||||
'connected_endpoint_reachable', 'tags', 'custom_fields', 'created', 'last_updated', '_occupied',
|
'connected_endpoints_reachable', 'tags', 'custom_fields', 'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class ConsolePortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointSerializer):
|
class ConsolePortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointsSerializer):
|
||||||
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:consoleport-detail')
|
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:consoleport-detail')
|
||||||
device = NestedDeviceSerializer()
|
device = NestedDeviceSerializer()
|
||||||
module = ComponentNestedModuleSerializer(
|
module = ComponentNestedModuleSerializer(
|
||||||
@ -710,12 +742,12 @@ class ConsolePortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, Co
|
|||||||
model = ConsolePort
|
model = ConsolePort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'speed', 'description',
|
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'speed', 'description',
|
||||||
'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoint', 'connected_endpoint_type',
|
'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoints', 'connected_endpoints_type',
|
||||||
'connected_endpoint_reachable', 'tags', 'custom_fields', 'created', 'last_updated', '_occupied',
|
'connected_endpoints_reachable', 'tags', 'custom_fields', 'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class PowerOutletSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointSerializer):
|
class PowerOutletSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointsSerializer):
|
||||||
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:poweroutlet-detail')
|
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:poweroutlet-detail')
|
||||||
device = NestedDeviceSerializer()
|
device = NestedDeviceSerializer()
|
||||||
module = ComponentNestedModuleSerializer(
|
module = ComponentNestedModuleSerializer(
|
||||||
@ -744,13 +776,13 @@ class PowerOutletSerializer(NetBoxModelSerializer, LinkTerminationSerializer, Co
|
|||||||
model = PowerOutlet
|
model = PowerOutlet
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'power_port', 'feed_leg',
|
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'power_port', 'feed_leg',
|
||||||
'description', 'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoint',
|
'description', 'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoints',
|
||||||
'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields', 'created',
|
'connected_endpoints_type', 'connected_endpoints_reachable', 'tags', 'custom_fields', 'created',
|
||||||
'last_updated', '_occupied',
|
'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class PowerPortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointSerializer):
|
class PowerPortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointsSerializer):
|
||||||
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:powerport-detail')
|
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:powerport-detail')
|
||||||
device = NestedDeviceSerializer()
|
device = NestedDeviceSerializer()
|
||||||
module = ComponentNestedModuleSerializer(
|
module = ComponentNestedModuleSerializer(
|
||||||
@ -768,13 +800,13 @@ class PowerPortSerializer(NetBoxModelSerializer, LinkTerminationSerializer, Conn
|
|||||||
model = PowerPort
|
model = PowerPort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw',
|
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw',
|
||||||
'description', 'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoint',
|
'description', 'mark_connected', 'cable', 'link_peer', 'link_peer_type', 'connected_endpoints',
|
||||||
'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields', 'created',
|
'connected_endpoints_type', 'connected_endpoints_reachable', 'tags', 'custom_fields', 'created',
|
||||||
'last_updated', '_occupied',
|
'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class InterfaceSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointSerializer):
|
class InterfaceSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointsSerializer):
|
||||||
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:interface-detail')
|
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:interface-detail')
|
||||||
device = NestedDeviceSerializer()
|
device = NestedDeviceSerializer()
|
||||||
module = ComponentNestedModuleSerializer(
|
module = ComponentNestedModuleSerializer(
|
||||||
@ -814,8 +846,8 @@ class InterfaceSerializer(NetBoxModelSerializer, LinkTerminationSerializer, Conn
|
|||||||
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'enabled', 'parent', 'bridge', 'lag',
|
'id', 'url', 'display', 'device', 'module', 'name', 'label', 'type', 'enabled', 'parent', 'bridge', 'lag',
|
||||||
'mtu', 'mac_address', 'speed', 'duplex', 'wwn', 'mgmt_only', 'description', 'mode', 'rf_role', 'rf_channel',
|
'mtu', 'mac_address', 'speed', 'duplex', 'wwn', 'mgmt_only', 'description', 'mode', 'rf_role', 'rf_channel',
|
||||||
'rf_channel_frequency', 'rf_channel_width', 'tx_power', 'untagged_vlan', 'tagged_vlans', 'mark_connected',
|
'rf_channel_frequency', 'rf_channel_width', 'tx_power', 'untagged_vlan', 'tagged_vlans', 'mark_connected',
|
||||||
'cable', 'wireless_link', 'link_peer', 'link_peer_type', 'wireless_lans', 'vrf', 'connected_endpoint',
|
'cable', 'wireless_link', 'link_peer', 'link_peer_type', 'wireless_lans', 'vrf', 'connected_endpoints',
|
||||||
'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields', 'created',
|
'connected_endpoints_type', 'connected_endpoints_reachable', 'tags', 'custom_fields', 'created',
|
||||||
'last_updated', 'count_ipaddresses', 'count_fhrp_groups', '_occupied',
|
'last_updated', 'count_ipaddresses', 'count_fhrp_groups', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
@ -1092,7 +1124,7 @@ class PowerPanelSerializer(NetBoxModelSerializer):
|
|||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class PowerFeedSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointSerializer):
|
class PowerFeedSerializer(NetBoxModelSerializer, LinkTerminationSerializer, ConnectedEndpointsSerializer):
|
||||||
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:powerfeed-detail')
|
url = serializers.HyperlinkedIdentityField(view_name='dcim-api:powerfeed-detail')
|
||||||
power_panel = NestedPowerPanelSerializer()
|
power_panel = NestedPowerPanelSerializer()
|
||||||
rack = NestedRackSerializer(
|
rack = NestedRackSerializer(
|
||||||
@ -1123,6 +1155,6 @@ class PowerFeedSerializer(NetBoxModelSerializer, LinkTerminationSerializer, Conn
|
|||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'display', 'power_panel', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage',
|
'id', 'url', 'display', 'power_panel', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage',
|
||||||
'amperage', 'max_utilization', 'comments', 'mark_connected', 'cable', 'link_peer', 'link_peer_type',
|
'amperage', 'max_utilization', 'comments', 'mark_connected', 'cable', 'link_peer', 'link_peer_type',
|
||||||
'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields',
|
'connected_endpoints', 'connected_endpoints_type', 'connected_endpoints_reachable', 'tags', 'custom_fields',
|
||||||
'created', 'last_updated', '_occupied',
|
'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
@ -93,7 +93,7 @@ class PassThroughPortMixin(object):
|
|||||||
Return all CablePaths which traverse a given pass-through port.
|
Return all CablePaths which traverse a given pass-through port.
|
||||||
"""
|
"""
|
||||||
obj = get_object_or_404(self.queryset, pk=pk)
|
obj = get_object_or_404(self.queryset, pk=pk)
|
||||||
cablepaths = CablePath.objects.filter(_nodes__contains=obj).prefetch_related('origin', 'destination')
|
cablepaths = CablePath.objects.filter(_nodes__contains=obj)
|
||||||
serializer = serializers.CablePathSerializer(cablepaths, context={'request': request}, many=True)
|
serializer = serializers.CablePathSerializer(cablepaths, context={'request': request}, many=True)
|
||||||
|
|
||||||
return Response(serializer.data)
|
return Response(serializer.data)
|
||||||
|
@ -224,13 +224,13 @@ class PathEndpoint(models.Model):
|
|||||||
return self._path
|
return self._path
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def connected_endpoint(self):
|
def connected_endpoints(self):
|
||||||
"""
|
"""
|
||||||
Caching accessor for the attached CablePath's destination (if any)
|
Caching accessor for the attached CablePath's destination (if any)
|
||||||
"""
|
"""
|
||||||
if not hasattr(self, '_connected_endpoint'):
|
if not hasattr(self, '_connected_endpoints'):
|
||||||
self._connected_endpoint = self._path.get_destination()
|
self._connected_endpoints = self._path.get_destination() if self._path else []
|
||||||
return self._connected_endpoint
|
return self._connected_endpoints
|
||||||
|
|
||||||
|
|
||||||
#
|
#
|
||||||
|
@ -45,7 +45,7 @@ class Mixins:
|
|||||||
device=peer_device,
|
device=peer_device,
|
||||||
name='Peer Termination'
|
name='Peer Termination'
|
||||||
)
|
)
|
||||||
cable = Cable(termination_a=obj, b_terminations=[peer_obj], label='Cable 1')
|
cable = Cable(a_terminations=[obj], b_terminations=[peer_obj], label='Cable 1')
|
||||||
cable.save()
|
cable.save()
|
||||||
|
|
||||||
self.add_permissions(f'dcim.view_{self.model._meta.model_name}')
|
self.add_permissions(f'dcim.view_{self.model._meta.model_name}')
|
||||||
|
@ -2771,7 +2771,7 @@ class PathTraceView(generic.ObjectView):
|
|||||||
|
|
||||||
# Otherwise, find all CablePaths which traverse the specified object
|
# Otherwise, find all CablePaths which traverse the specified object
|
||||||
else:
|
else:
|
||||||
related_paths = CablePath.objects.filter(_nodes__contains=instance).prefetch_related('origin')
|
related_paths = CablePath.objects.filter(_nodes__contains=instance)
|
||||||
# Check for specification of a particular path (when tracing pass-through ports)
|
# Check for specification of a particular path (when tracing pass-through ports)
|
||||||
try:
|
try:
|
||||||
path_id = int(request.GET.get('cablepath_id'))
|
path_id = int(request.GET.get('cablepath_id'))
|
||||||
|
Loading…
Reference in New Issue
Block a user