Sam R.
Sam R.

Reputation: 16450

django-rest-framework How to handle multiple URL parameter?

How can I use generic views with multiple URL parameters? Like

GET /author/{author_id}/book/{book_id}

class Book(generics.RetrieveAPIView):

    queryset = Book.objects.all()
    serializer_class = BookSerializer
    lookup_field = 'book_id'
    lookup_url_kwarg = 'book_id'

    # lookup_field = 'author_id' for author
    # lookup_url_kwarg = 'author_id'

Upvotes: 6

Views: 4249

Answers (3)

Hank
Hank

Reputation: 1688

Might be late to the party here, but this is what I do:

class Book(generics.RetrieveAPIView):

    serializer_class = BookSerializer
    
    def get_queryset(self):
           book_id = self.kwargs['book_id']
           author_id = self.kwargs['author_id']     
           
           return Book.objects.filter(Book = book_id, Author = author_id)

Upvotes: 3

talz
talz

Reputation: 1200

Just add a little custom Mixin:

in urls.py:

...

path('/author/<int:author_id>/book/<int:book_id>', views.Book.as_view()),

...

in views.py: Adapted from example in the DRF documentation:

class MultipleFieldLookupMixin:
    def get_object(self):
        queryset = self.get_queryset()                          # Get the base queryset
        queryset = self.filter_queryset(queryset)               # Apply any filter backends
        multi_filter = {field: self.kwargs[field] for field in self.lookup_fields}
        obj = get_object_or_404(queryset, **multi_filter)       # Lookup the object
        self.check_object_permissions(self.request, obj)
        return obj


class Book(MultipleFieldLookupMixin, generics.RetrieveAPIView):
    queryset = Book.objects.all()
    serializer_class = BookSerializer
    lookup_fields = ['author_id', 'book_id']    # possible thanks to custom Mixin

Upvotes: 4

Related Questions