2

I am running a Django 2.0 and DRF (Django REST Framework) 3.8.0.

I want to be able to GET JSON in a specific format as seen in GOAL NESTED JSON ARRAY.

Right now, I am able to retrieve an JSON Array as shown in MY CURRENT JSON ARRAY. I have checked this question and it seems like we have the goal but i was unable to be successful.

I have my model, view and serializer below. This is achieved by using this:

GET /studentlectures/1/get_studlect/ where 1 is {pk}

CURRENT JSON ARRAY:

[
{
    "id": 1,
    "lecture": 1,
    "student": 1
},
{
    "id": 19,
    "lecture": 4,
    "student": 1
}
]

GOAL NESTED JSON ARRAY

{
        "id": 1,
        "student_code": "60637-009",
        "first_name": "Zoltan",
        "last_name": "Drogo",
        "lectures": [
            {
                "lecture_id": 1,
                "subject_name": "English",
                "teacher_id": 1,
                "teacher_name": "Cirillo Kierans",
                "room": "Room A",
                "schedule": "08:00 AM - 10:00 AM"
            },
            {
                "lecture_id": 2,
                "subject_name": "Math",
                "teacher_id": 3,
                "teacher_name": "Johanna Probate",
                "room": "Room C",
                "schedule": "08:00 AM - 10:00 AM"
            },
            . . . . . . 
}

MODEL:

class Studentlecture(models.Model):
    student = models.ForeignKey(Student, default='')
    lecture = models.ForeignKey(Lecture, default='')
    studentlecture_name = models.CharField(max_length=20, default='ComputerScience Lectures')

    def __str__(self):
        return f'{self.studentlecture_name}'

VIEW:

class StudentlectureViewSet(ModelViewSet):
    """
    API endpoint that allows groups to be viewed or edited.
    """
    serializer_class = StudentlectureSerializer
    queryset = Studentlecture.objects.all()
    permission_classes = (permissions.IsAuthenticatedOrReadOnly,)

    #/studentlectures/{pk}/get_studlect/ gives the lectures of student pk
    @action(detail=True)
    def get_studlect(self, request, *args, **kwargs):
        student_lectures = Studentlecture.objects.all().filter(student_id=self.kwargs['pk'])
        serializer = self.get_serializer(student_lectures, many=True)
        return Response(serializer.data)

    #/studentlectures/{pk}/get_lectstud/ gives the students of lecture pk
    @action(detail=True)
    def get_lectstud(self, request, *args, **kwargs):
        lecture_students = Studentlecture.objects.all().filter(lecture_id=self.kwargs['pk'])
        serializer = self.get_serializer(lecture_students, many=True)
        print(serializer)
        return Response(serializer.data)

SERIALIZER:

class StudentlectureSerializer(serializers.ModelSerializer):
    class Meta:
        model = Studentlecture
        fields = ('url', 'id', 'lecture', 'student')

2 Answers 2

0

You can use RelatedField for that:

Serializer

from rest_framework.serializers import ModelSerializer, IntegerField

from lectures.fields import LectureRelatedField

class StudentLectureSerializer(ModelSerializer):
    id = IntegerField(read_only=True)
    lecture = LectureRelatedField(
        queryset=Lecture.objects.all(), required=True
    )
    ...

lectures.fields

from rest_framework.serializers import RelatedField

class LectureRelatedField(RelatedField):
    def to_representation(self, obj):
        data = {
            'lecture_id': obj.lecture_id,
            'subject_name': obj.subject_name,
            'teacher_id': obj.teacher_id,
            'teacher_name': obj.teacher_name,
            'room': obj.room,
            'schedule': obj.schedule
        }
        return data

    def to_internal_value(self, pk):
        return Lecture.objects.get(id=pk)

As a result you will get a json like this while making requests:

"lectures": [
    {
        "lecture_id": 1,
        "subject_name": "English",
        "teacher_id": 1,
        "teacher_name": "Cirillo Kierans",
        "room": "Room A",
        "schedule": "08:00 AM - 10:00 AM"
    },
Sign up to request clarification or add additional context in comments.

Comments

0

Haven't been able to check back right away, but this what I have done:

#/studentlectures/{pk}/get_studlect/ gives the lectures of student pk
@action(detail=True)
def get_studlect(self, request, *args, **kwargs):
    student_lectures = Studentlecture.objects.all().filter(student_id=self.kwargs['pk'])
    serializer = self.get_serializer(student_lectures, many=True)

    student = Student.objects.filter(id=self.kwargs['pk'])
    lecture_nest = serializer.data        

    data = {
      "id": student.values()[0]['id'],
      "student_code": student.values()[0]['student_code'],
      "first_name": student.values()[0]['first_name'],
      "last_name": student.values()[0]['last_name'],
      "lectures": lecture_nest
    }

    return Response(data)

I adapted Madi7's answer a bit and I know it looks really dirty but I am changing projects now.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.