#20000 closed New feature (fixed)

Allow overriding `label`, `help_text` and `error_messages` for the default fields in `ModelForm`

Reported by: loic84 Owned by: loic84
Component: Forms Version: master
Severity: Normal Keywords:
Cc: Triage Stage: Accepted
Has patch: yes Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no


Currently ModelForm requires to completely redefine fields in order to customize user-facing strings such as labels, help_texts and error_messages.

This leads to a lot of boilerplate code to anyone who wants to customize these, but most importantly it's an error prone process. The bigger the ModelForm becomes, the more difficult it is to ensure functional parity between the Model fields and the Form fields for the critical parts such as blank/required, default, validators, etc.

One shouldn't be at risk of completely breaking a form functionality in order to make small cosmetic changes.

It's understood that we have to draw a line somewhere, else we would have field definitions in the Meta, but I believe that line should be drawn at "anything cosmetic" available through Meta overrides, and "anything functional" through fields overrides. I believe the currently provided widgets lie in between the two, so it's almost surprising that it was added as a convenience in a first place instead of the purely cosmetic options.

Attachments (0)

Change History (15)

comment:1 Changed 16 months ago by loic84

  • Needs documentation unset
  • Needs tests unset
  • Patch needs improvement unset

comment:2 Changed 16 months ago by jezdez

  • Resolution set to wontfix
  • Status changed from new to closed

This has been previously discussed and wontfixed before. Feel free to raise the issue on the developer list.

comment:3 Changed 16 months ago by carljm

FWIW, I think this patch would be a positive improvement. It makes common customization cases simpler, and avoids the error-prone alternative of overriding the field entirely and the extra-boilerplate alternative of overriding __init__ and patching fields there. I also think the supplied new customization points are very similar in nature to the existing Meta.widgets, and it's an odd inconsistency to have one but not the others. What argument is there for Meta.widgets that does not apply equally to labels, help texts, and error messages?

In other words, if you decide to bring it up on django-developers, I am +1 for the change.

comment:4 Changed 16 months ago by carljm

  • Resolution wontfix deleted
  • Status changed from closed to new
  • Triage Stage changed from Unreviewed to Design decision needed

comment:5 Changed 16 months ago by jacob

  • Triage Stage changed from Design decision needed to Accepted

I agree with Carl.

comment:7 Changed 14 months ago by lrekucki

Just for the record, this is a duplicate of #17924.

comment:8 Changed 13 months ago by timo

I've updated the pull request to merge cleanly and also added the labels, help_texts, and error_messages arguments to the model(form|formset)_factory functions:

comment:9 Changed 13 months ago by jezdez

I've previously warned that introducing the widgets parameter to the Meta class would open up the possibility "to ask for more". I can't believe Jacob or Carl would become soft in the strict separation of concern between form class and field.

Since I can't provide an alternative as requirement to veto a feature request other than "DON'T DO IT!!1!" I'm forced to change to -0. But I reserve the right to say "I told you so" when a ticket is opened to allow overriding arbitrary field options in the Meta class.

comment:10 Changed 13 months ago by timo

An alternative which may mitigate the underlying issue of making simple customizations on a ModelForm without having to redeclare the options that are generated by the default form:

FooFormField = MyModel._meta.get_field('foo').formfield() # would probably need a better API

class MyModelForm(ModelForm):
  foo = FooFormField(label='My Foo')

Alternatively, we could recommend doing customization's in __init__, but it doesn't see like the cleanest solution.

comment:11 Changed 13 months ago by loic84

I dislike the FooFormField suggestion, it's very verbose and the intent (override the label) is not immediately obvious.

Also I can't think of any other places in Django where we use such pattern so it feels particularly out of place.

comment:12 Changed 13 months ago by timo

But it could be a way to override selected options on the the default ModelForm field without having to redeclare all of that field's default options (i.e. for non-cosmetic changes).

comment:13 Changed 13 months ago by mrmachine

As jezdez points out, this opens up the possibility to "ask for me"... I liked #17924 and I am asking for more :) If we're going to hard code support for a few special cases, why not just support anything in a clean and DRY/elegant/flexible way as was suggested before...

Version 0, edited 13 months ago by mrmachine (next)

comment:14 Changed 13 months ago by carljm

I think we should move ahead with this ticket as outlined in the description.

I might favor the version in #17924 if we were designing the API from scratch, but the problem with #17924 is that for consistent API it would imply deprecating Meta.widgets, and I just don't think the benefit of a "universal" approach is worth a deprecation cycle for already-existing functionality that's in wide use. (#17924 also carries the minor disadvantage of requiring a lot more commas, quotes, and curly braces for simple customizations.) If we have the common cases covered via direct Meta options, overriding __init__ is still always an option for the uncommon cases.

comment:15 Changed 13 months ago by Tim Graham <timograham@…>

  • Resolution set to fixed
  • Status changed from new to closed

In 9e50833e2293aa2734f14f9873abe4f83d03b8c6:

Fixed #20000 -- Allowed ModelForm meta overrides for label, help_text and error_messages

Add Comment

Modify Ticket

Change Properties
<Author field>
as closed
as The resolution will be set. Next status will be 'closed'
The resolution will be deleted. Next status will be 'new'

E-mail address and user name can be saved in the Preferences.

Note: See TracTickets for help on using tickets.