Browse Source

Converted nested serializers to HyperlinkedModelSerializer

Jeremy Stretch 8 years ago
parent
commit
fa900d5dbb

+ 32 - 23
netbox/circuits/api/serializers.py

@@ -1,9 +1,9 @@
 from rest_framework import serializers
 from rest_framework import serializers
 
 
 from circuits.models import Provider, Circuit, CircuitTermination, CircuitType
 from circuits.models import Provider, Circuit, CircuitTermination, CircuitType
-from dcim.api.serializers import SiteNestedSerializer, NestedInterfaceSerializer
+from dcim.api.serializers import NestedSiteSerializer, ChildInterfaceSerializer
 from extras.api.serializers import CustomFieldSerializer
 from extras.api.serializers import CustomFieldSerializer
-from tenancy.api.serializers import TenantNestedSerializer
+from tenancy.api.serializers import NestedTenantSerializer
 
 
 
 
 #
 #
@@ -14,14 +14,17 @@ class ProviderSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 
 
     class Meta:
     class Meta:
         model = Provider
         model = Provider
-        fields = ['id', 'name', 'slug', 'asn', 'account', 'portal_url', 'noc_contact', 'admin_contact', 'comments',
+        fields = [
-                  'custom_fields']
+            'id', 'name', 'slug', 'asn', 'account', 'portal_url', 'noc_contact', 'admin_contact', 'comments',
+            'custom_fields',
+        ]
 
 
 
 
-class ProviderNestedSerializer(ProviderSerializer):
+class NestedProviderSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(ProviderSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = Provider
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -35,10 +38,11 @@ class CircuitTypeSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug']
         fields = ['id', 'name', 'slug']
 
 
 
 
-class CircuitTypeNestedSerializer(CircuitTypeSerializer):
+class NestedCircuitTypeSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(CircuitTypeSerializer.Meta):
+    class Meta:
-        pass
+        model = CircuitType
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -46,8 +50,8 @@ class CircuitTypeNestedSerializer(CircuitTypeSerializer):
 #
 #
 
 
 class CircuitTerminationSerializer(serializers.ModelSerializer):
 class CircuitTerminationSerializer(serializers.ModelSerializer):
-    site = SiteNestedSerializer()
+    site = NestedSiteSerializer()
-    interface = NestedInterfaceSerializer()
+    interface = ChildInterfaceSerializer()
 
 
     class Meta:
     class Meta:
         model = CircuitTermination
         model = CircuitTermination
@@ -58,27 +62,32 @@ class CircuitTerminationSerializer(serializers.ModelSerializer):
 # Circuits
 # Circuits
 #
 #
 
 
-
 class CircuitSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class CircuitSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    provider = ProviderNestedSerializer()
+    provider = NestedProviderSerializer()
-    type = CircuitTypeNestedSerializer()
+    type = NestedCircuitTypeSerializer()
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
 
 
     class Meta:
     class Meta:
         model = Circuit
         model = Circuit
-        fields = ['id', 'cid', 'provider', 'type', 'tenant', 'install_date', 'commit_rate', 'description', 'comments',
+        fields = [
-                  'custom_fields']
+            'id', 'cid', 'provider', 'type', 'tenant', 'install_date', 'commit_rate', 'description', 'comments',
+            'custom_fields',
+        ]
 
 
 
 
-class CircuitNestedSerializer(CircuitSerializer):
+class NestedCircuitSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(CircuitSerializer.Meta):
+    class Meta:
-        fields = ['id', 'cid']
+        model = Circuit
+        fields = ['id', 'url', 'cid']
 
 
 
 
+# TODO: Delete this
 class CircuitDetailSerializer(CircuitSerializer):
 class CircuitDetailSerializer(CircuitSerializer):
     terminations = CircuitTerminationSerializer(many=True)
     terminations = CircuitTerminationSerializer(many=True)
 
 
     class Meta(CircuitSerializer.Meta):
     class Meta(CircuitSerializer.Meta):
-        fields = ['id', 'cid', 'provider', 'type', 'tenant', 'install_date', 'commit_rate', 'description', 'comments',
+        fields = [
-                  'terminations', 'custom_fields']
+            'id', 'cid', 'provider', 'type', 'tenant', 'install_date', 'commit_rate', 'description', 'comments',
+            'terminations', 'custom_fields',
+        ]

+ 118 - 90
netbox/dcim/api/serializers.py

@@ -8,7 +8,7 @@ from dcim.models import (
     SUBDEVICE_ROLE_CHILD, SUBDEVICE_ROLE_PARENT,
     SUBDEVICE_ROLE_CHILD, SUBDEVICE_ROLE_PARENT,
 )
 )
 from extras.api.serializers import CustomFieldSerializer
 from extras.api.serializers import CustomFieldSerializer
-from tenancy.api.serializers import TenantNestedSerializer
+from tenancy.api.serializers import NestedTenantSerializer
 
 
 
 
 #
 #
@@ -16,19 +16,22 @@ from tenancy.api.serializers import TenantNestedSerializer
 #
 #
 
 
 class SiteSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class SiteSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
 
 
     class Meta:
     class Meta:
         model = Site
         model = Site
-        fields = ['id', 'name', 'slug', 'tenant', 'facility', 'asn', 'physical_address', 'shipping_address',
+        fields = [
-                  'contact_name', 'contact_phone', 'contact_email', 'comments', 'custom_fields', 'count_prefixes',
+            'id', 'name', 'slug', 'tenant', 'facility', 'asn', 'physical_address', 'shipping_address', 'contact_name',
-                  'count_vlans', 'count_racks', 'count_devices', 'count_circuits']
+            'contact_phone', 'contact_email', 'comments', 'custom_fields', 'count_prefixes', 'count_vlans',
+            'count_racks', 'count_devices', 'count_circuits',
+        ]
 
 
 
 
-class SiteNestedSerializer(SiteSerializer):
+class NestedSiteSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(SiteSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = Site
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -36,17 +39,18 @@ class SiteNestedSerializer(SiteSerializer):
 #
 #
 
 
 class RackGroupSerializer(serializers.ModelSerializer):
 class RackGroupSerializer(serializers.ModelSerializer):
-    site = SiteNestedSerializer()
+    site = NestedSiteSerializer()
 
 
     class Meta:
     class Meta:
         model = RackGroup
         model = RackGroup
         fields = ['id', 'name', 'slug', 'site']
         fields = ['id', 'name', 'slug', 'site']
 
 
 
 
-class RackGroupNestedSerializer(RackGroupSerializer):
+class NestedRackGroupSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(SiteSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = RackGroup
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -60,10 +64,11 @@ class RackRoleSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug', 'color']
         fields = ['id', 'name', 'slug', 'color']
 
 
 
 
-class RackRoleNestedSerializer(RackRoleSerializer):
+class NestedRackRoleSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(RackRoleSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = RackRole
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -72,21 +77,24 @@ class RackRoleNestedSerializer(RackRoleSerializer):
 
 
 
 
 class RackSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class RackSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    site = SiteNestedSerializer()
+    site = NestedSiteSerializer()
-    group = RackGroupNestedSerializer()
+    group = NestedRackGroupSerializer()
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
-    role = RackRoleNestedSerializer()
+    role = NestedRackRoleSerializer()
 
 
     class Meta:
     class Meta:
         model = Rack
         model = Rack
-        fields = ['id', 'name', 'facility_id', 'display_name', 'site', 'group', 'tenant', 'role', 'type', 'width',
+        fields = [
-                  'u_height', 'desc_units', 'comments', 'custom_fields']
+            'id', 'name', 'facility_id', 'display_name', 'site', 'group', 'tenant', 'role', 'type', 'width', 'u_height',
+            'desc_units', 'comments', 'custom_fields',
+        ]
 
 
 
 
-class RackNestedSerializer(RackSerializer):
+class NestedRackSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(RackSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'facility_id', 'display_name']
+        model = Rack
+        fields = ['id', 'url', 'name', 'display_name']
 
 
 
 
 class RackDetailSerializer(RackSerializer):
 class RackDetailSerializer(RackSerializer):
@@ -94,19 +102,21 @@ class RackDetailSerializer(RackSerializer):
     rear_units = serializers.SerializerMethodField()
     rear_units = serializers.SerializerMethodField()
 
 
     class Meta(RackSerializer.Meta):
     class Meta(RackSerializer.Meta):
-        fields = ['id', 'name', 'facility_id', 'display_name', 'site', 'group', 'tenant', 'role', 'type', 'width',
+        fields = [
-                  'u_height', 'desc_units', 'comments', 'custom_fields', 'front_units', 'rear_units']
+            'id', 'name', 'facility_id', 'display_name', 'site', 'group', 'tenant', 'role', 'type', 'width', 'u_height',
+            'desc_units', 'comments', 'custom_fields', 'front_units', 'rear_units',
+        ]
 
 
     def get_front_units(self, obj):
     def get_front_units(self, obj):
         units = obj.get_rack_units(face=RACK_FACE_FRONT)
         units = obj.get_rack_units(face=RACK_FACE_FRONT)
         for u in units:
         for u in units:
-            u['device'] = DeviceNestedSerializer(u['device']).data if u['device'] else None
+            u['device'] = NestedDeviceSerializer(u['device']).data if u['device'] else None
         return units
         return units
 
 
     def get_rear_units(self, obj):
     def get_rear_units(self, obj):
         units = obj.get_rack_units(face=RACK_FACE_REAR)
         units = obj.get_rack_units(face=RACK_FACE_REAR)
         for u in units:
         for u in units:
-            u['device'] = DeviceNestedSerializer(u['device']).data if u['device'] else None
+            u['device'] = NestedDeviceSerializer(u['device']).data if u['device'] else None
         return units
         return units
 
 
 
 
@@ -121,10 +131,11 @@ class ManufacturerSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug']
         fields = ['id', 'name', 'slug']
 
 
 
 
-class ManufacturerNestedSerializer(ManufacturerSerializer):
+class NestedManufacturerSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(ManufacturerSerializer.Meta):
+    class Meta:
-        pass
+        model = Manufacturer
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -132,15 +143,17 @@ class ManufacturerNestedSerializer(ManufacturerSerializer):
 #
 #
 
 
 class DeviceTypeSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class DeviceTypeSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    manufacturer = ManufacturerNestedSerializer()
+    manufacturer = NestedManufacturerSerializer()
     subdevice_role = serializers.SerializerMethodField()
     subdevice_role = serializers.SerializerMethodField()
     instance_count = serializers.IntegerField(source='instances.count', read_only=True)
     instance_count = serializers.IntegerField(source='instances.count', read_only=True)
 
 
     class Meta:
     class Meta:
         model = DeviceType
         model = DeviceType
-        fields = ['id', 'manufacturer', 'model', 'slug', 'part_number', 'u_height', 'is_full_depth',
+        fields = [
-                  'interface_ordering', 'is_console_server', 'is_pdu', 'is_network_device', 'subdevice_role',
+            'id', 'manufacturer', 'model', 'slug', 'part_number', 'u_height', 'is_full_depth', 'interface_ordering',
-                  'comments', 'custom_fields', 'instance_count']
+            'is_console_server', 'is_pdu', 'is_network_device', 'subdevice_role', 'comments', 'custom_fields',
+            'instance_count',
+        ]
 
 
     def get_subdevice_role(self, obj):
     def get_subdevice_role(self, obj):
         return {
         return {
@@ -150,47 +163,55 @@ class DeviceTypeSerializer(CustomFieldSerializer, serializers.ModelSerializer):
         }[obj.subdevice_role]
         }[obj.subdevice_role]
 
 
 
 
-class DeviceTypeNestedSerializer(DeviceTypeSerializer):
+class NestedDeviceTypeSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(DeviceTypeSerializer.Meta):
+    class Meta:
-        fields = ['id', 'manufacturer', 'model', 'slug']
+        model = DeviceType
+        fields = ['id', 'url', 'manufacturer', 'model', 'slug']
 
 
 
 
-class ConsolePortTemplateNestedSerializer(serializers.ModelSerializer):
+class ConsolePortTemplateSerializer(serializers.ModelSerializer):
 
 
     class Meta:
     class Meta:
         model = ConsolePortTemplate
         model = ConsolePortTemplate
         fields = ['id', 'name']
         fields = ['id', 'name']
 
 
 
 
-class ConsoleServerPortTemplateNestedSerializer(serializers.ModelSerializer):
+class ConsoleServerPortTemplateSerializer(serializers.ModelSerializer):
 
 
     class Meta:
     class Meta:
         model = ConsoleServerPortTemplate
         model = ConsoleServerPortTemplate
         fields = ['id', 'name']
         fields = ['id', 'name']
 
 
 
 
-class PowerPortTemplateNestedSerializer(serializers.ModelSerializer):
+class PowerPortTemplateSerializer(serializers.ModelSerializer):
 
 
     class Meta:
     class Meta:
         model = PowerPortTemplate
         model = PowerPortTemplate
         fields = ['id', 'name']
         fields = ['id', 'name']
 
 
 
 
-class PowerOutletTemplateNestedSerializer(serializers.ModelSerializer):
+class PowerOutletTemplateSerializer(serializers.ModelSerializer):
 
 
     class Meta:
     class Meta:
         model = PowerOutletTemplate
         model = PowerOutletTemplate
         fields = ['id', 'name']
         fields = ['id', 'name']
 
 
 
 
-class InterfaceTemplateNestedSerializer(serializers.ModelSerializer):
+class InterfaceTemplateSerializer(serializers.ModelSerializer):
 
 
     class Meta:
     class Meta:
         model = InterfaceTemplate
         model = InterfaceTemplate
         fields = ['id', 'name', 'form_factor', 'mgmt_only']
         fields = ['id', 'name', 'form_factor', 'mgmt_only']
 
 
 
 
+class DeviceBayTemplateSerializer(serializers.ModelSerializer):
+
+    class Meta:
+        model = DeviceBay
+        fields = ['id', 'name',]
+
+
 #
 #
 # Device roles
 # Device roles
 #
 #
@@ -202,10 +223,11 @@ class DeviceRoleSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug', 'color']
         fields = ['id', 'name', 'slug', 'color']
 
 
 
 
-class DeviceRoleNestedSerializer(DeviceRoleSerializer):
+class NestedDeviceRoleSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(DeviceRoleSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = DeviceRole
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -219,40 +241,43 @@ class PlatformSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug', 'rpc_client']
         fields = ['id', 'name', 'slug', 'rpc_client']
 
 
 
 
-class PlatformNestedSerializer(PlatformSerializer):
+class NestedPlatformSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(PlatformSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = Platform
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
 # Devices
 # Devices
 #
 #
 
 
-# Cannot import ipam.api.IPAddressNestedSerializer due to circular dependency
+# Cannot import ipam.api.NestedIPAddressSerializer due to circular dependency
-class DeviceIPAddressNestedSerializer(serializers.ModelSerializer):
+class DeviceIPAddressSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = IPAddress
         model = IPAddress
-        fields = ['id', 'family', 'address']
+        fields = ['id', 'url', 'family', 'address']
 
 
 
 
 class DeviceSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class DeviceSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    device_type = DeviceTypeNestedSerializer()
+    device_type = NestedDeviceTypeSerializer()
-    device_role = DeviceRoleNestedSerializer()
+    device_role = NestedDeviceRoleSerializer()
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
-    platform = PlatformNestedSerializer()
+    platform = NestedPlatformSerializer()
-    rack = RackNestedSerializer()
+    rack = NestedRackSerializer()
-    primary_ip = DeviceIPAddressNestedSerializer()
+    primary_ip = DeviceIPAddressSerializer()
-    primary_ip4 = DeviceIPAddressNestedSerializer()
+    primary_ip4 = DeviceIPAddressSerializer()
-    primary_ip6 = DeviceIPAddressNestedSerializer()
+    primary_ip6 = DeviceIPAddressSerializer()
     parent_device = serializers.SerializerMethodField()
     parent_device = serializers.SerializerMethodField()
 
 
     class Meta:
     class Meta:
         model = Device
         model = Device
-        fields = ['id', 'name', 'display_name', 'device_type', 'device_role', 'tenant', 'platform', 'serial',
+        fields = [
-                  'asset_tag', 'rack', 'position', 'face', 'parent_device', 'status', 'primary_ip', 'primary_ip4',
+            'id', 'name', 'display_name', 'device_type', 'device_role', 'tenant', 'platform', 'serial',  'asset_tag',
-                  'primary_ip6', 'comments', 'custom_fields']
+            'rack', 'position', 'face', 'parent_device', 'status', 'primary_ip', 'primary_ip4', 'primary_ip6',
+            'comments', 'custom_fields',
+        ]
 
 
     def get_parent_device(self, obj):
     def get_parent_device(self, obj):
         try:
         try:
@@ -269,11 +294,11 @@ class DeviceSerializer(CustomFieldSerializer, serializers.ModelSerializer):
         }
         }
 
 
 
 
-class DeviceNestedSerializer(serializers.ModelSerializer):
+class NestedDeviceSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = Device
         model = Device
-        fields = ['id', 'name', 'display_name']
+        fields = ['id', 'url', 'name', 'display_name']
 
 
 
 
 #
 #
@@ -281,18 +306,18 @@ class DeviceNestedSerializer(serializers.ModelSerializer):
 #
 #
 
 
 class ConsoleServerPortSerializer(serializers.ModelSerializer):
 class ConsoleServerPortSerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
 
 
     class Meta:
     class Meta:
         model = ConsoleServerPort
         model = ConsoleServerPort
         fields = ['id', 'device', 'name', 'connected_console']
         fields = ['id', 'device', 'name', 'connected_console']
 
 
 
 
-class NestedConsoleServerPortSerializer(ConsoleServerPortSerializer):
+class ChildConsoleServerPortSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = ConsoleServerPort
         model = ConsoleServerPort
-        fields = ['id', 'name', 'connected_console']
+        fields = ['id', 'url', 'name', 'connected_console']
 
 
 
 
 #
 #
@@ -300,7 +325,7 @@ class NestedConsoleServerPortSerializer(ConsoleServerPortSerializer):
 #
 #
 
 
 class ConsolePortSerializer(serializers.ModelSerializer):
 class ConsolePortSerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
     cs_port = ConsoleServerPortSerializer()
     cs_port = ConsoleServerPortSerializer()
 
 
     class Meta:
     class Meta:
@@ -308,11 +333,11 @@ class ConsolePortSerializer(serializers.ModelSerializer):
         fields = ['id', 'device', 'name', 'cs_port', 'connection_status']
         fields = ['id', 'device', 'name', 'cs_port', 'connection_status']
 
 
 
 
-class NestedConsolePortSerializer(ConsolePortSerializer):
+class ChildConsolePortSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = ConsolePort
         model = ConsolePort
-        fields = ['id', 'name', 'cs_port', 'connection_status']
+        fields = ['id', 'url', 'name', 'cs_port', 'connection_status']
 
 
 
 
 #
 #
@@ -320,18 +345,18 @@ class NestedConsolePortSerializer(ConsolePortSerializer):
 #
 #
 
 
 class PowerOutletSerializer(serializers.ModelSerializer):
 class PowerOutletSerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
 
 
     class Meta:
     class Meta:
         model = PowerOutlet
         model = PowerOutlet
         fields = ['id', 'device', 'name', 'connected_port']
         fields = ['id', 'device', 'name', 'connected_port']
 
 
 
 
-class NestedPowerOutletSerializer(PowerOutletSerializer):
+class ChildPowerOutletSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = PowerOutlet
         model = PowerOutlet
-        fields = ['id', 'name', 'connected_port']
+        fields = ['id', 'url', 'name', 'connected_port']
 
 
 
 
 #
 #
@@ -339,7 +364,7 @@ class NestedPowerOutletSerializer(PowerOutletSerializer):
 #
 #
 
 
 class PowerPortSerializer(serializers.ModelSerializer):
 class PowerPortSerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
     power_outlet = PowerOutletSerializer()
     power_outlet = PowerOutletSerializer()
 
 
     class Meta:
     class Meta:
@@ -347,11 +372,11 @@ class PowerPortSerializer(serializers.ModelSerializer):
         fields = ['id', 'device', 'name', 'power_outlet', 'connection_status']
         fields = ['id', 'device', 'name', 'power_outlet', 'connection_status']
 
 
 
 
-class NestedPowerPortSerializer(PowerPortSerializer):
+class ChildPowerPortSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = PowerPort
         model = PowerPort
-        fields = ['id', 'name', 'power_outlet', 'connection_status']
+        fields = ['id', 'url', 'name', 'power_outlet', 'connection_status']
 
 
 
 
 #
 #
@@ -359,7 +384,7 @@ class NestedPowerPortSerializer(PowerPortSerializer):
 #
 #
 
 
 class InterfaceSerializer(serializers.ModelSerializer):
 class InterfaceSerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
     form_factor = serializers.ReadOnlyField(source='get_form_factor_display')
     form_factor = serializers.ReadOnlyField(source='get_form_factor_display')
 
 
     class Meta:
     class Meta:
@@ -367,18 +392,21 @@ class InterfaceSerializer(serializers.ModelSerializer):
         fields = ['id', 'device', 'name', 'form_factor', 'mac_address', 'mgmt_only', 'description', 'is_connected']
         fields = ['id', 'device', 'name', 'form_factor', 'mac_address', 'mgmt_only', 'description', 'is_connected']
 
 
 
 
-class NestedInterfaceSerializer(InterfaceSerializer):
+class ChildInterfaceSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = Interface
         model = Interface
-        fields = ['id', 'name', 'form_factor', 'mac_address', 'mgmt_only', 'description', 'is_connected']
+        fields = ['id', 'url', 'name', 'form_factor', 'mac_address', 'mgmt_only', 'description', 'is_connected']
 
 
 
 
+# TODO: Remove this
 class InterfaceDetailSerializer(InterfaceSerializer):
 class InterfaceDetailSerializer(InterfaceSerializer):
 
 
     class Meta(InterfaceSerializer.Meta):
     class Meta(InterfaceSerializer.Meta):
-        fields = ['id', 'device', 'name', 'form_factor', 'mac_address', 'mgmt_only', 'description', 'is_connected',
+        fields = [
-                  'connected_interface']
+            'id', 'device', 'name', 'form_factor', 'mac_address', 'mgmt_only', 'description', 'is_connected',
+            'connected_interface',
+        ]
 
 
 
 
 #
 #
@@ -386,19 +414,19 @@ class InterfaceDetailSerializer(InterfaceSerializer):
 #
 #
 
 
 class DeviceBaySerializer(serializers.ModelSerializer):
 class DeviceBaySerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
-    installed_device = DeviceNestedSerializer()
+    installed_device = NestedDeviceSerializer()
 
 
     class Meta:
     class Meta:
         model = DeviceBay
         model = DeviceBay
         fields = ['id', 'device', 'name', 'installed_device']
         fields = ['id', 'device', 'name', 'installed_device']
 
 
 
 
-class NestedDeviceBaySerializer(DeviceBaySerializer):
+class ChildDeviceBaySerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = DeviceBay
         model = DeviceBay
-        fields = ['id', 'name', 'installed_device']
+        fields = ['id', 'url', 'name', 'installed_device']
 
 
 
 
 #
 #
@@ -406,19 +434,19 @@ class NestedDeviceBaySerializer(DeviceBaySerializer):
 #
 #
 
 
 class ModuleSerializer(serializers.ModelSerializer):
 class ModuleSerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
-    manufacturer = ManufacturerNestedSerializer()
+    manufacturer = NestedManufacturerSerializer()
 
 
     class Meta:
     class Meta:
         model = Module
         model = Module
         fields = ['id', 'device', 'parent', 'name', 'manufacturer', 'part_id', 'serial', 'discovered']
         fields = ['id', 'device', 'parent', 'name', 'manufacturer', 'part_id', 'serial', 'discovered']
 
 
 
 
-class NestedModuleSerializer(ModuleSerializer):
+class ChildModuleSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta:
     class Meta:
         model = Module
         model = Module
-        fields = ['id', 'parent', 'name', 'manufacturer', 'part_id', 'serial', 'discovered']
+        fields = ['id', 'url', 'parent', 'name', 'manufacturer', 'part_id', 'serial', 'discovered']
 
 
 
 
 #
 #

+ 14 - 14
netbox/dcim/api/urls.py

@@ -35,37 +35,37 @@ urlpatterns = [
 
 
     # Devices
     # Devices
     url(r'^devices/(?P<pk>\d+)/lldp-neighbors/$', views.LLDPNeighborsView.as_view(), name='device_lldp-neighbors'),
     url(r'^devices/(?P<pk>\d+)/lldp-neighbors/$', views.LLDPNeighborsView.as_view(), name='device_lldp-neighbors'),
-    url(r'^devices/(?P<pk>\d+)/console-ports/$', views.NestedConsolePortViewSet.as_view({'get': 'list'}), name='device_consoleports'),
+    url(r'^devices/(?P<pk>\d+)/console-ports/$', views.ChildConsolePortViewSet.as_view({'get': 'list'}), name='consoleport-list'),
-    url(r'^devices/(?P<pk>\d+)/console-server-ports/$', views.NestedConsoleServerPortViewSet.as_view({'get': 'list'}), name='device_consoleserverports'),
+    url(r'^devices/(?P<pk>\d+)/console-server-ports/$', views.ChildConsoleServerPortViewSet.as_view({'get': 'list'}), name='consoleserverport-list'),
-    url(r'^devices/(?P<pk>\d+)/power-ports/$', views.NestedPowerPortViewSet.as_view({'get': 'list'}), name='device_powerports'),
+    url(r'^devices/(?P<pk>\d+)/power-ports/$', views.NestedPowerPortViewSet.as_view({'get': 'list'}), name='powerport-list'),
-    url(r'^devices/(?P<pk>\d+)/power-outlets/$', views.NestedPowerOutletViewSet.as_view({'get': 'list'}), name='device_poweroutlets'),
+    url(r'^devices/(?P<pk>\d+)/power-outlets/$', views.NestedPowerOutletViewSet.as_view({'get': 'list'}), name='poweroutlet-list'),
-    url(r'^devices/(?P<pk>\d+)/interfaces/$', views.NestedInterfaceViewSet.as_view({'get': 'list'}), name='device_interfaces'),
+    url(r'^devices/(?P<pk>\d+)/interfaces/$', views.NestedInterfaceViewSet.as_view({'get': 'list'}), name='interface-list'),
-    url(r'^devices/(?P<pk>\d+)/device-bays/$', views.NestedDeviceBayViewSet.as_view({'get': 'list'}), name='device_devicebays'),
+    url(r'^devices/(?P<pk>\d+)/device-bays/$', views.NestedDeviceBayViewSet.as_view({'get': 'list'}), name='devicebay-list'),
-    url(r'^devices/(?P<pk>\d+)/modules/$', views.NestedModuleViewSet.as_view({'get': 'list'}), name='device_modules'),
+    url(r'^devices/(?P<pk>\d+)/modules/$', views.NestedModuleViewSet.as_view({'get': 'list'}), name='module-list'),
     # TODO: Services
     # TODO: Services
 
 
     # Console ports
     # Console ports
-    url(r'^console-ports/(?P<pk>\d+)/$', views.ConsolePortViewSet.as_view({'get': 'retrieve'}), name='consoleport'),
+    url(r'^console-ports/(?P<pk>\d+)/$', views.ConsolePortViewSet.as_view({'get': 'retrieve'}), name='consoleport-detail'),
 
 
     # Console server ports
     # Console server ports
-    url(r'^console-server-ports/(?P<pk>\d+)/$', views.ConsoleServerPortViewSet.as_view({'get': 'retrieve'}), name='consoleserverport'),
+    url(r'^console-server-ports/(?P<pk>\d+)/$', views.ConsoleServerPortViewSet.as_view({'get': 'retrieve'}), name='consoleserverport-detail'),
 
 
     # Power ports
     # Power ports
-    url(r'^power-ports/(?P<pk>\d+)/$', views.PowerPortViewSet.as_view({'get': 'retrieve'}), name='powerport'),
+    url(r'^power-ports/(?P<pk>\d+)/$', views.PowerPortViewSet.as_view({'get': 'retrieve'}), name='powerport-detail'),
 
 
     # Power outlets
     # Power outlets
-    url(r'^power-outlets/(?P<pk>\d+)/$', views.PowerOutletViewSet.as_view({'get': 'retrieve'}), name='poweroutlet'),
+    url(r'^power-outlets/(?P<pk>\d+)/$', views.PowerOutletViewSet.as_view({'get': 'retrieve'}), name='poweroutlet-detail'),
 
 
     # Interfaces
     # Interfaces
-    url(r'^interfaces/(?P<pk>\d+)/$', views.InterfaceViewSet.as_view({'get': 'retrieve'}), name='interface'),
+    url(r'^interfaces/(?P<pk>\d+)/$', views.InterfaceViewSet.as_view({'get': 'retrieve'}), name='interface-detail'),
     url(r'^interfaces/(?P<pk>\d+)/graphs/$', GraphListView.as_view(), {'type': GRAPH_TYPE_INTERFACE},
     url(r'^interfaces/(?P<pk>\d+)/graphs/$', GraphListView.as_view(), {'type': GRAPH_TYPE_INTERFACE},
         name='interface_graphs'),
         name='interface_graphs'),
 
 
     # Device bays
     # Device bays
-    url(r'^device-bays/(?P<pk>\d+)/$', views.DeviceBayViewSet.as_view({'get': 'retrieve'}), name='devicebay'),
+    url(r'^device-bays/(?P<pk>\d+)/$', views.DeviceBayViewSet.as_view({'get': 'retrieve'}), name='devicebay-detail'),
 
 
     # Modules
     # Modules
-    url(r'^modules/(?P<pk>\d+)/$', views.ModuleViewSet.as_view({'get': 'retrieve'}), name='module'),
+    url(r'^modules/(?P<pk>\d+)/$', views.ModuleViewSet.as_view({'get': 'retrieve'}), name='module-detail'),
 
 
     # Miscellaneous
     # Miscellaneous
     url(r'^related-connections/$', views.RelatedConnectionsView.as_view(), name='related_connections'),
     url(r'^related-connections/$', views.RelatedConnectionsView.as_view(), name='related_connections'),

+ 15 - 16
netbox/dcim/api/views.py

@@ -57,13 +57,9 @@ class RackRoleViewSet(ModelViewSet):
 
 
 class RackViewSet(CustomFieldModelViewSet):
 class RackViewSet(CustomFieldModelViewSet):
     queryset = Rack.objects.select_related('site', 'group__site', 'tenant')
     queryset = Rack.objects.select_related('site', 'group__site', 'tenant')
+    serializer_class = serializers.RackSerializer
     filter_class = filters.RackFilter
     filter_class = filters.RackFilter
 
 
-    def get_serializer_class(self):
-        if self.action == 'retrieve':
-            return serializers.RackDetailSerializer
-        return serializers.RackSerializer
-
 
 
 class RackUnitListView(APIView):
 class RackUnitListView(APIView):
     """
     """
@@ -85,7 +81,10 @@ class RackUnitListView(APIView):
         # Serialize Devices within the rack elevation
         # Serialize Devices within the rack elevation
         for u in elevation:
         for u in elevation:
             if u['device']:
             if u['device']:
-                u['device'] = serializers.DeviceNestedSerializer(instance=u['device']).data
+                u['device'] = serializers.NestedDeviceSerializer(
+                    instance=u['device'],
+                    context={'request': request},
+                ).data
 
 
         return Response(elevation)
         return Response(elevation)
 
 
@@ -105,7 +104,7 @@ class ManufacturerViewSet(ModelViewSet):
 
 
 class DeviceTypeViewSet(CustomFieldModelViewSet):
 class DeviceTypeViewSet(CustomFieldModelViewSet):
     queryset = DeviceType.objects.select_related('manufacturer')
     queryset = DeviceType.objects.select_related('manufacturer')
-    filter_class = filters.DeviceTypeFilter
+    serializer_class = serializers.DeviceTypeSerializer
 
 
 
 
 #
 #
@@ -150,8 +149,8 @@ class ConsolePortViewSet(RetrieveModelMixin, UpdateModelMixin, DestroyModelMixin
     serializer_class = serializers.ConsolePortSerializer
     serializer_class = serializers.ConsolePortSerializer
 
 
 
 
-class NestedConsolePortViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
+class ChildConsolePortViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
-    serializer_class = serializers.NestedConsolePortSerializer
+    serializer_class = serializers.ChildConsoleServerPortSerializer
 
 
     def get_queryset(self):
     def get_queryset(self):
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
@@ -167,8 +166,8 @@ class ConsoleServerPortViewSet(RetrieveModelMixin, UpdateModelMixin, DestroyMode
     serializer_class = serializers.ConsoleServerPortSerializer
     serializer_class = serializers.ConsoleServerPortSerializer
 
 
 
 
-class NestedConsoleServerPortViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
+class ChildConsoleServerPortViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
-    serializer_class = serializers.NestedConsoleServerPortSerializer
+    serializer_class = serializers.ChildConsoleServerPortSerializer
 
 
     def get_queryset(self):
     def get_queryset(self):
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
@@ -185,7 +184,7 @@ class PowerPortViewSet(RetrieveModelMixin, UpdateModelMixin, DestroyModelMixin,
 
 
 
 
 class NestedPowerPortViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
 class NestedPowerPortViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
-    serializer_class = serializers.NestedPowerPortSerializer
+    serializer_class = serializers.ChildPowerPortSerializer
 
 
     def get_queryset(self):
     def get_queryset(self):
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
@@ -202,7 +201,7 @@ class PowerOutletViewSet(RetrieveModelMixin, UpdateModelMixin, DestroyModelMixin
 
 
 
 
 class NestedPowerOutletViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
 class NestedPowerOutletViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
-    serializer_class = serializers.NestedPowerOutletSerializer
+    serializer_class = serializers.ChildPowerOutletSerializer
 
 
     def get_queryset(self):
     def get_queryset(self):
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
@@ -219,7 +218,7 @@ class InterfaceViewSet(RetrieveModelMixin, UpdateModelMixin, DestroyModelMixin,
 
 
 
 
 class NestedInterfaceViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
 class NestedInterfaceViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
-    serializer_class = serializers.NestedInterfaceSerializer
+    serializer_class = serializers.ChildInterfaceSerializer
     filter_class = filters.InterfaceFilter
     filter_class = filters.InterfaceFilter
 
 
     def get_queryset(self):
     def get_queryset(self):
@@ -238,7 +237,7 @@ class DeviceBayViewSet(RetrieveModelMixin, UpdateModelMixin, DestroyModelMixin,
 
 
 
 
 class NestedDeviceBayViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
 class NestedDeviceBayViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
-    serializer_class = serializers.NestedDeviceBaySerializer
+    serializer_class = serializers.ChildDeviceBaySerializer
 
 
     def get_queryset(self):
     def get_queryset(self):
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
@@ -255,7 +254,7 @@ class ModuleViewSet(RetrieveModelMixin, UpdateModelMixin, DestroyModelMixin, Gen
 
 
 
 
 class NestedModuleViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
 class NestedModuleViewSet(CreateModelMixin, ListModelMixin, GenericViewSet):
-    serializer_class = serializers.NestedModuleSerializer
+    serializer_class = serializers.ChildModuleSerializer
 
 
     def get_queryset(self):
     def get_queryset(self):
         device = get_object_or_404(Device, pk=self.kwargs['pk'])
         device = get_object_or_404(Device, pk=self.kwargs['pk'])

+ 8 - 3
netbox/extras/api/views.py

@@ -33,10 +33,12 @@ class CustomFieldModelViewSet(ModelViewSet):
                 custom_field_choices[cfc.id] = cfc.value
                 custom_field_choices[cfc.id] = cfc.value
         custom_field_choices = custom_field_choices
         custom_field_choices = custom_field_choices
 
 
-        return {
+        context = super(CustomFieldModelViewSet, self).get_serializer_context()
+        context.update({
             'custom_fields': custom_fields,
             'custom_fields': custom_fields,
             'custom_field_choices': custom_field_choices,
             'custom_field_choices': custom_field_choices,
-        }
+        })
+        return context
 
 
     def get_queryset(self):
     def get_queryset(self):
         # Prefetch custom field values
         # Prefetch custom field values
@@ -55,8 +57,11 @@ class GraphListView(generics.ListAPIView):
             GRAPH_TYPE_PROVIDER: Provider,
             GRAPH_TYPE_PROVIDER: Provider,
             GRAPH_TYPE_SITE: Site,
             GRAPH_TYPE_SITE: Site,
         }
         }
+        obj = get_object_or_404(cls[self.kwargs.get('type')], pk=self.kwargs['pk'])
         context = super(GraphListView, self).get_serializer_context()
         context = super(GraphListView, self).get_serializer_context()
-        context.update({'graphed_object': get_object_or_404(cls[self.kwargs.get('type')], pk=self.kwargs['pk'])})
+        context.update({
+            'graphed_object': obj,
+        })
         return context
         return context
 
 
     def get_queryset(self):
     def get_queryset(self):

+ 64 - 65
netbox/ipam/api/serializers.py

@@ -1,9 +1,9 @@
 from rest_framework import serializers
 from rest_framework import serializers
 
 
-from dcim.api.serializers import DeviceNestedSerializer, NestedInterfaceSerializer, SiteNestedSerializer
+from dcim.api.serializers import NestedDeviceSerializer, ChildInterfaceSerializer, NestedSiteSerializer
 from extras.api.serializers import CustomFieldSerializer
 from extras.api.serializers import CustomFieldSerializer
 from ipam.models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from ipam.models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
-from tenancy.api.serializers import TenantNestedSerializer
+from tenancy.api.serializers import NestedTenantSerializer
 
 
 
 
 #
 #
@@ -11,26 +11,18 @@ from tenancy.api.serializers import TenantNestedSerializer
 #
 #
 
 
 class VRFSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class VRFSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
 
 
     class Meta:
     class Meta:
         model = VRF
         model = VRF
         fields = ['id', 'name', 'rd', 'tenant', 'enforce_unique', 'description', 'custom_fields']
         fields = ['id', 'name', 'rd', 'tenant', 'enforce_unique', 'description', 'custom_fields']
 
 
 
 
-class VRFNestedSerializer(VRFSerializer):
+class NestedVRFSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(VRFSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'rd']
+        model = VRF
-
+        fields = ['id', 'url', 'name', 'rd']
-
-class VRFTenantSerializer(VRFSerializer):
-    """
-    Include tenant serializer. Useful for determining tenant inheritance for Prefixes and IPAddresses.
-    """
-
-    class Meta(VRFSerializer.Meta):
-        fields = ['id', 'name', 'rd', 'tenant']
 
 
 
 
 #
 #
@@ -44,10 +36,11 @@ class RoleSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug', 'weight']
         fields = ['id', 'name', 'slug', 'weight']
 
 
 
 
-class RoleNestedSerializer(RoleSerializer):
+class NestedRoleSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(RoleSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = Role
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -61,10 +54,11 @@ class RIRSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug', 'is_private']
         fields = ['id', 'name', 'slug', 'is_private']
 
 
 
 
-class RIRNestedSerializer(RIRSerializer):
+class NestedRIRSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(RIRSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = RIR
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -72,17 +66,18 @@ class RIRNestedSerializer(RIRSerializer):
 #
 #
 
 
 class AggregateSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class AggregateSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    rir = RIRNestedSerializer()
+    rir = NestedRIRSerializer()
 
 
     class Meta:
     class Meta:
         model = Aggregate
         model = Aggregate
         fields = ['id', 'family', 'prefix', 'rir', 'date_added', 'description', 'custom_fields']
         fields = ['id', 'family', 'prefix', 'rir', 'date_added', 'description', 'custom_fields']
 
 
 
 
-class AggregateNestedSerializer(AggregateSerializer):
+class NestedAggregateSerializer(serializers.HyperlinkedModelSerializer):
 
 
     class Meta(AggregateSerializer.Meta):
     class Meta(AggregateSerializer.Meta):
-        fields = ['id', 'family', 'prefix']
+        model = Aggregate
+        fields = ['id', 'url', 'family', 'prefix']
 
 
 
 
 #
 #
@@ -90,17 +85,18 @@ class AggregateNestedSerializer(AggregateSerializer):
 #
 #
 
 
 class VLANGroupSerializer(serializers.ModelSerializer):
 class VLANGroupSerializer(serializers.ModelSerializer):
-    site = SiteNestedSerializer()
+    site = NestedSiteSerializer()
 
 
     class Meta:
     class Meta:
         model = VLANGroup
         model = VLANGroup
         fields = ['id', 'name', 'slug', 'site']
         fields = ['id', 'name', 'slug', 'site']
 
 
 
 
-class VLANGroupNestedSerializer(VLANGroupSerializer):
+class NestedVLANGroupSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(VLANGroupSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = VLANGroup
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -108,21 +104,24 @@ class VLANGroupNestedSerializer(VLANGroupSerializer):
 #
 #
 
 
 class VLANSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class VLANSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    site = SiteNestedSerializer()
+    site = NestedSiteSerializer()
-    group = VLANGroupNestedSerializer()
+    group = NestedVLANGroupSerializer()
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
-    role = RoleNestedSerializer()
+    role = NestedRoleSerializer()
 
 
     class Meta:
     class Meta:
         model = VLAN
         model = VLAN
-        fields = ['id', 'site', 'group', 'vid', 'name', 'tenant', 'status', 'role', 'description', 'display_name',
+        fields = [
-                  'custom_fields']
+            'id', 'site', 'group', 'vid', 'name', 'tenant', 'status', 'role', 'description', 'display_name',
+            'custom_fields',
+        ]
 
 
 
 
-class VLANNestedSerializer(VLANSerializer):
+class NestedVLANSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(VLANSerializer.Meta):
+    class Meta:
-        fields = ['id', 'vid', 'name', 'display_name']
+        model = VLAN
+        fields = ['id', 'url', 'vid', 'name', 'display_name']
 
 
 
 
 #
 #
@@ -130,22 +129,25 @@ class VLANNestedSerializer(VLANSerializer):
 #
 #
 
 
 class PrefixSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class PrefixSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    site = SiteNestedSerializer()
+    site = NestedSiteSerializer()
-    vrf = VRFTenantSerializer()
+    vrf = NestedVRFSerializer()
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
-    vlan = VLANNestedSerializer()
+    vlan = NestedVLANSerializer()
-    role = RoleNestedSerializer()
+    role = NestedRoleSerializer()
 
 
     class Meta:
     class Meta:
         model = Prefix
         model = Prefix
-        fields = ['id', 'family', 'prefix', 'site', 'vrf', 'tenant', 'vlan', 'status', 'role', 'is_pool', 'description',
+        fields = [
-                  'custom_fields']
+            'id', 'family', 'prefix', 'site', 'vrf', 'tenant', 'vlan', 'status', 'role', 'is_pool', 'description',
+            'custom_fields',
+        ]
 
 
 
 
-class PrefixNestedSerializer(PrefixSerializer):
+class NestedPrefixSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(PrefixSerializer.Meta):
+    class Meta:
-        fields = ['id', 'family', 'prefix']
+        model = Prefix
+        fields = ['id', 'url', 'family', 'prefix']
 
 
 
 
 #
 #
@@ -153,23 +155,26 @@ class PrefixNestedSerializer(PrefixSerializer):
 #
 #
 
 
 class IPAddressSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class IPAddressSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    vrf = VRFTenantSerializer()
+    vrf = NestedVRFSerializer()
-    tenant = TenantNestedSerializer()
+    tenant = NestedTenantSerializer()
-    interface = NestedInterfaceSerializer()
+    interface = ChildInterfaceSerializer()
 
 
     class Meta:
     class Meta:
         model = IPAddress
         model = IPAddress
-        fields = ['id', 'family', 'address', 'vrf', 'tenant', 'status', 'interface', 'description', 'nat_inside',
+        fields = [
-                  'nat_outside', 'custom_fields']
+            'id', 'family', 'address', 'vrf', 'tenant', 'status', 'interface', 'description', 'nat_inside',
+            'nat_outside', 'custom_fields',
+        ]
 
 
 
 
-class IPAddressNestedSerializer(IPAddressSerializer):
+class NestedIPAddressSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(IPAddressSerializer.Meta):
+    class Meta:
-        fields = ['id', 'family', 'address']
+        model = IPAddress
+        fields = ['id', 'url', 'family', 'address']
 
 
-IPAddressSerializer._declared_fields['nat_inside'] = IPAddressNestedSerializer()
+IPAddressSerializer._declared_fields['nat_inside'] = NestedIPAddressSerializer()
-IPAddressSerializer._declared_fields['nat_outside'] = IPAddressNestedSerializer()
+IPAddressSerializer._declared_fields['nat_outside'] = NestedIPAddressSerializer()
 
 
 
 
 #
 #
@@ -177,15 +182,9 @@ IPAddressSerializer._declared_fields['nat_outside'] = IPAddressNestedSerializer(
 #
 #
 
 
 class ServiceSerializer(serializers.ModelSerializer):
 class ServiceSerializer(serializers.ModelSerializer):
-    device = DeviceNestedSerializer()
+    device = NestedDeviceSerializer()
-    ipaddresses = IPAddressNestedSerializer(many=True)
+    ipaddresses = NestedIPAddressSerializer(many=True)
 
 
     class Meta:
     class Meta:
         model = Service
         model = Service
         fields = ['id', 'device', 'name', 'port', 'protocol', 'ipaddresses', 'description']
         fields = ['id', 'device', 'name', 'port', 'protocol', 'ipaddresses', 'description']
-
-
-class ServiceNestedSerializer(ServiceSerializer):
-
-    class Meta(ServiceSerializer.Meta):
-        fields = ['id', 'name', 'port', 'protocol']

+ 6 - 6
netbox/netbox/urls.py

@@ -26,12 +26,12 @@ _patterns = [
     url(r'^profile/', include('users.urls', namespace='users')),
     url(r'^profile/', include('users.urls', namespace='users')),
 
 
     # API
     # API
-    url(r'^api/circuits/', include('circuits.api.urls', namespace='circuits-api')),
+    url(r'^api/circuits/', include('circuits.api.urls')),
-    url(r'^api/dcim/', include('dcim.api.urls', namespace='dcim-api')),
+    url(r'^api/dcim/', include('dcim.api.urls')),
-    url(r'^api/ipam/', include('ipam.api.urls', namespace='ipam-api')),
+    url(r'^api/ipam/', include('ipam.api.urls')),
-    url(r'^api/secrets/', include('secrets.api.urls', namespace='secrets-api')),
+    url(r'^api/secrets/', include('secrets.api.urls')),
-    url(r'^api/tenancy/', include('tenancy.api.urls', namespace='tenancy-api')),
+    url(r'^api/tenancy/', include('tenancy.api.urls')),
-    url(r'^api-auth/', include('rest_framework.urls', namespace='rest_framework')),
+    url(r'^api-auth/', include('rest_framework.urls')),
 
 
     # Error testing
     # Error testing
     url(r'^500/$', trigger_500),
     url(r'^500/$', trigger_500),

+ 7 - 21
netbox/secrets/api/serializers.py

@@ -1,7 +1,6 @@
 from rest_framework import serializers
 from rest_framework import serializers
 
 
-from dcim.models import Device
+from dcim.api.serializers import NestedDeviceSerializer
-from ipam.api.serializers import IPAddressNestedSerializer
 from secrets.models import Secret, SecretRole
 from secrets.models import Secret, SecretRole
 
 
 
 
@@ -16,34 +15,21 @@ class SecretRoleSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug']
         fields = ['id', 'name', 'slug']
 
 
 
 
-class SecretRoleNestedSerializer(SecretRoleSerializer):
+class NestedSecretRoleSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(SecretRoleSerializer.Meta):
+    class Meta:
-        pass
+        model = SecretRole
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
 # Secrets
 # Secrets
 #
 #
 
 
-class SecretDeviceSerializer(serializers.ModelSerializer):
-    primary_ip = IPAddressNestedSerializer()
-
-    class Meta:
-        model = Device
-        fields = ['id', 'name', 'primary_ip']
-
-
 class SecretSerializer(serializers.ModelSerializer):
 class SecretSerializer(serializers.ModelSerializer):
-    device = SecretDeviceSerializer()
+    device = NestedDeviceSerializer()
-    role = SecretRoleNestedSerializer()
+    role = NestedSecretRoleSerializer()
 
 
     class Meta:
     class Meta:
         model = Secret
         model = Secret
         fields = ['id', 'device', 'role', 'name', 'plaintext', 'hash', 'created', 'last_updated']
         fields = ['id', 'device', 'role', 'name', 'plaintext', 'hash', 'created', 'last_updated']
-
-
-class SecretNestedSerializer(SecretSerializer):
-
-    class Meta(SecretSerializer.Meta):
-        fields = ['id', 'name']

+ 9 - 7
netbox/tenancy/api/serializers.py

@@ -15,10 +15,11 @@ class TenantGroupSerializer(serializers.ModelSerializer):
         fields = ['id', 'name', 'slug']
         fields = ['id', 'name', 'slug']
 
 
 
 
-class TenantGroupNestedSerializer(TenantGroupSerializer):
+class NestedTenantGroupSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(TenantGroupSerializer.Meta):
+    class Meta:
-        pass
+        model = TenantGroup
+        fields = ['id', 'url', 'name', 'slug']
 
 
 
 
 #
 #
@@ -26,14 +27,15 @@ class TenantGroupNestedSerializer(TenantGroupSerializer):
 #
 #
 
 
 class TenantSerializer(CustomFieldSerializer, serializers.ModelSerializer):
 class TenantSerializer(CustomFieldSerializer, serializers.ModelSerializer):
-    group = TenantGroupNestedSerializer()
+    group = NestedTenantGroupSerializer()
 
 
     class Meta:
     class Meta:
         model = Tenant
         model = Tenant
         fields = ['id', 'name', 'slug', 'group', 'description', 'comments', 'custom_fields']
         fields = ['id', 'name', 'slug', 'group', 'description', 'comments', 'custom_fields']
 
 
 
 
-class TenantNestedSerializer(TenantSerializer):
+class NestedTenantSerializer(serializers.HyperlinkedModelSerializer):
 
 
-    class Meta(TenantSerializer.Meta):
+    class Meta:
-        fields = ['id', 'name', 'slug']
+        model = Tenant
+        fields = ['id', 'url', 'name', 'slug']