mirror of
https://github.com/netbox-community/netbox.git
synced 2024-05-10 07:54:54 +00:00
dcim: added json flat renderer.
This commit is contained in:
@ -16,7 +16,7 @@ from .serializers import SiteSerializer, RackGroupSerializer, RackSerializer, Ra
|
||||
ManufacturerSerializer, DeviceTypeSerializer, DeviceRoleSerializer, PlatformSerializer, DeviceSerializer, \
|
||||
DeviceNestedSerializer, ConsolePortSerializer, ConsoleServerPortSerializer, PowerPortSerializer, \
|
||||
PowerOutletSerializer, InterfaceSerializer, InterfaceDetailSerializer, InterfaceConnectionSerializer
|
||||
from extras.api.renderers import BINDZoneRenderer
|
||||
from extras.api.renderers import BINDZoneRenderer, FlatJSONRenderer
|
||||
from utilities.api import ServiceUnavailable
|
||||
|
||||
|
||||
@ -198,7 +198,7 @@ class DeviceListView(generics.ListAPIView):
|
||||
.prefetch_related('primary_ip__nat_outside')
|
||||
serializer_class = DeviceSerializer
|
||||
filter_class = DeviceFilter
|
||||
renderer_classes = api_settings.DEFAULT_RENDERER_CLASSES + [BINDZoneRenderer]
|
||||
renderer_classes = api_settings.DEFAULT_RENDERER_CLASSES + [BINDZoneRenderer, FlatJSONRenderer]
|
||||
|
||||
|
||||
class DeviceDetailView(generics.RetrieveAPIView):
|
||||
|
@ -322,6 +322,14 @@ class DeviceTest(APITestCase):
|
||||
|
||||
nested_fields = ['id', 'name']
|
||||
|
||||
# Holds primary IP nested fields until api tests
|
||||
# can be made and fields imported.
|
||||
primary_ip = [
|
||||
'id',
|
||||
'family',
|
||||
'address'
|
||||
]
|
||||
|
||||
def test_get_list(self, endpoint='/api/dcim/devices/'):
|
||||
response = self.client.get(endpoint)
|
||||
content = json.loads(response.content)
|
||||
@ -349,6 +357,48 @@ class DeviceTest(APITestCase):
|
||||
sorted(RackTest.nested_fields),
|
||||
)
|
||||
|
||||
def test_get_list_flat(self, endpoint='/api/dcim/devices/?format=json_flat'):
|
||||
|
||||
flat_fields = [
|
||||
'comments',
|
||||
'device_role_id',
|
||||
'device_role_name',
|
||||
'device_role_slug',
|
||||
'device_type_id',
|
||||
'device_type_manufacturer_id',
|
||||
'device_type_manufacturer_name',
|
||||
'device_type_manufacturer_slug',
|
||||
'device_type_model',
|
||||
'device_type_slug',
|
||||
'display_name',
|
||||
'face',
|
||||
'id',
|
||||
'name',
|
||||
'platform_id',
|
||||
'platform_name',
|
||||
'platform_slug',
|
||||
'position',
|
||||
'primary_ip_address',
|
||||
'primary_ip_family',
|
||||
'primary_ip_id',
|
||||
'rack_display_name',
|
||||
'rack_facility_id',
|
||||
'rack_id',
|
||||
'rack_name',
|
||||
'ro_snmp',
|
||||
'serial',
|
||||
'status',
|
||||
]
|
||||
|
||||
response = self.client.get(endpoint)
|
||||
content = json.loads(response.content)
|
||||
self.assertEqual(response.status_code, status.HTTP_200_OK)
|
||||
device = content[0]
|
||||
self.assertEqual(
|
||||
sorted(device.keys()),
|
||||
sorted(flat_fields),
|
||||
)
|
||||
|
||||
def test_get_detail(self, endpoint='/api/dcim/devices/1/'):
|
||||
response = self.client.get(endpoint)
|
||||
content = json.loads(response.content)
|
||||
|
@ -1,6 +1,6 @@
|
||||
import json
|
||||
from rest_framework import renderers
|
||||
|
||||
|
||||
# IP address family designations
|
||||
AF = {
|
||||
4: 'A',
|
||||
@ -29,3 +29,23 @@ class BINDZoneRenderer(renderers.BaseRenderer):
|
||||
except KeyError:
|
||||
pass
|
||||
return '\n'.join(records)
|
||||
|
||||
|
||||
class FlatJSONRenderer(renderers.BaseRenderer):
|
||||
"""
|
||||
Flattens a nested JSON reponse.
|
||||
"""
|
||||
format = 'json_flat'
|
||||
media_type = 'application/json'
|
||||
|
||||
def render(self, data, media_type=None, renderer_context=None):
|
||||
|
||||
def flatten(entry):
|
||||
for key, val in entry.iteritems():
|
||||
if isinstance(val, dict):
|
||||
for child_key, child_val in flatten(val):
|
||||
yield "{}_{}".format(key, child_key), child_val
|
||||
else:
|
||||
yield key, val
|
||||
|
||||
return json.dumps([dict(flatten(i)) for i in data])
|
||||
|
Reference in New Issue
Block a user