3

I've been following the tutorial at http://www.django-rest-framework.org/tutorial/4-authentication-and-permissions/ (which is pretty good) but I've got to the end and I'm running the command

http -a admin:password123 POST http://127.0.0.1:8000/snippets/ code="print 789"

and it gives me an error back:

HTTP/1.1 400 Bad Request Allow: GET, POST, HEAD, OPTIONS Content-Length: 37 Content-Type: application/json Date: Wed, 28 Feb 2018 18:29:15 GMT Server: WSGIServer/0.2 CPython/3.6.3 Vary: Accept, Cookie X-Frame-Options: SAMEORIGIN

{ "owner": [ "This field is required." ] }

The owner field is also visible on the browseable api giving options for all the users I've created. When saving it though (either browser or command line) it does save the user who made the request so that part is right. I think its not supposed to be visible on the browseable api and not required on the api call as it figures it out from the request.

Here is my code:

views.py:

class SnippetList(generics.ListCreateAPIView):
  queryset = Snippet.objects.all()
  serializer_class = SnippetSerializer
  permission_classes = (permissions.IsAuthenticatedOrReadOnly,)

  def perform_create(self, serializer):
    serializer.save(owner=self.request.user)

models.py:

class Snippet(models.Model):
  created = models.DateTimeField(auto_now_add=True)
  title = models.CharField(max_length=100, blank=True, default='')
  code = models.TextField()
  linenos = models.BooleanField(default=False)
  language = models.CharField(choices=LANGUAGE_CHOICES, default='python', max_length=100)
  style = models.CharField(choices=STYLE_CHOICES, default='friendly', max_length=100)
  owner = models.ForeignKey('auth.User', related_name='snippets', on_delete=models.CASCADE)
  highlighted = models.TextField()

  class Meta:
    ordering = ('created',)

  def save(self, *args, **kwargs):
    lexer = get_lexer_by_name(self.language)
    linenos = self.linenos and 'table' or False
    options = self.title and {'title': self.title} or {}
    formatter = HtmlFormatter(style=self.style, linenos=linenos, full=True, **options)
    self.highlighted = highlight(self.code, lexer, formatter)
    super(Snippet, self).save(*args, **kwargs)

serializers.py

class SnippetSerializer(serializers.ModelSerializer):
  class Meta:
    model = Snippet
    fields = ('id', 'title', 'code', 'linenos', 'language', 'style', 'owner')
    owner = serializers.ReadOnlyField(source='owner.username')
1
  • Had the same problem. Commenting to add visibility. Commented Sep 26, 2020 at 4:12

2 Answers 2

9

In serializer you define fields as attribute of class, not inside Meta. Try this:

class SnippetSerializer(serializers.ModelSerializer):
  owner = serializers.ReadOnlyField(source='owner.username')
  class Meta:
    model = Snippet
    fields = ('id', 'title', 'code', 'linenos', 'language', 'style', 'owner')
Sign up to request clarification or add additional context in comments.

2 Comments

awesome thanks! I thought I had done something stupid. The tutorial doesn't show the code, just to add the field and I added it to the wrong place.
Had the same issue. Thanks @neverwalkaloner. Makes sense now that I'm looking at the solution. But totally missed this while going through the tutorial.
0
class SnippetList(generics.ListCreateAPIView):
    queryset = Snippet.objects.all()
    serializer_class = SnippetSerializer
    permission_classes = (permissions.IsAuthenticatedOrReadOnly,)

    def perform_create(self, serializer):
        serializer.validated_data['owner'] = self.request.user
        serializer.save()

class SnippetSerializer(serializers.ModelSerializer):
      class Meta:
      model = Snippet
      fields = ('id', 'title', 'code', 'linenos', 'language', 'style', 'owner')
      read_only_fields = ('owner',)

You have to assign value in serializer validated data.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.