djongo
djongo copied to clipboard
Embedded Model attributes not working
Embedded Model fields attributes do not work
class Blog(models.Model):
name = models.CharField(max_length=100, db_index=True)
tagline = models.TextField()
image = models.ImageField(upload_to='upload/path')
created = models.DateTimeField(auto_now_add=True)
class Meta:
abstract = True
class Entry(models.Model):
blog = models.EmbeddedModelField(
model_container=Blog
)
headline = models.CharField(max_length=255)
objects = models.DjongoManager()
- Migration do not create index for
blog.name
. I ended up using a patch withpymongo
thruEntry.objects
to create the index - when creating a new entry with an embedded blog, no error is thrown but
blog.created
does not get the current date as expected of theauto_now_add
attribute - also the image field does not upload image to specified path and that is the most worrying one cuz with the
created
field i could just override thesave()
of the entry to take care of that
So i can conclude that attributes on field of embedded model are not having any effects when creating the embedded document.
Can someone please provide a workaround especially for the image field
python 3.6 django 2.0.7 djongo 1.2.29
I ended creating a custom EmbeddedModelField
and overwriting the pre_save
so that each fields pre_save will run
def pre_save(self, model_instance, add):
value = getattr(model_instance, self.attname)
# go thru each field and and run its pre_save
for fld in value._meta.get_fields():
if not fields.useful_field(fld):
continue
# for date/datetime fields with auto_add_now when updating and the field value tend
# to set to null when the incoming field value is not set.
# we therefore have to set it to its original value so null is not inserted in the db
if isinstance(fld, models.DateTimeField) or isinstance(fld, models.DateField):
fld_value = getattr(value, fld.attname)
if fld.auto_now_add and not add and not fld_value:
instance_model = type(model_instance)
initial = instance_model.objects.filter(pk=model_instance.pk).values_list(
self.attname, flat=True).first()
val = getattr(initial, fld.name)
# django already saves all dates in UTC so we might as well assume the date
# coming out is in UTC and if not tz info is provided to add it.
# works around django naive datetime warning
if not val.tzinfo:
val = pytz.UTC.fromutc(val)
setattr(value, fld.name, val)
continue
fld.pre_save(value, add)
if isinstance(value, fields.ModelSubterfuge):
return value
subterfuge = fields.ModelSubterfuge(value)
return subterfuge
with this embedded fields attributes like auto_add_now
, update_to
work with exception of db_index
which doesnt work yet cuz i guess it is used during migration.
If the creators could investigate the code above and factor a better version into the project it would be helpful
@nesdis any comments on this issue??
I ended creating a custom
EmbeddedModelField
and overwriting thepre_save
so that each fields pre_save will rundef pre_save(self, model_instance, add): value = getattr(model_instance, self.attname) # go thru each field and and run its pre_save for fld in value._meta.get_fields(): if not fields.useful_field(fld): continue # for date/datetime fields with auto_add_now when updating and the field value tend # to set to null when the incoming field value is not set. # we therefore have to set it to its original value so null is not inserted in the db if isinstance(fld, models.DateTimeField) or isinstance(fld, models.DateField): fld_value = getattr(value, fld.attname) if fld.auto_now_add and not add and not fld_value: instance_model = type(model_instance) initial = instance_model.objects.filter(pk=model_instance.pk).values_list( self.attname, flat=True).first() val = getattr(initial, fld.name) # django already saves all dates in UTC so we might as well assume the date # coming out is in UTC and if not tz info is provided to add it. # works around django naive datetime warning if not val.tzinfo: val = pytz.UTC.fromutc(val) setattr(value, fld.name, val) continue fld.pre_save(value, add) if isinstance(value, fields.ModelSubterfuge): return value subterfuge = fields.ModelSubterfuge(value) return subterfuge
with this embedded fields attributes like
auto_add_now
,update_to
work with exception ofdb_index
which doesnt work yet cuz i guess it is used during migration.If the creators could investigate the code above and factor a better version into the project it would be helpful
Hi, would you share the code?? There's some piece of it missing in your comment
Hi @eldano1995, I know it's an old issue. But, Im facing a bit similar issue, the embedded model with imagefield within it do not save the path of the content (and the content is not written into the disk) passed into it. Perhaps you found a fix before? Thank you.