Skip to main content

image

image

image


Django REST Typed models

Based on the great work django-rest-typed-models by denisorehovsky

Typed model serializers for Django REST Framework.

Overview

django-rest-typed-models allows you to easily define serializers for your inherited models that you have created using django-typed-models library.

Installation

Install using pip:

$ poetry add django-rest-typed-models

Usage

Define your typed models:

# models.py
from django.db import models
from typedmodels.models import TypedModel

class Project(TypedModel):
    topic = models.CharField(max_length=30)


class ArtProject(Project):
    artist = models.CharField(max_length=30)


class ResearchProject(Project):
    supervisor = models.CharField(max_length=30)

Define serializers for each typed model the way you did it when you used django-rest-framework:

# serializers.py
from rest_framework import serializers
from .models import Project, ArtProject, ResearchProject


class ProjectSerializer(serializers.ModelSerializer):
    class Meta:
        model = Project
        fields = ('topic', )


class ArtProjectSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model = ArtProject
        fields = ('topic', 'artist', 'url')
        extra_kwargs = {
            'url': {'view_name': 'project-detail', 'lookup_field': 'pk'},
        }


class ResearchProjectSerializer(serializers.ModelSerializer):
    class Meta:
        model = ResearchProject
        fields = ('topic', 'supervisor')

Note that if you extend HyperlinkedModelSerializer instead of ModelSerializer you need to define extra_kwargs to direct the URL to the appropriate view for your typed model serializer.

Then you have to create a typed model serializer that serves as a mapper between models and serializers which you have defined above:

# serializers.py
from rest_typed_models.serializers import TypedModelSerializer


class ProjectTypedModelSerializer(TypedModelSerializer):
    model_serializer_mapping = {
        Project: ProjectSerializer,
        ArtProject: ArtProjectSerializer,
        ResearchProject: ResearchProjectSerializer
    }

Create viewset with serializer_class equals to your polymorphic serializer:

# views.py
from rest_framework import viewsets
from .models import Project
from .serializers import ProjectTypedModelSerializer


class ProjectViewSet(viewsets.ModelViewSet):
    queryset = Project.objects.all()
    serializer_class = ProjectTypedModelSerializer

Test it:

$ http GET "http://localhost:8000/projects/"
HTTP/1.0 200 OK
Content-Length: 227
Content-Type: application/json

[
    {
        "resourcetype": "Project",
        "topic": "John's gathering"
    },
    {
        "artist": "T. Turner",
        "resourcetype": "ArtProject",
        "topic": "Sculpting with Tim",
        "url": "http://localhost:8000/projects/2/"
    },
    {
        "resourcetype": "ResearchProject",
        "supervisor": "Dr. Winter",
        "topic": "Swallow Aerodynamics"
    }
]
$ http POST "http://localhost:8000/projects/" resourcetype="ArtProject" topic="Guernica" artist="Picasso"
HTTP/1.0 201 Created
Content-Length: 67
Content-Type: application/json

{
    "artist": "Picasso",
    "resourcetype": "ArtProject",
    "topic": "Guernica",
    "url": "http://localhost:8000/projects/4/"
}

Customize resource type

As you can see from the example above, in order to specify the type of your typed model, you need to send a request with resource type field. The value of resource type should be the name of the model.

If you want to change the resource type field name from resourcetype to something else, you should override resource_type_field_name attribute:

class ProjectTypedModelSerializer(TypedModelSerializer):
    resource_type_field_name = 'projecttype'
    ...

If you want to change the behavior of resource type, you should override to_resource_type method:

class ProjectTypedModelSerializer(TypedModelSerializer):
    ...

    def to_resource_type(self, model_or_instance):
        return model_or_instance._meta.object_name.lower()

Now, the request for creating new object will look like this:

$ http POST "http://localhost:8000/projects/" projecttype="artproject" topic="Guernica" artist="Picasso"

Metadata

Release files for django-rest-typed-models 0.1.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for django-rest-typed-models 0.1.0
File Size Uploaded Provenance
django_rest_typed_models-0.1.0.tar.gz 5.4 kB Without provenance Details

Built distribution (wheel)

Table of built distributions (wheels) for django-rest-typed-models 0.1.0
File Interpreter ABI Platform
django_rest_typed_models-0.1.0-py3-none-any.whl Python 3 none any Details

Total release size: 11.0 kB

Release files / django_rest_typed_models-0.1.0.tar.gz

Download URL django_rest_typed_models-0.1.0.tar.gz
Size 5.4 kB
Tags Source
SHA-256 checksum
How to use checksums
988b8da888f7c2c51f13b8a9699ec99e5e877b927cbd3aeeb70b6aa7bc44ae41
BLAKE2b-256 checksum
How to use checksums
31f821b02983263097a3db3c9d691f5f9190e5f37a52190586797be0bce34053
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via poetry/1.2.2 CPython/3.9.15 Darwin/21.4.0

Release files / django_rest_typed_models-0.1.0-py3-none-any.whl

Download URL django_rest_typed_models-0.1.0-py3-none-any.whl
Size 5.6 kB
Tags Python 3
SHA-256 checksum
How to use checksums
3ba5b7e078e35d372eaf773dfc529c90ac65916fd1869e7d0cafcf9f2acbf952
BLAKE2b-256 checksum
How to use checksums
27a4ed5b5160743f4a22399421a0e323c245bfc5db3beefd6b47e7c4eab4d380
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via poetry/1.2.2 CPython/3.9.15 Darwin/21.4.0

Security for django-rest-typed-models 0.1.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.1.0 This release

2 release files No provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page