对模型使用自定义方法而不是 __unicode__/__str__?

Posted

技术标签:

【中文标题】对模型使用自定义方法而不是 __unicode__/__str__?【英文标题】:use custom method instead of __unicode__/__str__ for a Model? 【发布时间】:2016-02-06 20:48:25 【问题描述】:

我有两个模型,

class Person(models.Model):
    first_name = models.CharField(max_length=50)
    last_name = models.CharField(max_length=50)
    surname = models.CharField(max_length=50)

    def __unicode__(self):
        return self.first_name

    def get_last_name(self):
        return self.last_name

    def get_full_name(self):
        return (self.first_name + self.surname + self.last_name)

class House(models.Model):
    name = models.CharField(max_length=50)
    persons = models.ManyToManyField(Person)
    house_number = models.CharField(max_length=5)

    def __unicode__(self):
        return self.first_name

并且模型已在管理站点上注册。

@admin.register(Person)
class PersonAdmin(admin.ModelAdmin):
    pass

@admin.register(House)
class HouseAdmin(admin.ModelAdmin):
    pass

对于模型Person,我希望管理站点在模型HouseManyToManyField 上显示方法get_full_name() 而不是__unicode__()get_last_name

我怎样才能做到这一点?

谢谢

【问题讨论】:

澄清一下,对于Person,您希望在管理员中使用get_full_name(),但在其他任何地方使用first_name @MikeCovington,对于person,我希望人员管理网址/admin/app/person 在模型House 和@987654338 的ManyToManyField 上显示get_full_name()get_last_name @其他地方。 【参考方案1】:

要让PersonAdmin 使用get_full_name,只需在list_display 中使用get_full_name

@admin.register(Person)
class PersonAdmin(admin.ModelAdmin):
    list_display = ['get_full_name']

要自定义人员在多对多字段中的显示方式,override the label_from_instance method。

from django.forms import ModelMultipleChoiceField

class PersonLastNameChoiceField(ModelMultipleChoiceField):
    def label_from_instance(self, obj):
        return obj.get_last_name

定义一个使用您的自定义字段的模型表单,

class HouseForm(forms.ModelForm):
    persons = models.PersonLastNameChoiceField(Person.objects.all())

然后在模型管理中使用模型表单。

@admin.register(House)
class HouseAdmin(admin.ModelAdmin):
    form = HouseForm

【讨论】:

我应该把PersonLastNameChoiceField放在哪里? 随心所欲。你只在模型管理员中使用它,那么admin.py 就可以了。如果您在其他地方重用它,那么您可能想要一个单独的模块,例如fields.py,然后导入。【参考方案2】:

阅读代理模型。代理模型的典型用例是通过更改模型的默认管理器或类方法来覆盖模型的 Python 行为。

class PersonAdmin(Person):
    class Meta:
        proxy = True
    def __unicode__(self):
        return self.get_full_name()

更多信息请阅读:Multiple ModelAdmins/views for same model in Django admin

【讨论】:

以上是关于对模型使用自定义方法而不是 __unicode__/__str__?的主要内容,如果未能解决你的问题,请参考以下文章

Django - 在管理页面中显示“模型对象”而不是对象标题

关于django模型里面的__str__和__unicode

django模型中的__str__()方法和__unicode__()方法

在 ModelChoiceField Django 中使用 __unicode__ 以外的方法

django __unicode__() - 我如何在模板中调用此方法

python中__unicode__方法的使用