Opened 2 years ago

Closed 2 years ago

Last modified 18 months ago

#28406 closed Bug (invalid)

bug with HStore that has a default value of empty dict - {}

Reported by: Eyal Elkevity Owned by: nobody
Component: Database layer (models, ORM) Version: 1.11
Severity: Normal Keywords: hstore
Cc: Craig de Stigter Triage Stage: Unreviewed
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description

using django version 1.11.2 I have in one of my models an HStoreField. I've defined this field with "default={}" in the model definition, so when creating a new object (using objects.create) - the new hstore field will be an empty dictionary.

however - there is a weird bug, If I create a first object, it is created with an empty dict indeed. but when creating another object, instead of an empty dictionary - it is loaded with the dictionary of the previous, non-related object!!. I'm not sure where's the problem in django's code but maybe it's related to models/base.py, in line 518 there's a "if kwargs" which returns false in the case of the empty dict that is my default. maybe it should return something?

my workaround was simple of course - stop using the default value. just wanted to let you know...

Change History (4)

comment:1 Changed 2 years ago by Tim Graham

Resolution: invalid
Status: newclosed
Type: UncategorizedBug

As documented:

The default can’t be a mutable object (model instance, list, set, etc.), as a reference to the same instance of that object would be used as the default value in all new model instances. Instead, wrap the desired default in a callable.

In other words, you should use default=dict.

comment:2 Changed 18 months ago by Craig de Stigter

I just got bit by this and it took several hours to track down what was wrong. Some thoughts:

  • Seems the docs should say "shouldn't" here rather than "can't", since HStoreField happily accepts a mutable default value.
  • There should be a load-time check for this. It's an easy mistake to make, and very confusing / hard to track down.
  • In fact, why doesn't the field reject default={} outright? Not every mutable value is obvious, but dict instances are probably 99% of them, so it could check for those.

comment:3 Changed 18 months ago by Craig de Stigter

Cc: Craig de Stigter added

comment:4 Changed 18 months ago by Tim Graham

#28577 added checks for JSONField and ArrayField default. I added a PR to do to the same for HStoreField.

Note: See TracTickets for help on using tickets.
Back to Top