Open ewills opened 2 years ago
Sorry to not respond sooner @ewills. Interesting. You are pushing the limits of my experience in this area. It might be interesting to have 2 caches. One specifically for the call frame that is tracking the objects that are are partially hydrated so they don't get doubly created. Then the other to hold the hydrated objects. I agree that putting the partially hydrated instances in the cache might be bad unless there was some sort of lock in place.
I've got a scenario where a DatabaseTable A has an eager ForeignCollectionField referring to table B, which has a foreign DatabaseField referring to table C, which has a foreign field referring back to table A. When querying for an uncached instance of A, I'm seeing:
At this point I've got the instance of A from step 2 (and 6) in my object cache along with an instance of C that has a foreign DatabaseField referring to the instance of A from step 4.
I could avoid this particular scenario by lowering maxForeignAutoRefreshLevel on either B's reference to C or C's reference to A, but we add columns to our data model often and I'd rather not consider these possible cycles each time we do this!
So my question is: would it make sense to modify BaseMappedQuery mapRow() to add newly-created instances to the object cache prior to resolving foreign references (i.e., between steps 2 and 3 above)? That way (I think) the subsequent mapRow calls for the foreign references would be find the cached instance from step 2 rather than creating a new instance?
I can also imagine that it might be a bad idea to add partially-hydrated instances to the object cache, so this idea may be a nonstarter!