8

I try to make one field in django admin's fieldsets to show only certain data, but according to django document, only an example of list_display is shown to be able to customize. I tried the similar approach on fieldsets like the following:

In models.py:

def ports_with_same_scanner(self):
    return PortList.objects.filter(scanner=self.scanner)
ports_with_same_scanner.short_description = 'port_lists'

In admin.py, this won't work:

fieldsets = (
            ('Scan Template', { 
            'fields': ( ('name', 'scanner', 'ports_with_same_scanner',), 'comment', ('in_use',
                'fc_growing', 'nc_growing'), 'nvt_prefs')
            }),
)

However, if I do this:

list_display = ('name', 'scanner', 'ports_with_same_scanner', 'comment', 'in_use', 'fc_growing', 'nc_growing', 'nvt_prefs')

the ports_with_same_scanner works just fine. The problem is that I don't want to change my display from fieldsets to list_display, I wonder how can I achieve the same functionality. Thanks.

Shang Wang
  • 24,909
  • 20
  • 73
  • 94

2 Answers2

7

I don't know if real problem at past ... I always using simple approach - to adding a name of method to the readonly_fields = ()

Example:

models.py

class My(models.Model):

    def custom_name(self):
        return 'test'
    custom_name.allow_tags = False
    custom_name.short_description = 'custom_name'

admin.py

class MyAdmin(admin.ModelAdmin):
    fieldsets = (
            (None, {
                    'fields': ('custom_name', )
            }),
    )
    readonly_fields = ('custom_name', )

It must be working Django >=1.7 It seems the approach can be apply to early version of Django^ but I don't testing

Abbasov Alexander
  • 1,848
  • 1
  • 18
  • 27
5

Would it work to apply the filter at the model level? If so you can use the limit_choices_to attribute on the model's ForeignKeyField.

Alternatively you could override the formfield_for_foreignkey attribute of the modelAdmin class.

Something like -

class YourModelAdmin(admin.ModelAdmin):
    def formfield_for_foreignkey(self, db_field, request, **kwargs):
        if db_field.name == "ports_with_same_scanner":
            kwargs["queryset"] = PortList.objects.filter(scanner=self.scanner)
        return super(YourModelAdmin, self).formfield_for_foreignkey(db_field, request, **kwargs)

(Apologies if I've misunderstood the question)

Aidan Ewen
  • 13,049
  • 8
  • 63
  • 88
  • 3
    Since `ports_with_same_scanner` is not an actual field on the Model, how is the above code not erring out? If I try to define a non-model-field in my `fieldsets` definition, Django will bork out with `FieldError: Unknown field(s) (my_field_1, my_field_2) specified for MyModel. Check fields/fieldsets/exclude attributes of class MyModelAdmin.`, and it will bork out BEFORE it calls the `formfield_for_foreignkey()` method. How do you define `ports_with_same_scanner` in a way that keeps Django happy? – Troy Apr 17 '15 at 19:21