【问题标题】:Django admin InlineModels for manytomany fields多对多字段的 Django admin InlineModels
【发布时间】:2016-03-21 00:30:59
【问题描述】:

我为我的博客设计了以下模型

from django.db import models

class Post(models.Model):
    title = models.CharField(max_length=200)
    body = models.TextField(default='')
    created_at = models.DateTimeField('created date', auto_now_add=True, auto_now=False)
    updated_at = models.DateTimeField('updated date', auto_now_add=False, auto_now=True)
    author = models.ForeignKey('Author', default='admin')

    def __str__(self):
        return self.title


class Author(models.Model):
    name = models.CharField(max_length=150)
    email = models.EmailField(blank=True)
    bio = models.TextField()

    def __str__(self):
        return self.name

class Category(models.Model):
    cat_name = models.CharField(max_length=200)
    post = models.ManyToManyField('Post')

    def __str__(self):
        return self.cat_name

class Tag(models.Model):
    tag_name = models.CharField(max_length=200)
    post = models.ManyToManyField('Post')

    def __str__(self):
        return self.tag_name

我正在尝试以这样的方式在 django admin 下注册此模型。我可以从帖子页面编辑类别、标签和作者。但是我很难完成这个演讲,我已经在 admin.py 文件中编写了这段代码

from django.contrib import admin
from .models import Post, Author, Tag, Category

class AuthorInline(admin.TabularInline):
    model= Author

class TagInline(admin.StackedInline):
    model= Tag

class CategoryInline(admin.StackedInline):
    model = Category

@admin.register(Post) #another method of registration admin.site.register(Post, PostAdmin)
class PostAdmin(admin.ModelAdmin):
    #Show the following fields in this order
    fields = ['body', 'title']
    #show the following filelds for nice formattng 
    list_display = ['title', 'author', 'created_at']
    #display based on the date hirerarchy
    date_hierachy = 'created_at'
    #embed the following child models in this parent models
    inlines = [AuthorInline, TagInline, CategoryInline,]

    #to exclude fields
    exclude = ('author',)

当我运行我的服务器时,我得到了类似的错误

ERRORS:
<class 'blogs.admin.AuthorInline'>: (admin.E202) 'blogs.Author' has no ForeignKey to 'blogs.Post'.
<class 'blogs.admin.CategoryInline'>: (admin.E202) 'blogs.Category' has no ForeignKey to 'blogs.Post'.
<class 'blogs.admin.TagInline'>: (admin.E202) 'blogs.Tag' has no ForeignKey to 'blogs.Post'.

在调查错误时,如果模型没有外键,我们不能有 StackedInline 类,但是如何将标签、类别和作者呈现形式放在 django admin 的帖子页面下,

【问题讨论】:

    标签: python django django-models django-admin django-admin-tools


    【解决方案1】:

    这不是内联的用途,你不希望它们在这里。

    内联用于反向关系:给定作者,编辑他们的详细信息并在同一页面上输入他们的所有书籍。您的外键和多对多字段最好显示为简单的小部件,这是 Django 默认所做的;作者和类别将显示为允许您选择项目的下拉列表,并且标签将显示为多选框。

    您也可以选择在作者管理员中将 Book 注册为内联;这取决于你。

    【讨论】:

    • 没有在我的帖子页面中,我可以看到 post_title、post_body、author 作为下拉列表,这里没有显示类别和标签
    【解决方案2】:

    为了使用 AuthorInline,您需要在 Author 模型中定义一个外键字段

    例如:

    class Author(models.Model):
        post = models.ForeignKey('Post')
    

    这意味着一篇文章可能有多个作者。

    但在您的情况下,您拥有正确的模型和文件,其中一篇文章只有一位作者,因此您可以删除 AuthorInline。

    如果是标签和类别,您使用的是多对多字段,如果您阅读此文档会很好https://docs.djangoproject.com/en/dev/ref/contrib/admin/#working-with-many-to-many-models

    你必须重写 CategoryInline 和 TagInline;

    class TagInline(admin.StackedInline):
        model= Tag.post.through
    
    class CategoryInline(admin.StackedInline):
        model = Category.post.through
    

    【讨论】:

    • 但是第一个逻辑会改变我的业务逻辑,因为我希望一个作者可以有很多帖子,但两个作者不能共同创作一个帖子。对于其他内联,我将检查文档
    • 那么你必须在 Author 模型中添加一个外键字段,并在 Post 中删除 author 字段;或者您应该将作者字段更改为 maytomany 而不是外键
    【解决方案3】:

    最后我做了,我想要的,主要是让文章页面中可以选择类别、作者和标签,所以要做到这一点,我们需要在文章模型中添加所有字段,也就是修改后的型号

    from django.db import models
    from django.utils import timezone
    
    class Author(models.Model):
        first_name = models.CharField(max_length=50)
        last_name = models.CharField(max_length=50)
        email = models.EmailField(blank=True)
        bio = models.TextField()
    
    
    class Tag(models.Model):
        tag_name = models.CharField(max_length=50)
    
    class Category(models.Model):
        cat_name = models.CharField(max_length=50)
    
    class Post(models.Model):
        '''post can have many categories 
        and categories can have many post
        author can have many post but post
        can have single author
        post can have many tags, and tags 
        can have many posts'''
    
        title = models.CharField('post title', max_length=200)
        body = models.TextField(default='', null=True)
        created_at = models.DateTimeField(auto_now_add=True, auto_now=False)
        updated_at = models.DateTimeField(auto_now_add=False, auto_now=True)
        author = models.ForeignKey(Author, verbose_name = "List of Author") #many to one relationship
    
        def __str__(self):
            return self.title
    
        #Generally many to many fields should into that model which is going to be edited.
        tags = models.ManyToManyField(Tag)
        categories = models.ManyToManyField(Category)
    
        class Meta:
            ordering = ['-created_at']
            verbose_name_plural = "Posteeees"
    
    
        # def post_status(self):
        # return timezone.now() - self.updated_at <= 1
    
    
    
    #Recursive realation, we can define the foreignkey itself to the model  and this is called rrecursive realation
    #
    

    【讨论】:

      猜你喜欢
      • 2016-02-23
      • 1970-01-01
      • 1970-01-01
      • 2021-08-01
      • 2012-05-15
      • 2013-11-17
      • 2021-06-01
      • 2011-07-20
      • 2013-09-14
      相关资源
      最近更新 更多