如何使用 django rest 框架在模板中获取模型选择字段名称而不是 id

Posted

技术标签:

【中文标题】如何使用 django rest 框架在模板中获取模型选择字段名称而不是 id【英文标题】:How to get Model Choice Field name instead of id in template using django rest framework 【发布时间】:2017-01-04 20:04:04 【问题描述】:

我在模板中获得了选择字段的 ID。但我希望显示选择字段的名称。请查看以下文件并告诉我如何获取名称。

这是我的models.py

================================================ ================

class Posted(models.Model):
    name = models.CharField(_('Posted In'),max_length=255, unique=True)

class Tags(models.Model):
    name = models.CharField(_('Tag Name'),max_length=255, unique=True)

class Blogs(models.Model):
    author = models.ForeignKey(CustomUser)
    title=models.CharField(max_length=100)
    posted=models.ForeignKey(Posted, blank=True)
    tags= models.ManyToManyField(Tags, blank=True)
    content = models.TextField()
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)

序列化器.py


class BlogsSerializer(serializers.ModelSerializer):
    author = AccountSerializer(read_only=True,required=False)
    class Meta:
        model = Blogs
        fields = ('id','author','title','tags','posted','content','created_at','updated_at')
        read_only_fields=('id','created_at','updated_at')

class TagsSerializer(serializers.ModelSerializer):
    name = serializers.SerializerMethodField()   
    class Meta:
        model = Tags 
        fields = ('id','name')
        read_only_fields=('id','name')
class PostedSerializer(serializers.ModelSerializer):
    name = serializers.SerializerMethodField()
    class Meta:
        model = Posted
        fields = ('id','name')
        read_only_fields=('id','name')

views.py


class BlogViewSet(viewsets.ModelViewSet):
    queryset=Blogs.objects.order_by('-created_at')
    serializer_class= BlogsSerializer

    def get_permissions(self):
        if self.request.method in permissions.SAFE_METHODS:
            return (permissions.AllowAny(),)
        return (permissions.IsAuthenticated(),IsAuthorOfBlog(),)

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

        return super(BlogViewSet,self).perform_create(serializer)

class TagsViewSet(viewsets.ModelViewSet):
    queryset=Tags.objects.all
    serializer_class= TagsSerializer

class PostedViewSet(viewsets.ModelViewSet):
    queryset=Posted.objects.all
    serializer_class= PostedSerializer

模板

<div class="row">
  <div class="col-sm-12">
    <div class="well">
      <div class="blog">
        <div class="blog__meta">
          <a href="#">
            + blog.author.first_name 
          </a>
        </div>

        <div class="blog__content">
          <p> blog.title </p>
          <p> blog.posted</p>
          <p> blog.tags</p>
          <p> blog.content </p>

        </div>
      </div>
    </div>
  </div>
</div>

提前致谢

【问题讨论】:

【参考方案1】:

你所说的选择是什么意思?我在 Field kwargs 中看不到 choices。您可以通过例如设置选择字段: chairs = models.IntegerField(max_length=255, choices=CHOICES) 你到底从哪里得到 id 而不是 name ?

【讨论】:

选项来自两个表。发布和标记 .modelchoicefields 我重新创建了你的环境,这就是我完成的:在你的 BlogsSerializer 添加你的序列化程序,这会给你正确的 json 输出:class BlogsSerializer(serializers.ModelSerializer): posted = PostedSerializer() tags = TagsSerializer(many=True) 请注意,因为标签是多对多的关系,我们需要传递 kwarg many=True 并作为未来提示 - 在您的情况下尝试为模型使用单数名称,它将是 BlogTag 等。【参考方案2】:

您可以使用SlugRelatedField 选项将特定字段作为关系对象返回。例如,

class BlogsSerializer(serializers.ModelSerializer):
author = AccountSerializer(read_only=True,required=False)
tags = serializers.SlugRelatedField(
    many=True,
    read_only=True,
    slug_field='name'
 )
class Meta:
    model = Blogs
    fields = ('id','author','title','tags','posted','content','created_at','updated_at')
    read_only_fields=('id','created_at','updated_at')

【讨论】:

【参考方案3】:

感谢@Karol Sztajerwald。 是的,BlogsSerializer 必须这样制作。

最终博客 Serializer.py 是

class TagsSerializer(serializers.ModelSerializer):
    class Meta:
        model = Tags

        fields = ('id','name')
        read_only_fields=('id','name')

class PostedSerializer(serializers.ModelSerializer):
    class Meta:
        model = Posted

        fields = ('id','name')
        read_only_fields=('id','name')
class BlogsSerializer(serializers.ModelSerializer):
    author = AccountSerializer(read_only=True,required=False)
    tags=TagsSerializer(many=True)
    posted=PostedSerializer()
    class Meta:
        model = Blogs

        fields = ('id','author','title','tags','posted','content','created_at','updated_at')
        read_only_fields=('id','created_at','updated_at')

模板是

<p> blog.title </p>
<p> blog.posted.name</p>
<p> blog.tags.name</p>
<p> blog.content </p>

【讨论】:

以上是关于如何使用 django rest 框架在模板中获取模型选择字段名称而不是 id的主要内容,如果未能解决你的问题,请参考以下文章

如何修复 Python(Django Rest 框架模板)中的 UnicodeDecodeError?

如何在 django rest 框架中获取与外键相关的数据?

在 HTML 页面或模板中使用 Django-REST-Framework 从在 Django 中创建的 API 获取/显示 API 数据

你如何在 django rest 框架中实现 CSRF 令牌?

Django REST 框架。如何获取包含协议、域和路径的页面的完整 url?

django rest框架:在视图中获取url路径变量