﻿id	summary	reporter	owner	description	type	status	component	version	severity	resolution	keywords	cc	stage	has_patch	needs_docs	needs_tests	needs_better_patch	easy	ui_ux
31867	Inconsistency in rendering hidden fields in Django admin	Antoine Humbert	nobody	"In django admin, when having an inline ModelAdmin with a hidden widget (e.g. ""position"" field when using sortable inlines with django_nested_admin or grappelli), the field may be rendered in admin interface depending on context:

* when user has change permission on the model, the field is not shown (because is has an HiddenInput widget)
* when user has view permission, but not change permission:
  * If field is in a StackedInline and is the only field on a line (e.g. fields = (""field1"", ""field2"", ""hidden_field"") or fields = ((""field1"", ""field2""), ""hidden_field"")), then field does not appear in admin interface
    * => this is due to the row having the hidden class (coming from django.contrib.admin.helpers.Fieldline.has_visible_field which is False, because it is evaluated according to the field widget - which is HiddenInput). The <div> containing field value itself does not have the hidden class.
  * If field is in a StackedInline and is not the only field on a line (e.g. fields = (""field1"", (""field2"", ""hidden_field""))), then field appear in admin interface
    * => this time, the row does not have the hidden class, because not all fields of the line are hidden
  * If field is in a TabularInline, then field appear in the admin interface
    * => There is no django.contrig.admin.helpers.Fieldline in this case which may hide a row containing the field

The inconsistency resided in the fact that django.contrib.admin.helpers.Fieldline.has_visible_field rely on the field widget.is_hidden (whatever user has change permission on the model or nat), whereas in django.contrib.admin.helpers.InlineAdminFormset.fields, if user has change permission, field is rendered using the field widget (HiddenInput in this case), but is user does not have change permission, field widget is statically defined with {'hidden': False}.

In this function, changing lines


{{{
            if not self.has_change_permission or field_name in self.readonly_fields:
                yield {
                    'name': field_name,
                    'label': meta_labels.get(field_name) or label_for_field(
                        field_name,
                        self.opts.model,
                        self.opts,
                        form=empty_form,
                    ),
                    'widget': {'is_hidden': False},
                    'required': False,
                    'help_text': meta_help_texts.get(field_name) or help_text_for_field(field_name, self.opts.model),
                }

}}}

to


{{{
            if not self.has_change_permission or field_name in self.readonly_fields:
                yield {
                    'name': field_name,
                    'label': meta_labels.get(field_name) or label_for_field(
                        field_name,
                        self.opts.model,
                        self.opts,
                        form=empty_form,
                    ),
                    'widget': {'is_hidden': empty_form.fields[field_name].widget.is_hidden},
                    'required': False,
                    'help_text': meta_help_texts.get(field_name) or help_text_for_field(field_name, self.opts.model),
                }

}}}

effectively hides the field.

I produce the bug in version 2.1, but I expect it to be present is newer versions as the implied code is the same."	Bug	new	contrib.admin	2.1	Normal		admin hidden field		Unreviewed	1	0	0	0	0	1
