Redirect viewset to another viewset on Django Rest Framework after parsing data

121 views Asked by At

Say I have a viewset A, where I will receive a bunch of data via querystring. I want to parse this querystring on viewset A, and then redirect the request with the parsed querystring to viewset B. How would I go about doing this?

I've tried insatiating the viewset B inside of A and then calling the get method manually to no avail.

1

There are 1 answers

3
Mihail Andreev On BEST ANSWER

If you want to redirect from an action in ViewsetA to an action in ViewsetB, here's how you can do it using the two different approaches mentioned before:

HTTP Redirect Approach:

Redirecting via HTTP will involve creating a URL for the action in ViewsetB and then sending an HTTP 302 response to redirect the client to that URL.

from rest_framework import viewsets, status
from rest_framework.decorators import action
from rest_framework.response import Response
from django.urls import reverse
from urllib.parse import urlencode

class ViewsetA(viewsets.ViewSet):

    @action(detail=False, methods=['GET'])
    def action_in_a(self, request):
        # Do your parsing here
        parsed_data = parse_querystring(request.GET)
        
        # Prepare the new URL for the action in ViewsetB
        new_url = reverse('viewsetb-action_in_b') + '?' + urlencode(parsed_data)
        
        # Redirect to action in Viewset B
        return Response(status=status.HTTP_302_FOUND, headers={'Location': new_url})

class ViewsetB(viewsets.ViewSet):

    @action(detail=False, methods=['GET'])
    def action_in_b(self, request):
        # Handle your request as needed
        return Response(data={"message": "Handled in ViewsetB's action"})

Internal Invocation Approach:

This will involve manually invoking the action in ViewsetB from within ViewsetA.

from rest_framework import viewsets
from rest_framework.decorators import action
from rest_framework.response import Response

class ViewsetA(viewsets.ViewSet):

    @action(detail=False, methods=['GET'])
    def action_in_a(self, request):
        # Do your parsing here
        parsed_data = parse_querystring(request.GET)

        # Manually instantiate and invoke action in Viewset B
        viewset_b = ViewsetB()
        viewset_b.request = request
        viewset_b.format_kwarg = self.format_kwarg
        viewset_b.args = self.args
        viewset_b.kwargs = self.kwargs
        
        # Add parsed_data to the request or any other adjustments
        viewset_b.request.GET = parsed_data

        return viewset_b.action_in_b(request)

class ViewsetB(viewsets.ViewSet):

    @action(detail=False, methods=['GET'])
    def action_in_b(self, request):
        # Handle your request as needed
        return Response(data={"message": "Handled in ViewsetB's action"})