Code

#20093 closed New feature (worksforme)

Allow Model Cache Invalidation

Reported by: s.shanabrook@… Owned by: nobody
Component: Database layer (models, ORM) Version: master
Severity: Normal Keywords:
Cc: Triage Stage: Unreviewed
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description

I propose allowing a model instance to have its fields refetched from the database. For instance, it could work something like this.

>>> model = MyModel.objects.create()
>>> model.field
None
>>> model.field = 'New Value'
>>> model.field
'New Value'
>>> model.invalidate()
>>> model.field
None

This is useful when testing a model. For instance, if I want to test a function that modifies a model, I currently have to re get the model from the database, before testing its fields, to make sure they have been saved.

model = MyModel.objects.create()
model_modifier(model)
assert model.field == 'New Value'
model_non_caches = MyModel.objects.get(pk=model.pk)
assert model.field == 'New Value'

Attachments (0)

Change History (4)

comment:1 Changed 13 months ago by jcatalan

  • Needs documentation unset
  • Needs tests unset
  • Patch needs improvement unset

I'm not sure if that's the responsibility of your function's test. The actual saving into the DB should be tested in an ORM or database layer test (which for sure must be already around django's tests). I think you should only test the different cases your function calls to the save method for your model but not the saving itself. And you could do just that by mocking the object and then checking if the save method was called.

Even if you are overriding the save method for your model, you should have a separate test for the overridden version too. Either way IMHO this is not what you should be testing in the example you provide.

comment:2 Changed 13 months ago by s.shanabrook@…

I am testing a post_save signal, and so I need to make sure it doesn't save a model recursively. I save only one field using update_fields. What would you say is the proper way to test something like this? Is there a better method than re-retrieving the object from the database to make sure it saved the field?

comment:3 Changed 13 months ago by jcatalan

What I would do is mock the object and check that the save method is called with the proper args (ie. update_fields as required in this case). In case you don't know it, what I would use to mock this is python mock library: https://pypi.python.org/pypi/mock

You might want to check its assert_called_once_with method.

Last edited 13 months ago by jcatalan (previous) (diff)

comment:4 Changed 13 months ago by anonymous

  • Resolution set to worksforme
  • Status changed from new to closed

Thanks for that, yeah that seems like a good idea. I also relived I should check my signal function differently anyway. In a separate test, just calling the signal receiver and making sure the arguments work out the right way.

Add Comment

Modify Ticket

Change Properties
<Author field>
Action
as closed
as The resolution will be set. Next status will be 'closed'
The resolution will be deleted. Next status will be 'new'
Author


E-mail address and user name can be saved in the Preferences.

 
Note: See TracTickets for help on using tickets.