0

I'm trying to change the content of a field with my own function. I'm using a simplified function that adds commas between each word. I want to be able to send my comma-fied sentence to the frontend but I don't know how to do that with the serializer that was given in Django documentation. I can't find any examples online of someone trying to do this online. I also need to do this in the backend because some of my other custom functions need access to a specific python library.

Here is my api > views.py

@api_view(['PUT'])
def accentLine(request, pk):
    data = request.data
    line = Lines.objects.get(id=pk)

    if data['accent'] == 'shatner':
        shatnerLine = line.content.replace(' ', ', ')
        line.translation = shatnerLine
        line.save()

    serializer = LineSerializer(instance=line, data=data)

    if serializer.is_valid():
        serializer.save()

    return Response(serializer.data)

Here is my api > models.py

class Lines(models.Model):
    # userId = models.ForeignKey(Users, on_delete=models.CASCADE)
    script = models.ForeignKey(Scripts, null=True, on_delete=models.SET_NULL)
    title = models.CharField(max_length=50, null=True)
    content = models.TextField(max_length=5000, null=True)
    accent = models.CharField(max_length=50, default='english')
    translation = models.TextField(max_length=5000, null=True)
    updatedAt = models.DateField(auto_now=True)

Here is my api > serializers.py

from rest_framework.serializers import ModelSerializer
from .models import Lines

class LineSerializer(ModelSerializer):
    class Meta:
        model = Lines
        fields = '__all__'
6
  • Now you're saving the sentence with commas, right? And response contains that data. What else do you want? Commented May 31, 2022 at 3:41
  • @DavidLu Thank you for responding! Yeah the line gets saved with commas but when I look at serializer it, does not have these changes. I'm guessing because instance=line still represents the sentence without commas. Is there a syntax other than LineSerializer(instance=line, data=data) where I can get the sentence with commas? Or am I missing some other line of code? In my other functions I'm using a python library to convert the sentence to the international phonetic alphabet (ex. yes => ‘jɛs’) Commented Jun 1, 2022 at 0:46
  • Now comma is added only when data['accent'] is shatner, right? Commented Jun 1, 2022 at 2:57
  • @DavidLu Yep a comma is added no problem, it's just not saving in the second portion when I am validating with the serializer. For instance I can add line = Lines.objects.get(id=pk) outside/after the if statement, then if I look at line.translation there are commas. I've tried assigning it again as something else like updatedLine = Lines.objects.get(id=pk) and then using LineSerializer(instance=updatedLine, data=data) but this doesn't work. The only other thing I can think of is making two different routes or just not validating with the serializer and creating my own to_dict() method Commented Jun 1, 2022 at 13:25
  • I think you don't have to replace " " to ", " but just show in the frontend with commas. What do you think? Commented Jun 1, 2022 at 14:28

1 Answer 1

1

First and foremost, you are calling save on the model instance twice by calling it directly on the instance, and then again on the serializer. The serializer save method will perform save on the model instance itself. Docs on saving instances with serializers: https://www.django-rest-framework.org/api-guide/serializers/#saving-instances

To achieve what you want to do you should create a custom serializer field probably called TranslationField and either override the to_internal_value method to perform your string mutations before the data is persisted to the database, or override to_representation which will perform the string mutations before the data is returned from the serializer. It depends on if you wish to persist the field... with commas or add the commas when getting the data via serializer. Docs on custom fields here: https://www.django-rest-framework.org/api-guide/fields/#custom-fields

Once you set up your custom field you will not perform any mutations in your accentLine view and instead simply pass the request data to the serializer like so

@api_view(['PUT'])
def accentLine(request, pk):
    data = request.data
    line = Lines.objects.get(id=pk)

    serializer = LineSerializer(instance=line, data=data)

    if serializer.is_valid():
        serializer.save()

    return Response(serializer.data)
Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.