【发布时间】:2020-12-19 09:14:07
【问题描述】:
我有一些彼此之间具有不同关系的 django 模型(即多对多、外键)。现在,我想使用djnago-rest 对它们进行序列化。
这是我的模型及其关系的示例:
class CommonFieldsAbstarct(models.Model):
name = models.CharField(max_length=30, unique=True)
class ServerModel(CommonFieldsAbstarct):
server_ip = models.GenericIPAddressField(default='172.17.0.1')
server_port = models.IntegerField(default='9001')
class SNMPLineModel(CommonFieldsAbstarct):
ip_address = models.GenericIPAddressField()
port = models.IntegerField(default=161)
class SNMPModel(CommonFieldsAbstarct): # target
line = models.ForeignKey(SNMPLineModel, on_delete=CASCADE)
servers = models.ManyToManyField(ServerModel)
class MetaDataModel(models.Model):
key = models.CharField(max_length=20)
value = models.CharField(max_length=20)
snmp_device = models.ForeignKey(SNMPModel, on_delete=CASCADE)
以前,我用这种方式手动创建json:
def meta_data_json(meta_data):
meta_data_list = []
for meta in meta_data:
meta_data_list.append({
meta.key: meta.value
})
return meta_data_list
def server_json(servers):
return [{'ip': server.server_ip,
'port': server.server_port}
for server in servers]
def create_json():
snmp = SNMPModel.objects.filter(name__contains='a-name')
return {
'name': snmp.name,
'address': snmp.line.ip_address,
'port': snmp.line.port,
'servers': server_json(snmp.servers.all()),
'meta_data': meta_data_json(MetaDataModel.objects.filter(
snmp_device=snmp.pk
)
),
'device_pk': snmp.pk
}
我的问题:
现在,我怎样才能通过django-rest-framework创建这样一个上面的json呢?
我对多对多没有任何问题。事实上,我的问题在于他们的foreignkey(s)。
这是我到目前为止所做的:
序列化器.py
from rest_framework import serializers
class MetaDataSerializer(serializers.ModelSerializer):
class Meta:
fields = [
'id',
'key',
'value',
]
model = MetaDataModel
class ServerSerializer(serializers.ModelSerializer):
class Meta:
fields = [
'id',
'server_ip',
'server_port',
]
model = ServerModel
class LineSerializer(serializers.ModelSerializer):
port = serializers.RelatedField(many=True)
class Meta:
fields = '__all__'
model = SNMPLineModel
class SNMPSerializer(serializers.ModelSerializer):
servers = ServerSerializer(many=True, read_only=True) # It is ok
meta_data = MetaDataSerializer(many=True, read_only=True) # It's not ok
line = LineSerializer(many=True, read_only=True) # It's not ok
address = serializers.CharField(source=SNMPLineModel.ip_address) # It's not ok
port = serializers.CharField(source=SNMPLineModel.port) # It's not ok
class Meta:
fields = [
'id',
'servers',
'name',
'address',
'port',
'line',
'meta_data'
]
model = SNMPModel
views.py
from django.views.decorators.csrf import csrf_exempt
from django.http import HttpResponse, JsonResponse
@csrf_exempt
def snippet_detail(request, name):
try:
snmp_conf = SNMPModel.objects.filter(name__contains=name)
except SNMPModel.DoesNotExist:
return HttpResponse(status=404)
if request.method == 'GET':
serializer = SNMPSerializer(snmp_conf, many=True)
return JsonResponse(serializer.data, status=200, safe=False)
urls.py
from django.urls import path
urlpatterns = [
path('snippets/<name>/', views.snippet_detail)
]
任何帮助将不胜感激。
【问题讨论】:
标签: python django django-models django-rest-framework django-serializer