Ad N
Ad N

Reputation: 8376

How to set a default value for a Django Form Field, that would be saved even in the absence of user initiated changes?

When looking for this feature, one is flooded under answers pointing toward the Form initial member.

Yet, by its design, this approach would not save anything to database if the user does not change at least one value in the form, because the has_changed method returns False when only initial values are submitted. Then, if one were to override has_changed to always return true, the behaviour would be to try to save forms for which no value (nor initial nor user input) is found.

Is it possible to have a real default value in Django: a value that the user can change if he wants, but that would still save the form to DB when the form is only submitted with default values ?

Upvotes: 1

Views: 1194

Answers (2)

Ad N
Ad N

Reputation: 8376

Here is the solution I am currently using to replace the meaning of initial to achieve the behaviour described in the question. I override the had_changed method of the Form to be:

def has_changed(self):
    for name, field in self.fields.items():
        prefixed_name = self.add_prefix(name)
        data_value = field.widget.value_from_datadict(self.data, self.files, prefixed_name)

        if data_value and not issubclass(field.__class__, forms.models.InlineForeignKeyField):
            return True
    return False

The second check (issubclass(...)) is required in case the Form is used in an InlineFormset: when editing the parent model, the foreign_key field is automatically populated for all forms displayed (even the ones that have no default values), so it prevents saving the ones that are left blank (neither defaults nor user input).


Now, on a personal and probably polemic note, I must say I hope I missed something obvious. My requirements seem quite basic, yet the solution here is nothing short of a brittle hack...

Upvotes: 2

John Gordon
John Gordon

Reputation: 33310

I don't think there is a premade solution for you. You'll have to do one of two things:

  1. When the form is submitted, examine the value of the field in question. If it is equal to the default value, then ignore the result of has_changed and save it. (Be aware that this could result in duplicate items being saved, depending on your schema.)

  2. When the form is submitted, search for an existing record with those field values. If no such record exists, save it. Otherwise do nothing. (If these records contain a last-updated timestamp, you might update that value, depending on your application.)

Upvotes: 1

Related Questions