Read-Only Fields in Admin: Design Proposal
This page is intended to lay out concepts regarding a possible implementation of read-only fields in django.contrib.admin. It will specifically deal with four areas:
- Inducing fixed read-only behavior through ModelAdmin options
- Inducing optional read-only behavior through permissions
- Allowing fields to be populated by the user at the time of object creation and then made un-alterable/read-only when accessed subsiquently
- Attaching fine-grained read-only permissions to fieldsets
The following functional aspects will be addressed by this document:
- The nature of read-only widget functionality, and how to provide custom read-only functionality for custom and non-custom field types and custom and non-custom editable widgets (possibly through a registration meme).
- The manner of read-only configuration within ModelAdmin subclasses, and read-only configuration options within ModelAdmin.
- readonly_fields will be a general option of the ModelAdmin, and would restrict editing of any fields of the model.
- Configuration will also be available via additional options for fieldsets's field_options dictionary, specifically:
- readonly_fields: fields otherwise listed within the fieldset that are designated as read-only.
- permission: the name of the permission change and read permissions that can control access to this fieldset. Specifically, if this is defined, either a "change" or "read" version of this permission would need to exist for the fieldset to be rendered. An "add" permission for a user would be required for this fieldset to be editable when the object is being added. This schema would permit a set of users to add fields to an object when it is created, but subsequently only view/read that data and not modify it. A "delete" permission would not apply and would not be available. If this option is not specified or is None, then current default behavior would apply.
- The decision process within the admin site generator that determines whether a read-only widget, an editable widget, or no widget should be included in the change screen, a process that includes:
- in the case that a change permission exists on a model, examining readonly_fields and fieldset.readonly_fields to see if the field is required statically to be read-only
- examining the permissions, checking to see that in the absence of a change permission on a model, the read-only permission exists
- in the case that a change permission exists on a fieldset, examining readonly_fields and fieldset.readonly_fields to see if the field is required statically to be read-only
- examining the permissions, checking to see that in the absence of a change permission on a fieldset, the read-only permission exists
- examining whether the user is a superuser and if SUPERUSER_OVERRIDE_READONLY is set in the settings.
- The changes that would be required to attach permissions to fieldsets generally.
- When a form is submitted editing an object that contains required fields that are read-only, how will that validation interaction work? (Fetch the object before saving, then merge it with the form? How would form validation be performed? What might happen if the object has been changed since it was fetched?)
- Should an option be added to make a statically read-only field editable when the object is being added the first time? (Might a solution be that if the field is marked as blank=False the read-only field becomes editable when the object is first added?)
- Decide on an override hierarchy for model vs fieldset permissions, specifically from the following list:
- read-only overrides change; i.e. the presence of both model and fieldset change permissions are required
- fieldset overrides model; i.e. fieldset.change is required and sufficient for editing
- change overrides read-only; i.e. either model.change or fieldset.change is sufficient for editing
model overrides fieldset; i.e. model.change is required and sufficient for editing (this makes no sense)
- A similar hierarchy must be defined for deciding on whether or not to display a fieldset at all (i.e. what permissions are required and sufficient to access a ModelAdmin and see its fieldsets).
- The first option seems to make the most sense, in light of the fact that not every fieldset will have a permission defined. Under this hierarchy it can be said that the model permission controls access to the page as a whole and the fieldset permissions can then further restrict (but not expand) access to each of the fieldsets. If no fieldset permission is defined, then the model permission controls.
- What is the interaction with the behavior of DateField's auto_add_now option, if any?
More detail will be added here subsequently...