Donald

Backward compatibility can be maintained with just a log warning to give
developer time to clean up code or throwing an exception when
`settings.DEBUG=True` and only log warning when `False`; I am not sure how
this ought to be implemented but again I am big +1 for this proposal.

On Thu, Jan 12, 2012 at 4:02 AM, Tai Lee <real.hu...@mrmachine.net> wrote:

> Donald,
>
> Thanks for sharing your feedback with everyone.
>
> I do believe that there should be some kind of validation error or at
> least a loud warning to the console or logs when a form is bound to
> incomplete data. The only time when this should occur is for
> "unsuccessful controls" such as unchecked radio buttons and
> checkboxes. These shouldn't be a problem for Django, which already
> normalises no value for a checkbox to False and any value for it to
> True.
>
> I'm not sure that there is a widespread practice of submitting partial
> forms with JS and still expecting the entire form to validate and save
> is widespread, or even valid according to the RFC and HTML4 specs
> which expect every successful control to be included in the form data.
>
> Sure, I can see that forms could be fully or even partially submitted
> via JS to perform AJAX validation in real time, but I don't see how
> the form as a whole being invalid and validation errors on the missing
> fields would impact that.
>
> If we can't find a clear definition or distinction between null and an
> empty string in the RFC or HTML4 specs, and we go to our browser (you
> mentioned Chrome), I think you will find that they consider text input
> fields with an empty string as the value are "successful controls", as
> these are included in the form data.
>
> Before knocking back this proposal on the grounds of ambiguous specs
> (multiple interpretations), I would like to know if there are actually
> any UAs that behave as you fear they might. If there are, then this
> change would definitely be a problem for those UAs.
>
> However, even in the event that this is deemed a backwards
> incompatible change and the potential silent data loss issue is not
> serious enough to override that, then a loud warning could still be
> added without changing the current behaviour.
>
> Cheers.
> Tai.
>
>
> On Jan 12, 3:29 am, Donald Stufft <donald.stu...@gmail.com> wrote:
> > I'm very much -1 on this change.
> >
> > To "fix" this change would require throwing an error anytime an
> incomplete dictionary was passed as the data arg to a form. This would
> break any existing code that relies on this (in particular it's common
> practice to accept a subset of the fields via json). So this would be a
> backwards incompatible change.
> >
> > Further more I disagree with the interpretation of the RFC as provided.
> The RFC states that any UA may choose to not send along a form field if it
> contains a null value. So the question then becomes what is a null value in
> regards to the RFC? As I cannot find any mention of what constitutes a null
> value in the RFC I went to my browser. Using javascript I executed
> ``document.getElementById('textfield').value = null`` in the js console.
> The result was that the value was set to "". So in my browser (Chrome on OS
> X) it is treating null and "" with equivalence.
> >
> > Going by my personal interpretation of the RFC, and Chrome's behavior in
> my javascript test I can only conclude that the proposed change would cause
> Django forms to violate the RFC spec and while Violating the RFC spec in
> and of itself isn't always the wrong thing to do I do believe that it
> should only be done when RFC and implementations are at odds in a way that
> are incompatible with each other. In this case they are not, and the RFC is
> more permissive and should be followed as Django does not have a list of
> supported browsers so we must strive to follow the RFC's where we can (and
> where they are actually defined) and deviate only when the alternative is
> being broken in major browsers.
> >
> > Additionally I believe in this case there are two major error conditions.
> >
> > A) The proposed change is made, a visitor is using a UA that I believe
> follows the RFC and any Django forms with optional, and unfilled in values
> stop working for this visitor.
> > B) The proposed change is not made, and when an optional form field is
> left off of a form (or json, or any partially incomplete dictionary of
> values) the form assumes the default initial value of "".
> >
> > Neither error condition is optimal, however A has the additional
> downside that this error is completely outside of the control of the
> developer whereas B is the result of developer error and is under his
> control.
> >
> >
> >
> >
> >
> >
> >
> > On Tuesday, January 10, 2012 at 8:38 PM, Tai Lee wrote:
> > > There is a potential for data loss with optional form fields that are
> > > (for whatever reason) omitted from an HTML template.
> >
> > > For example, if we take an existing model form and template that
> > > works, add an optional character field to the model but fail to add a
> > > corresponding field to the HTML template (e.g. human error, forgot
> > > about a template, didn't tell the template author to make a change,
> > > didn't realise a change needed to be made to a template), when that
> > > form is submitted Django will assume that the user has provided an
> > > empty string value for the missing field and save that to the model,
> > > erasing any existing value. This is not a bug, but it is relatively
> > > easy to trigger silent and unexpected data loss.
> >
> > > I have briefly discussed this with PaulM and dstufft on django-dev,
> > > but could did not reach any consensus.
> >
> > > RFC1866 [1] says:
> >
> > > > The fields are listed in the order they appear in the
> > > > document with the name separated from the value by `=' and
> > > > the pairs separated from each other by `&'. Fields with null
> > > > values may be omitted. In particular, unselected radio
> > > > buttons and checkboxes should not appear in the encoded
> > > > data, but hidden fields with VALUE attributes present
> > > > should.
> >
> > > The HTML4 spec at W3C.org (http://W3C.org) [2] says:
> >
> > > > Users interact with forms through named controls.
> >
> > > > A control's "control name" is given by its name attribute. The scope
> of the
> > > > name attribute for a control within a FORM element is the FORM
> element.
> >
> > > > Each control has both an initial value and a current value, both of
> which are
> > > > character strings. Please consult the definition of each control for
> > > > information about initial values and possible constraints on values
> imposed by
> > > > the control. In general, a control's "initial value" may be
> specified with the
> > > > control element's value attribute. However, the initial value of a
> TEXTAREA
> > > > element is given by its contents, and the initial value of an OBJECT
> element
> > > > in a form is determined by the object implementation (i.e., it lies
> outside
> > > > the scope of this specification).
> >
> > > > The control's "current value" is first set to the initial value.
> Thereafter,
> > > > the control's current value may be modified through user interaction
> and
> > > > scripts.
> >
> > > > A control's initial value does not change. Thus, when a form is
> reset, each
> > > > control's current value is reset to its initial value. If a control
> does not
> > > > have an initial value, the effect of a form reset on that control is
> > > > undefined.
> >
> > > > When a form is submitted for processing, some controls have their
> name paired
> > > > with their current value and these pairs are submitted with the
> form. Those
> > > > controls for which name/value pairs are submitted are called
> successful
> > > > controls.
> >
> > > as well as [3]:
> >
> > > > A successful control is "valid" for submission. Every successful
> control has
> > > > its control name paired with its current value as part of the
> submitted form
> > > > data set. A successful control must be defined within a FORM element
> and must
> > > > have a control name.
> >
> > > > However:
> >
> > > > * Controls that are disabled cannot be successful.
> > > > * If a form contains more than one submit button, only the activated
> submit
> > > > button is successful.
> > > > * All "on" checkboxes may be successful.
> > > > * For radio buttons that share the same value of the name attribute,
> only the
> > > > "on" radio button may be successful.
> > > > * For menus, the control name is provided by a SELECT element and
> values are
> > > > provided by OPTION elements. Only selected options may be
> successful. When
> > > > no options are selected, the control is not successful and neither
> the name
> > > > nor any values are submitted to the server when the form is
> submitted.
> > > > * The current value of a file select is a list of one or more file
> names. Upon
> > > > submission of the form, the contents of each file are submitted with
> the
> > > > rest of the form data. The file contents are packaged according to
> the
> > > > form's content type.
> > > > * The current value of an object control is determined by the
> object's
> > > > implementation.
> >
> > > > If a control doesn't have a current value when the form is
> submitted, user
> > > > agents are not required to treat it as a successful control.
> >
> > > > Furthermore, user agents should not consider the following controls
> > > > successful:
> >
> > > > * Reset buttons.
> > > > * OBJECT elements whose declare attribute has been set.
> >
> > > > Hidden controls and controls that are not rendered because of style
> sheet
> > > > settings may still be successful.
> >
> > > I interpret the above to mean that any text input with a value
> > > attribute (even `value=""`) is successful control, and should be
> > > included in the encoded form data. This is what current versions of
> > > Chrome and Firefox do, at least. I have not found any examples of
> > > browsers which are known not to do this.
> >
> > > What I would like to change in Django is for it to stop assuming that
> > > missing POST data for a character field is actually an empty string,
> > > and instead raise a form validation error that would prevent the model
> > > instance from being saved to the database (potentially causing data
> > > loss for that field).
> >
> > > I don't see any benefit in the current behaviour, except to
> > > potentially support undetermined and unspecified UAs which might treat
> > > form fields as unsuccessful controls if the have an empty string as
> > > their value, and if those UAs accordingly do not include those fields
> > > in the encoded form data. Even if such UAs were found, I would argue
> > > that the RFC and HTML4 specs show that text fields with a value (even
> > > an empty string) are successful controls that should be included.
> >
> > > Failing that, I would like for Django to at least raise a loud warning
> > > when a form is bound to data is missing values for character fields,
> > > so that it will at least be easier to detect this silent and
> > > unexpected data loss in a test environment, before it occurs in a
> > > production environment.
> >
> > > Does anybody else have opposing or supporting arguments, or any
> > > knowledge of actual UAs that do not include fields with empty values
> > > in their encoded form data, or an alternative interpretation of the
> > > RFC and HTML4 specs above?
> >
> > > Cheers.
> > > Tai.
> >
> > > [1]http://www.rfc-editor.org/rfc/rfc1866.txt
> > > [2]http://www.w3.org/TR/html4/interact/forms.html#h-17.2
> > > [3]http://www.w3.org/TR/html4/interact/forms.html#successful-controls
> >
> > > --
> > > You received this message because you are subscribed to the Google
> Groups "Django developers" group.
> > > To post to this group, send email to
> django-developers@googlegroups.com (mailto:
> django-developers@googlegroups.com).
> > > To unsubscribe from this group, send email to
> django-developers+unsubscr...@googlegroups.com (mailto:
> django-developers+unsubscr...@googlegroups.com).
> > > For more options, visit this group athttp://
> groups.google.com/group/django-developers?hl=en.
>
> --
> You received this message because you are subscribed to the Google Groups
> "Django developers" group.
> To post to this group, send email to django-developers@googlegroups.com.
> To unsubscribe from this group, send email to
> django-developers+unsubscr...@googlegroups.com.
> For more options, visit this group at
> http://groups.google.com/group/django-developers?hl=en.
>
>

-- 
You received this message because you are subscribed to the Google Groups 
"Django developers" group.
To post to this group, send email to django-developers@googlegroups.com.
To unsubscribe from this group, send email to 
django-developers+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/django-developers?hl=en.

Reply via email to