AssertionError:`HyperlinkedIdentityField`需要序列化器上下文中的请求 [英] AssertionError: `HyperlinkedIdentityField` requires the request in the serializer context

查看:705
本文介绍了AssertionError:`HyperlinkedIdentityField`需要序列化器上下文中的请求的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想创建一个多对多关系,其中一个人可以在很多俱乐部中,而一个俱乐部可以有很多人。我添加了 models.py serializers.py 的以下逻辑,但是当我尝试在命令中对其进行序列化时提示时,出现以下错误-我在做什么错?我什至没有 HyperlinkedIdentityField

I want to create a many-to-many relationship where one person can be in many clubs and one club can have many persons. I added the models.py and serializers.py for the following logic but when I try to serialize it in the command prompt, I get the following error - What am I doing wrong here? I don't even have a HyperlinkedIdentityField

Traceback (most recent call last):
File "<console>", line 1, in <module>
File "C:\Users\user\corr\lib\site-packages\rest_framework\serializers.py", line 503, in data
ret = super(Serializer, self).data
File "C:\Users\user\corr\lib\site-packages\rest_framework\serializers.py", line 239, in data
self._data = self.to_representation(self.instance)
File "C:\Users\user\corr\lib\site-packages\rest_framework\serializers.py", line 472, in to_representation
ret[field.field_name] = field.to_representation(attribute)
File "C:\Users\user\corr\lib\site-packages\rest_framework\relations.py", line 320, in to_representation"the serializer." % self.__class__.__name__
AssertionError: `HyperlinkedIdentityField` requires the request in the serializer context. Add `context={'request': request}` when instantiating the serializer.

models.py

class Club(models.Model):
    club_name = models.CharField(default='',blank=False,max_length=100)

class Person(models.Model):
    person_name = models.CharField(default='',blank=False,max_length=200)
    clubs = models.ManyToManyField(Club)

serializers.py

class ClubSerializer(serializers.ModelSerializer):
    class Meta:
        model = Club
        fields = ('url','id','club_name','person')

class PersonSerializer(serializers.ModelSerializer):
    clubs = ClubSerializer()
    class Meta:
        model = Person
        fields = ('url','id','person_name','clubs')

views.py

class ClubDetail(generics.ListCreateAPIView):
serializer_class = ClubSerializer

def get_queryset(self):
     club = Clubs.objects.get(pk=self.kwargs.get('pk',None))
     persons = Person.objects.filter(club=club)
     return persons

class ClubList(generics.ListCreateAPIView):
    queryset = Club.objects.all()
    serializer_class = ClubSerializer


class PersonDetail(generics.RetrieveUpdateDestroyAPIView):
    serializer_class = PersonSerializer


def get_object(self):
    person_id = self.kwargs.get('pk',None)
    return Person.objects.get(pk=person_id) 

检查创建的序列化程序可以让我-

Inspecting the created serializer gives me this -

PersonSerializer(<Person: fd>):
url = HyperlinkedIdentityField(view_name='person-detail')
id = IntegerField(label='ID', read_only=True)
person_name = CharField(max_length=200, required=False)
clubs = ClubSerializer():
    url = HyperlinkedIdentityField(view_name='club-detail')
    id = IntegerField(label='ID', read_only=True)
    club_name = CharField(max_length=100, required=False)

但是 serializer.data 给我错误

*************** *** edit *************************
我意识到该错误可能是由于 url 模式,因此我添加了以下网址模式,但仍然出现错误-

******************edit********************* I realized the error could be because of url patterns, so I added the following url patterns but I still get the error -

urlpatterns = format_suffix_patterns([
url(r'^$', views.api_root),
url(r'^clubs/$',
    views.ClubList.as_view(),
    name='club-list'),
 url(r'^clubs/(?P<pk>[0-9]+)/persons/$',
    views.ClubDetail.as_view(),
    name='club-detail'),
url(r'^person/(?P<pk>[0-9]+)/$',
    views.PersonDetail.as_view(),
    name='person-detail'),
])


推荐答案

您收到此错误,因为 HyperlinkedIdentityField 预计会在请求 > context lizer,以便它可以构建绝对URL。在命令行上初始化序列化程序时,您无权访问请求,因此会收到错误。

You're getting this error as the HyperlinkedIdentityField expects to receive request in context of the serializer so it can build absolute URLs. As you are initializing your serializer on the command line, you don't have access to request and so receive an error.

如果需要在命令上检查序列化程序行,您需要执行以下操作:

If you need to check your serializer on the command line, you'd need to do something like this:

from rest_framework.request import Request
from rest_framework.test import APIRequestFactory

from .models import Person
from .serializers import PersonSerializer

factory = APIRequestFactory()
request = factory.get('/')


serializer_context = {
    'request': Request(request),
}

p = Person.objects.first()
s = PersonSerializer(instance=p, context=serializer_context)

print s.data

您的url字段类似于 http:// testserver / person / 1 /

Your url field would look something like http://testserver/person/1/.

这篇关于AssertionError:`HyperlinkedIdentityField`需要序列化器上下文中的请求的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆