Reputation: 809
New to DRF (and REST in general).
Models:
class Event(models.Model):
name = models.CharField()
class Result(models.Model):
event = models.ForeignKey(Event, related_name='results')
person = models.CharField()
score = models.IntegerField()
Serializers:
class ResultSerializer(serializers.ModelSerializer):
class Meta:
model = Result
class EventSerializer(serializers.HyperlinkedModelSerializer):
class Meta:
model = Event
Viewsets:
class ResultViewSet(viewsets.ModelViewSet):
queryset = Result.objects.all()
serializer_class = ResultSerializer
class EventViewSet(viewsets.ModelViewSet):
queryset = Event.objects.all()
serializer_class = EventSerializer
Router:
router = routers.DefaultRouter()
router.register(r'events', EventViewSet)
URL:
urlpatterns = [
url(r'^api/', include(router.urls)),
]
This works fine, I can go to http://mysite/api and see "events" with a link to http://mysite/api/events/. From there each event has a link to http://mysite/api/events/id. So far so good.
If I change the event serializer to this, it will also include all the results (for that event) from Result:
class EventSerializer(serializers.HyperlinkedModelSerializer):
results = ResultSerializer(many=True, read_only=True)
class Meta:
model = Event
This also works fine. But I don't want the (often very long) results to be included for each event at http://mysite/api/events. There are way too many. I'd only like to see results included when I go to http://mysite/api/events/id.
Any tips on how I can get from where I am to where I want to be? It would be even better if each item on http://mysite/api/events included a count of the results, then http://mysite/api/events/id actually had the results.
Hope this made sense. Thanks.
Upvotes: 1
Views: 46
Reputation: 47846
We can create 2 serializers EventSerializer
and EventDetailSerializer
which will return different serialized representations based on the type of request.
class EventSerializer(serializers.HyperlinkedModelSerializer):
class Meta:
model = Event
class EventDetailSerializer(serializers.HyperlinkedModelSerializer):
results = ResultSerializer(many=True, read_only=True) # contain the serialized results
class Meta:
model = Event
Then we will override the get_serializer_class()
of EventViewSet
which return EventDetailSerializer
in case of retrieve
requests and EventSerializer
otherwise.
class EventViewSet(viewsets.ModelViewSet):
queryset = Event.objects.all()
def get_serializer_class(self):
if self.action == 'retrieve': # check if a 'retrieve' request
return EventDetailSerializer
return EventSerializer # otherwise return this serializer
Upvotes: 1