Search code examples
djangoinline

How to make some Django Inlines Read Only


I'm using django admin and adding a TabularInline to my ModelAdmin class. Think Author and the inline is Books. How do I make some of those inlines appear read only and some appear editable based on certain characteristics of the model instance for each specific inline? Say I wanted all the books written before 2001 to be read only. And all the books written after that to be editable.

I've tried overriding has_change_permission() on the TablularInline and using the obj param, but it is receiving the parent and not the instance of this specific inline.


Solution

  • You have to override your inline form and check the value on the instance in the __init__().

    Example:

    class AuthorBookInlineForm(forms.ModelForm):
        model = Book
    
        def __init__(self, *args, **kwargs):
            super().__init__(*args, **kwargs)
            if self.instance and self.instance.created_ts.year <= 2001:
                for f in self.fields:
                      self.fields[f].widget.attrs['readonly'] = 'readonly'
    

    Don't forget to set the form value on your inline...

    class AuthorBookInline(admin.TabularInline):
        model = Book
        form = AuthorBookInlineForm
        extra = 0