> If optional fields are
> left off the HTML form deliberately, without change the Form class or
> the view code, this is exactly when data loss will currently occur.
> I think you are confusing optional as in "may not be specified by the
> user" with optional as in "may not be processed by the form"?
I think it would be more accurate to call this developer error rather
than a data loss bug in Django. If you are defining forms in this way
you are exposing all the model fields to be changed by the form. You
shouldn't be defining forms with fields you don't want changed.
Imagine this form:
{{{
from django import forms
from django.contrib.auth.models import User
class UserForm(forms.ModelForm):
class Meta(object):
model = User
}}}
Look innocent? It's not. Even if you don't render the is_staff or
is_superuser fields they can still be changed if they are given in the
POST. That means exposing this form can allow changing a user to a
superuser. Don't trust data from the client and be explicit about the
fields you want to expose for the form to change. This is why the
'fields' and 'exclude' Meta options exist.
Best,
Mark
On Jan 12, 9:40 pm, Tai Lee <[email protected]> wrote:
> Ian,
>
> I agree that there are a lot of different ways that form data can be
> submitted to Django, including near endless combinations of multiple
> Django forms, multiple HTML forms, AJAX, etc.
>
> If we reduce the scope of our discussion and consider only a Django
> form (forgetting HTML forms and AJAX) and two possible scenarios:
>
> 1. Partial form data is bound to a Django form, and it is not expected
> to result in a call to the form's `save()` method and a change to the
> database. It is only intended to examine the form's validation state
> relating to the partial data that is bound to the form. In this case,
> the proposed change should have no impact.
>
> 2. Full form data is bound to a form, and it IS expected to validate
> and result in a call to the form's `save()` method and a change to the
> database. In this case, why would we ever want to assume that a
> character field which has no bound data, is actually bound to an empty
> string?
>
> This is a dangerous assumption, I think. If we intend to obtain
> complete data from the user, bind it to a form and save it to the
> database, we should be sure (as much as we can be) that the data is
> actually complete.
>
> Take the following pure Django example:
>
> {{{
> class Profile(models.Model):
> first_name = models.CharField(blank=True, max_length=50)
> last_name = models.CharField(blank=True, max_length=50)
> address = models.CharField(blank=True, max_length=50)
>
> class ProfileForm(ModelForm):
> class Meta:
> model = Profile
>
> profile = Profile.objects.create(first_name='Tai', last_name='Lee',
> address='Sydney')
> form = ProfileForm({}, instance=profile)
> if form.is_valid():
> form.save()
>
> }}}
>
> The profile will have no first name, last name or address. The form
> will produce no validation errors and will save the updated model to
> the database.
>
> This is very surprising and counter-intuitive to me.
>
> I think the only time we could safely make the assumption that fields
> with empty string values will be omitted by the UA is when we are
> confident that the source of the form data also makes a similar
> assumption that the back-end will re-normalise those missing fields
> back to an empty string.
>
> I'd be surprised if any UAs actually do make that assumption, because
> the way Django treats missing character fields does not appear to be
> based on any spec, and Django is not the only form processing back-end
> (or even the most popular one).
>
> I'm not sure I follow your simplest case example of one HTML form in a
> browser window and one Django Form in a view. If optional fields are
> left off the HTML form deliberately, without change the Form class or
> the view code, this is exactly when data loss will currently occur. I
> think you are confusing optional as in "may not be specified by the
> user" with optional as in "may not be processed by the form"?
>
> Cheers.
> Tai.
--
You received this message because you are subscribed to the Google Groups
"Django developers" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to
[email protected].
For more options, visit this group at
http://groups.google.com/group/django-developers?hl=en.