Django Rest Framework ModelViewSets with natural key lookup

DRF ModelViewSet can easily support detail views by slug via the lookup_value attribute. But what if you had compound keys (aka natural keys)? For example a url structure like


A computer slug may only be unique per organization. That means different organizations may have computers with the same slug. But no computer may have the same slug in one organization. By using both slugs, we can look up a specific computer. We can use the lookup_value_regex attribute for this.

class ComputerViewSet(viewsets.ModelViewSet):
    queryset = Computer.objects.all()
    serializer_class = ComputerSerializer
    lookup_value_regex = r"(?P<org_slug>[^/.]+)/(?P<slug>[-\w]+)"

    def get_object(self):
        queryset = self.filter_queryset(self.get_queryset())
        obj = get_object_or_404(

        # May raise a permission denied
        self.check_object_permissions(self.request, obj)

        return obj

This works with drf-nested-routers. For example, we could add a nested /hard_drives viewset. The url values are in self.kwargs.

class HardDriveViewSet(viewsets.ModelViewSet):
    queryset = HardDrive.objects.all()
    serializer_class = HardDriveSerializer

    def get_queryset(self):
        return (

By David

I am a supporter of free software and run Burke Software and Consulting LLC. I am always looking for contract work especially for non-profits and open source projects. Open Source Contributions I maintain a number of Django related projects including GlitchTip, Passit, and django-report-builder. You can view my work on gitlab. Academic papers Incorporating Gaming in Software Engineering Projects: Case of RMU Monopoly in the Journal of Systemics, Cybernetics and Informatics (2008)

Leave a comment

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

%d bloggers like this: