Reputation: 93
I'm new to Django. Within the Django rest framework, I'm struggling with the put & post request on a table that's linked to other table(s).
The main table I want to update via API is person
, that's basically where contact details are kept. It joins to 2 other tables, email
, phone
, where each of them only contains 1 piece of information (as their name stated). What I'm trying to achieve is that when I submit a put/post request to person
's api, it also updates email
, phone
without needing to update each of them respectively.
Below are some code:
Models:
class Person(models.Model):
id = models.AutoField(primary_key=True)
last_name = models.CharField(max_length=50)
first_name = models.CharField(max_length=50)
email = models.ManyToManyField('Email')
phone = models.ManyToManyField('Phone')
class Meta:
ordering = ['last_name', 'first_name']
def __str__(self):
return f'{self.first_name} {self.last_name}'
class Phone(models.Model):
phone = models.CharField(max_length=50, blank=True, null=True)
def __str__(self):
return f'{self.phone}'
class Email(models.Model):
email = models.CharField(max_length=50, blank=True, null=True)
def __str__(self):
return f'{self.email}'
Serializers:
class PersonSerializer(serializers.ModelSerializer):
email = serializers.StringRelatedField(many=True)
phone = serializers.StringRelatedField(many=True)
class Meta:
model = Person
fields = ('id', 'last_name', 'first_name', 'email', 'phone')
class PhoneSerializer(serializers.ModelSerializer):
class Meta:
model = Phone
fields = ('id', 'phone')
class EmailSerializer(serializers.ModelSerializer):
class Meta:
model = Email
fields = ('id', 'email')
Views:
class PersonViewSet(viewsets.ModelViewSet):
queryset = Person.objects.all()
serializer_class = PersonSerializer
class PhoneViewSet(RetrieveAPIView):
queryset = Phone.objects.all()
serializer_class = PhoneSerializer
class EmailViewSet(RetrieveAPIView):
queryset = Email.objects.all()
serializer_class = EmailSerializer
In the person
API detailed view, under put request, email
and phone
fields are currently grayed out and says "No items to select", I'm hoping to be able to enter values in there, and can successfully submit the put/post request via the front end (React) of my app.
I've been stucking here for weeks, any help would be appreciated!
Thanks
Upvotes: 1
Views: 1483
Reputation: 93
I might be able to answer my own question now, also in case someone else is having the same issue. This is how I resolved it.
As @JPG mentioned, you can also override the update
and/or create
method to define how to handle related fields explicitly, but there is a way easier approach.
from drf_writable_nested import WritableNestedModelSerializer
class PersonSerializer(WritableNestedModelSerializer):
last_name = serializers.CharField(required=True, max_length=100)
first_name = serializers.CharField(required=True, max_length=100)
address = AddressSerializer(many=True)
email = EmailSerializer(many=True)
phone = PhoneSerializer(many=True)
class Meta:
model = Person
fields = ('id', 'last_name', 'first_name', 'address', 'email', 'phone', 'group')
Upvotes: 1