繁体   English   中英

如何在Django Admin中显示关系

[英]How to show relationship in Django Admin

我正在使用Django 2.1,我正在努力弄清楚如何在Admin上显示关系。 我有两个医院和单位模型,第三个是考试。 他们这样设置,医院可以有多个单位,一个单位属于一个医院。 考试模型有考试名称和医院名称等考试属性。

class Hospital(models.Model):

    name = models.CharField(max_length=200)
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)

    def __str__(self):
        return self.name

class Unit(models.Model):

    unit_name = models.CharField(max_length=200)
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)
    parent_company = models.ForeignKey(
        Hospital, related_name='unit_parent', on_delete=models.CASCADE, verbose_name="Hospital")


class Exam(models.Model):

    unit_name = models.ForeignKey(
        Hospital, related_name='hospital_pk', on_delete=models.CASCADE)
    exam_name = models.CharField(max_length=255, blank=True,
                                 null=True, verbose_name="Exam's name")
    date = models.DateField()
    time = models.TimeField()

    def __str__(self):
        return self.exam_name


class CustomExamAdmin(admin.ModelAdmin):

    model = Exam
    list_display = ('exam_name', 'time', 'alert',
                    'document', 'notes', 'report', 'patients_name', 'unit_name')
    list_filter = ('exam_name', 'time')
    list_select_related = ('unit_name',)
    fieldsets = (
        ("Hospital's Name:", {
            'fields': ('unit_name',)}),
        ('Types of Exams:', {
            'fields': ('exam_name', 'modality', 'model_used')}),
        ("Patient's name:", {
            'fields': ('patients_name',)}),
     )

因此,在管理员的考试页面中,我可以选择医院名称,但是我无法选择属于医院的单位。 我需要选择医院以及属于它的单位。 我应该向Exams添加另一个外键,如下所示:unit_selected = models.ForeignKey(Unit,related_name ='unit_pk',on_delete = models.CASCADE)

例如:医院:布鲁克戴尔大学医院单位:市中心单位

我得到的: 在这里输入图像描述

要在Admin选择Unit ,您需要先将其添加到Exam模型中。 您有一个名为unit_name的字段,但您已将其定义为Hospital模型的外键,而不是Unit模型。 如果您有unit_name字段,则实际上并不需要单独的hospital字段,因为您可以从unit_name.parent_company轻松获取它。 所以你可以这样做:

class Exam(models.Model):

    unit_name = models.ForeignKey(
        Unit, related_name='exams', on_delete=models.CASCADE)
    exam_name = models.CharField(max_length=255, blank=True,
                                 null=True, verbose_name="Exam's name")
    date = models.DateField()
    time = models.TimeField()

    def __str__(self):
        return self.exam_name

对于管理员而言,不是单独选择医院和单位,我认为最简单的方法是在管理员中选择医院名称作为单位名称的一部分,如Brookdale University Hospital|Downtown Unit 这样你只需要一个下拉字段。 你可以这样做:

from django import forms


class UnitChoiceField(forms.ModelChoiceField):
     def label_from_instance(self, obj):
         return "{}|{}".format(obj.parent_company.name, obj.unit_name)


class CustomExamAdmin(admin.ModelAdmin):

    model = Exam
    list_display = ('exam_name', 'time', 'alert',
                    'document', 'notes', 'report', 'patients_name', 'get_hospital', 'unit_name')
    list_filter = ('exam_name', 'time')
    list_select_related = ('unit_name__parent_company',)
    fieldsets = (
        ("Hospital's Name:", {
            'fields': ('unit_name',)}),
        ('Types of Exams:', {
            'fields': ('exam_name', 'modality', 'model_used')}),
        ("Patient's name:", {
            'fields': ('patients_name',)}),
     )

    def formfield_for_foreignkey(self, db_field, request, **kwargs):
        if db_field.name == 'unit_name':
            return UnitChoiceField(
                queryset=Unit.objects.all().select_related('parent_company').order_by(
                'parent_company.name', 'unit_name'))
        return super().formfield_for_foreignkey(db_field, request, **kwargs)

    def get_hospital(self, obj):
    #  required to add hospital name to list_display
        return obj.unit_name.parent_company.name           
    get_hospital.short_description = 'Hospital'

另一个注意:在related_nameForeignKeyField是国外模型回您所定义的模型之间的关系。 所以在Unit模型中

parent_company = models.ForeignKey(
    Hospital, related_name='unit_parent', on_delete=models.CASCADE, verbose_name="Hospital")

应该

 parent_company = models.ForeignKey(
    Hospital, related_name='units', on_delete=models.CASCADE, verbose_name="Hospital")

然后从Hospital模型中,您可以将单位列表称为units

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM