Sorry, but the longer we discuss, the more it becomes clear: Django's
behaviour is certainly wrong.

I'm puzzled how no Django core developer seems to understand it. I hope
that this is just because they are not following this thread because
there is admittedly more urgent work to do right now.

With the danger of repeating myself I explain once more:

Example models:

  class Owner(models.Model):
      pass

  class Animal(models.Model):  # nullable owner
      owner = models.ForeignKey(Owner,blank=True,null=True)

  class Thing(models.Model):   # non-nullable owner
      owner = models.ForeignKey(Owner)

There should never be a related lookup when the fk_id is None. For
nullable FK Django behaves correctly:

  >>> a = Animal()
  >>> print a.owner
  None

The same doesn't work for non-nullable FK:

  >>> t = Thing()
  >>> print t.owner
  Traceback (most recent call last):
  ...
  DoesNotExist

This is whay I say that Django treats non-nullable FK in a special way.
It is as if Django thinks "Since Thing.owner may not be None, I can do
the lookup without even testing for a None value".

The correct exception is risen when you try to save it:

  >>> t.save()
  Traceback (most recent call last):
  ...
  IntegrityError: 20100212_thing.owner_id may not be NULL

How can you not understand that the DoesNotExist exception above is
risen too early? It is a bug!

Luc


On 12.02.2010 6:24, hcarvalhoalves wrote:
> On 10 fev, 12:42, Luc Saffre <luc.saf...@gmx.net> wrote:
>> Thank you, Henrique, for dropping in.
>>
>> Django's current behaviour is not correct because it forces me to access
>> non-nullable FK fields differently than nullable ones. "In Python,
>> throwing exceptions for expected outcomes is considered very bad form"
>> [1]. Django should raise an exception only if I try to save an instance
>> with invalid data (for example None in a non-nullable FK field), but not
>> when I try to access any data, may it be valid or not
>>
>> Luc
> 
> The exception doesn't come from the fact you're accessing an
> attribute. It comes from the related lookup, Django is just doing the
> right thing and letting the DoesNotExist exception flow up. It's
> better if you see things this way.
> 
> Also, the DoesNotExist exception is far from undocumented. Thru the
> docs and tutorials you see the idiom on how to handle it quite a few
> times. [1]
> 
> It also makes perfect sense to handle nullable FK's different than non-
> nullable ones. One have a constraint imposed, the other not. Returning
> None to a non-nullable FK, *this* would be what I call unexpected
> behaviour.
> 
> Remember also that this is not a pure OO world. If we were seeing
> things as just relations between classes, I would agree with you. But
> we're dealing with a cumbersome thing that is the database, and
> there's always a mismatch between the ER and OO models. [2]
> 
> Anyway, there's certainly nothing wrong or strange on throwing
> exceptions on accessing attributes in Python (or in any dynamic
> language, I would say), as any attribute on Python can be, in fact, a
> method (@property). I'm surprised how opposing you feel on this, my
> feeling is that you come from a different background, working with
> languages that enforce exception handling in a special way (Java, C#).
> But it's really getting into the field of personal taste now.
> 
> [1] http://docs.djangoproject.com/en/1.1/ref/models/querysets/#id5
> [2] http://www.sbql.pl/Topics/ImpedanceMismatch.html
> 

-- 
You received this message because you are subscribed to the Google Groups 
"Django developers" group.
To post to this group, send email to django-develop...@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