bmuller/twistar

dbobject.count() breaks dbobject.save()

Closed this issue · 6 comments

It appears that when bdobject.count() is called count() gets added to the object schema by some method. After the call to count() is executed calls to save() will throw 'table does not have a column count()' error. I am using the development branch of twistar, twisted 11.0, sqlite, and python 2.7.1.

Just to clarify, you're saying that when you call count() as a class method all existing instances of that class cannot be saved - is that the case?

Dear Brian,
Yes that is correct.

R/ Justin
On 9/8/11 1:26 PM, Brian Muller wrote:

Just to clarify, you're saying that when you call count() as a class method all existing instances of that class cannot be saved - is that the case?

I've written a test for the scenerio you described and the test passes. It's in a branch called count_save_test - you can view the commit here - a50dea0

What I see is a similar issue... for some reason after calling count() on a hasmany relationship:

for ex User.pictures.count()
and then allocating a Picture object, my picture object is defined in this way:

cls = Picture()
Picture object: {'count(*)': None}

then I cannot set any attr and save fails:
TWISTAR query: INSERT INTO pictures VALUES ()

The problem is that I'm not being able to reproduce it with test, while in my code happens consistently.
If I remove the call to count() everything works ok.

Btw, I'll continue to investigate...

Seems that a colleague of mine found out the issue.

The problems arise when the model you are counting is not yet in the Registry.SCHEMAS .
So, as soon as you do a .count() call on a schema not yet in cache, the valuesToHash function places count(*) as schema definition for that tablename.

Within test, that not happens because Picture is already allocated on init.
You can easly reproduce it by not creating a Picture on test init and calling Picture.count() on it.

The solution is to bypass caching on such queries or using, for example, runQuery() instead of select() which does not call valuesToHash.

if we'll find and elegant method to fix that, i'll post on my branch.

thanks to @flaviogrossi for finding out :)

Here a test example which fails:
VoiSmart@aedf316