用于 POST 方法 json 格式输出的嵌套序列化程序的 Django Rest Framework(已删除只读)
Django Rest Framework for nested serializer for POST method json format output (already removed read-only)
我想创建一个关于学生 class 出勤的应用程序,格式如下。我在这样的 GET 请求中得到了我需要的实际输出响应。
[
{
"id": 1,
"present": "Yes",
"schedule": {
"id": 2,
"schedule_date": "2019-02-28",
"start_time": "2019-02-28T11:00:00Z",
"end_time": "2019-02-28T11:45:00Z",
"description": "new schedule",
"class_name": 2,
"class_room": 1,
"subject": 2,
"teacher": 3
},
"student": {
"id": 2,
"username": "student",
"email": "",
"first_name": "rakhi",
"last_name": "sawant"
}
},
{
"id": 2,
"present": "No",
"schedule": {
"id": 2,
"schedule_date": "2019-02-28",
"start_time": "2019-02-28T11:00:00Z",
"end_time": "2019-02-28T11:45:00Z",
"description": "new schedule",
"class_name": 2,
"class_room": 1,
"subject": 2,
"teacher": 3
},
"student": {
"id": 5,
"username": "roshanritik",
"email": "ritik@gmail.com",
"first_name": "Ritik",
"last_name": "Roshan"
}
}
]
但是在 POST 请求的情况下,我没有得到我实际需要的格式。我已经给出了这样的输入请求
{
"present" : "Yes",
"student" : {
"id" : 1
},
"schedule" :{
"id" : 2
}
}
并希望 POST 的输出与上述 GET 响应相同。
这是我的Model.py
class Schedule(models.Model):
schedule_date = models.DateField()
start_time = models.DateTimeField()
end_time = models.DateTimeField()
description = models.CharField(max_length=200)
class_name = models.ForeignKey(ClassName, on_delete=models.CASCADE)
class_room = models.ForeignKey(ClassRoom, on_delete=models.CASCADE)
subject = models.ForeignKey(Subject, on_delete=models.CASCADE)
teacher = models.ForeignKey(User, on_delete=models.CASCADE)
def __str__(self):
return self.description
# Student's Attendance Table
class Attendance(models.Model):
present = EnumField(choices=['Yes', 'No'])
student = models.ForeignKey(User, on_delete=models.CASCADE)
schedule = models.ForeignKey(Schedule, on_delete=models.CASCADE)
def __str__(self):
return self.present
class Meta:
unique_together = ('student', 'schedule')
serializer.py
class AttendanceSerializers(serializers.ModelSerializer):
schedule = ScheduleSerializers(many=False, required=False)
student = UserSerializer(many=False, required=False)
class Meta:
model = Attendance
fields = ('id', 'present', 'schedule', 'student')
def create(self, validated_data):
schedule_data = validated_data.pop('schedule')
schedule = SchedulePartialSerializers.create(SchedulePartialSerializers(), validated_data=schedule_data)
student_data = validated_data.pop('student')
student = UserPartialSerializers.create(UserPartialSerializers(), validated_data=student_data)
attendance, created = Attendance.objects.update_or_create(schedule=schedule, student=student,
present=validated_data.pop('present'))
return attendance
Views.py
class AttendanceView(generics.ListCreateAPIView):
queryset = Attendance.objects.all()
serializer_class = AttendanceSerializers
def create(self, request, *args, **kwargs):
write_serializer = AttendanceSerializers(data=request.data)
write_serializer.is_valid(raise_exception=True)
instance = self.perform_create(write_serializer)
read_serializer = AttendanceSerializers(instance)
return Response(read_serializer.data)
userserializer
class UserSerializers(serializers.ModelSerializer):
class Meta:
model = User
fields = ('id', 'first_name')
ScheduleSerializer
class ScheduleSerializers(serializers.ModelSerializer):
class Meta:
model = Schedule
fields = "__all__"
请检查代码。会有帮助。
我们更改了一些代码,例如 Model.py
class Attendance(models.Model):
present = EnumField(choices=['Yes', 'No'])
student = models.ForeignKey(User, on_delete=models.CASCADE)
schedule = models.ForeignKey(Schedule, on_delete=models.CASCADE)
def __str__(self):
return self.present
在Serializer.py
class ScheduleSerializers(serializers.ModelSerializer):
class Meta:
model = Schedule
fields = "__all__"
class UserPartialSerializers(serializers.ModelSerializer):
class Meta:
model = User
fields = ('id', 'first_name')
class AttendanceSerializers(serializers.ModelSerializer):
class Meta:
model = Attendance
fields = '__all__'
class AttendanceScheduleSerializers(serializers.ModelSerializer):
schedule = ScheduleSerializers(many=False)
student = UserSerializer(many=False)
class Meta:
model = Attendance
fields = ('id', 'present', 'schedule', 'student',)
最需要的东西是View.py
实际数据正在按我们实际想要的所需格式序列化
class AttendanceView(APIView):
def get(self, request, format=None):
a_list = Attendance.objects.all()
serializer = AttendanceScheduleSerializers(a_list, many=True)
return Response(serializer.data)
def post(self, request, format=None):
present = request.data.get("present")
schedule = request.data['schedule']['id']
student = request.data['student']['id']
data = {'student': student, 'schedule': schedule, 'present': present}
serializer = AttendanceSerializers(data=data)
if serializer.is_valid():
serializer.save()
return Response(serializer.data, status=status.HTTP_201_CREATED)
下面在Views.py需要导入上面
from api.serializers import UserSerializer,AttendanceSerializer, ScheduleSerializer, AttendanceScheduleSerializer
终于得到输出
我想创建一个关于学生 class 出勤的应用程序,格式如下。我在这样的 GET 请求中得到了我需要的实际输出响应。
[
{
"id": 1,
"present": "Yes",
"schedule": {
"id": 2,
"schedule_date": "2019-02-28",
"start_time": "2019-02-28T11:00:00Z",
"end_time": "2019-02-28T11:45:00Z",
"description": "new schedule",
"class_name": 2,
"class_room": 1,
"subject": 2,
"teacher": 3
},
"student": {
"id": 2,
"username": "student",
"email": "",
"first_name": "rakhi",
"last_name": "sawant"
}
},
{
"id": 2,
"present": "No",
"schedule": {
"id": 2,
"schedule_date": "2019-02-28",
"start_time": "2019-02-28T11:00:00Z",
"end_time": "2019-02-28T11:45:00Z",
"description": "new schedule",
"class_name": 2,
"class_room": 1,
"subject": 2,
"teacher": 3
},
"student": {
"id": 5,
"username": "roshanritik",
"email": "ritik@gmail.com",
"first_name": "Ritik",
"last_name": "Roshan"
}
}
]
但是在 POST 请求的情况下,我没有得到我实际需要的格式。我已经给出了这样的输入请求
{
"present" : "Yes",
"student" : {
"id" : 1
},
"schedule" :{
"id" : 2
}
}
并希望 POST 的输出与上述 GET 响应相同。
这是我的Model.py
class Schedule(models.Model):
schedule_date = models.DateField()
start_time = models.DateTimeField()
end_time = models.DateTimeField()
description = models.CharField(max_length=200)
class_name = models.ForeignKey(ClassName, on_delete=models.CASCADE)
class_room = models.ForeignKey(ClassRoom, on_delete=models.CASCADE)
subject = models.ForeignKey(Subject, on_delete=models.CASCADE)
teacher = models.ForeignKey(User, on_delete=models.CASCADE)
def __str__(self):
return self.description
# Student's Attendance Table
class Attendance(models.Model):
present = EnumField(choices=['Yes', 'No'])
student = models.ForeignKey(User, on_delete=models.CASCADE)
schedule = models.ForeignKey(Schedule, on_delete=models.CASCADE)
def __str__(self):
return self.present
class Meta:
unique_together = ('student', 'schedule')
serializer.py
class AttendanceSerializers(serializers.ModelSerializer):
schedule = ScheduleSerializers(many=False, required=False)
student = UserSerializer(many=False, required=False)
class Meta:
model = Attendance
fields = ('id', 'present', 'schedule', 'student')
def create(self, validated_data):
schedule_data = validated_data.pop('schedule')
schedule = SchedulePartialSerializers.create(SchedulePartialSerializers(), validated_data=schedule_data)
student_data = validated_data.pop('student')
student = UserPartialSerializers.create(UserPartialSerializers(), validated_data=student_data)
attendance, created = Attendance.objects.update_or_create(schedule=schedule, student=student,
present=validated_data.pop('present'))
return attendance
Views.py
class AttendanceView(generics.ListCreateAPIView):
queryset = Attendance.objects.all()
serializer_class = AttendanceSerializers
def create(self, request, *args, **kwargs):
write_serializer = AttendanceSerializers(data=request.data)
write_serializer.is_valid(raise_exception=True)
instance = self.perform_create(write_serializer)
read_serializer = AttendanceSerializers(instance)
return Response(read_serializer.data)
userserializer
class UserSerializers(serializers.ModelSerializer):
class Meta:
model = User
fields = ('id', 'first_name')
ScheduleSerializer
class ScheduleSerializers(serializers.ModelSerializer):
class Meta:
model = Schedule
fields = "__all__"
请检查代码。会有帮助。
我们更改了一些代码,例如 Model.py
class Attendance(models.Model):
present = EnumField(choices=['Yes', 'No'])
student = models.ForeignKey(User, on_delete=models.CASCADE)
schedule = models.ForeignKey(Schedule, on_delete=models.CASCADE)
def __str__(self):
return self.present
在Serializer.py
class ScheduleSerializers(serializers.ModelSerializer):
class Meta:
model = Schedule
fields = "__all__"
class UserPartialSerializers(serializers.ModelSerializer):
class Meta:
model = User
fields = ('id', 'first_name')
class AttendanceSerializers(serializers.ModelSerializer):
class Meta:
model = Attendance
fields = '__all__'
class AttendanceScheduleSerializers(serializers.ModelSerializer):
schedule = ScheduleSerializers(many=False)
student = UserSerializer(many=False)
class Meta:
model = Attendance
fields = ('id', 'present', 'schedule', 'student',)
最需要的东西是View.py 实际数据正在按我们实际想要的所需格式序列化
class AttendanceView(APIView):
def get(self, request, format=None):
a_list = Attendance.objects.all()
serializer = AttendanceScheduleSerializers(a_list, many=True)
return Response(serializer.data)
def post(self, request, format=None):
present = request.data.get("present")
schedule = request.data['schedule']['id']
student = request.data['student']['id']
data = {'student': student, 'schedule': schedule, 'present': present}
serializer = AttendanceSerializers(data=data)
if serializer.is_valid():
serializer.save()
return Response(serializer.data, status=status.HTTP_201_CREATED)
from api.serializers import UserSerializer,AttendanceSerializer, ScheduleSerializer, AttendanceScheduleSerializer
终于得到输出