class Name(models.Model):
name = models.CharField(maxlength=100)
when making a new Name object...
>>> a=Name()
>>> a.save()
>>> a
<Name: Name object>
>>> a.name
''
The name field does not have blank=True or null=True set, but yet I am
able to create a new Name object using no parameters (because
CharFields and children are defaluting to empty string). Is this the
intended behavior?
hi,
yes, (unfortunately) it is.
the models do not validate their input.
you will have to use a manipulator (Name.AddManipulator) to validate
your input (and then save the object).
making the models validation-aware is planned, but not done yet.
gabor
But I am not talking about validating my input here. I just don't want
input to be inserted for me. For example, non-specified IntegerField
attributes don't defalut to zero. So why then do non-specified
CharField attributes default to empty string?
Yes, from the documentation:
http://www.djangoproject.com/documentation/model_api/#null
"Note that empty string values will always get stored as empty
strings, not as NULL -- so use null=True for non-string fields such
as integers, booleans and dates.
Avoid using null on string-based fields such as CharField and Text
Field unless you have an excellent reason. If a string-based field
has null=True, that means it has two possible values for "no
data":NULL, and the empty string. In most cases, it's redundant to
have two possible values for "no data"; Django convention is to use
the empty string, not NULL."
The reason that integers without values insert as null is because
their empty_strings_allowed value is False. Most non-string fields in
Django have this set to False, text fields have it set to True, in
order to assert the behavior described in the documentation. To
override this behavior, you need to set a default value.
Note that when gabor mentioned validation, he was talking about your
comment about not setting blank=True. Blank=True/False is a framework
constraint, null=True/False is a database constraint.
Don
Ok, after some trial and error, I see that if you have null=True on a
CharField, it will use NULL instead of empty string. This is what I
needed because in my model I have a field that I want to be optional
but unique. This is not possible if you don't put null=True for the
field because Django will try to use empty string by default.
Out of curiosity, any one know for what reason using empty strings for
CharFields is the Django convention? Technically, isn't an empty
string still data? Isn't it a bit confusing that some fields get
default values and others do not? Explicit better than implicit?
> Out of curiosity, any one know for what reason using empty strings for
> CharFields is the Django convention? Technically, isn't an empty
> string still data? Isn't it a bit confusing that some fields get
> default values and others do not? Explicit better than implicit?
>
Well, storing NULL vs Empty-string should consume just about the same
amount of data or the difference should be insignificant.
However, I think it empty-string was used due to the variations in how
databases handle NULL values in strings and how to handle the strings
['NULL','Null','nul']
not sure if I read that somewhere or came up with it on my own
though. :)
/Marc DM
My guess is that you need less code when you can assume that all text
columns in the database contain strings. Python strings are first-
class objects and so have instance methods you can call by appending
the function call onto the variable. If you had nulls returned from
those text columns, then every time you wanted to execute a string
function, you'd have to test for None, then convert it. Then with a
test, you may waste code AND cycles because if you code
if not string:
string = ''
string.split(...)
half the time you may be assigning an empty string to a variable that
already contains an empty string.
That's one reason I can think of, there may be others.
Don
On Thu, 2006-09-14 at 02:09 +0000, Gary Wilson wrote:
[...]
> Ok, after some trial and error, I see that if you have null=True on a
> CharField, it will use NULL instead of empty string. This is what I
> needed because in my model I have a field that I want to be optional
> but unique. This is not possible if you don't put null=True for the
> field because Django will try to use empty string by default.
>
> Out of curiosity, any one know for what reason using empty strings for
> CharFields is the Django convention? Technically, isn't an empty
> string still data? Isn't it a bit confusing that some fields get
> default values and others do not? Explicit better than implicit?
Looking at this from a database persepctive, it's bad, I agree (NULLs
and empty strings are different animals and they should be able to
co-exist). However, looking at it from a web framework perspective, a
decision has to be made, so Django's approach is not illogical. To
explain...
Think about how the data is entered: through a web form (the admin
interface, or a custom form). Now, how do you differentiate between an
explicit empty string and a "no data entered and so it should be NULL"
field? With web entry, you can't, so Django chooses to default to using
empty strings everywhere.
When I first started using Django, this drove me nuts. Why were the
developers being so righteous about good web practices and then paying
no heed to good databases in this fashion (I thought)? But, when you
think about it, it's a hard problem -- differentiating between the two
cases for web entry is tough. So the compromise is not unreasonable.
Remembering my own reaction, though, I can certainly sympathise with the
"are they evil?" thoughts that might occasionally flit through peoples'
heads when encountering this.
NULLs are still allowed in character fields, so legacy data is
supported. Evilness is averted. :-)
Regards,
Malcolm
I had the same reaction, but also understand there isn't a great way to
handle it. In Microsoft's SQL Enterprise Manager, you can enter Ctrl-0
in a field and it will set that field to NULL. I'm thinking about doing
something like this in one of my Django forms since I need to support
both an empty string _and_ a NULL input so I want an explicit way to
differentiate between the two. A control character doesn't work well
for browser input, but I may end up treating an empty string as NULL
and force the user to put "" if they really want a blank string (which
in this case is the exception, not the norm).
I don't know if something like that is a reasonable solution for Django
or not, but I know it would come in handy in a number of situations.
-Dave
assuming that you want to differentiate between:
- the user did not fill in the data
- the user's input was ""
wouldn't it be better to represent this in html as a checkbox+an input
field?
and by default have the checkbox unselected, and the input-field disabled.
and then if the user checks the checkbox, enable the field.
and then in the view code, simply check the checkbox's value and set the
field to null or to what-was-in-the-input-field.
gabor
Remember that we are trying to produce normal looking HTML pages here.
How many HTML forms have you filled out where you need to also check a
box saying "I want to use this input box"? That is exposing underlying
database representation to the end-user and if you put yourself in the
shoes of the user, it's just going to seem odd (and very off-putting).
Forcing a big change like that in the way forms naturally work is a
really leaky abstraction and it's why a choice had to be made. If
somebody really wants empty strings to be stored as NULL, they can
override their model's save method and fix it up there (there was
somebody posting on django-users last month about doing exactly that).
If, for some reason, the data entry person really is in a position to
make the decision, then implement something like the ctrl-0 trick Dave
Avraamides mentioned yesterday, or do the checkbox manually. But it's
not something where the person using your form should have to care, by
and large.
Cheers,
Malcolm
OK, ignore my post -- you were offering an alternative to David's idea,
not proposing a universal change.
/me backs sheepishly away from the keyboard and goes to get some coffee
and wake up.
Malcolm
gabor,
That's certainly more explicit but makes for a busier UI and also makes
it more difficult to reuse a standard FormWrapper in the template.
After thinking about this more, I can't come up with a case where the
input value should ever be an empty string so I think always mapping an
empty string to NULL on save() will work just fine. Just for some
background, the use case here is that for a financial instrument editor
(stock, bond, swap, etc.) there are certain fields that come from a
third party data vendor but occasionlly the user will wish to override.
Other fields are only maintained internally so they can be directly
edited. For the overridable fields, if the user enters a new value, it
will become the effective value for that field, but if they clear the
field, it reverts back to the default value.
For my specific case, I don't think treating empty fields as NULL will
create a problem (and if it does I can use the "" as an easy
workaround).
Thanks for the ideas, though.
-Dave
IMO, all FormFields should act the same and default to NULL. If you
want the database field to default to something other than NULL, then
you can use the "default" parameter in the model's definition. Then,
just as you might want to use default=0 for IntegerFields, you might
want to use default='' for CharFields.
So I understand that Django made the choice to default to empty
strings, but what I am really trying to learn is why.