2009年2月12日星期四

Re: [fw-db] Redundant information updates / Zend_Db_Mapper

Hi Moritz,

Yes, concurrency problems are always a pain. The Zend_Db_Mapper proposal
indicates some built-in support for optimistic offline locking (from
PoEAA, [1]), although the feature is not elaborated on in the proposal
documentation. It appears that you can define a field in the mapped
entity objects to serve as version field, and the mapper would assume
responsibility for validating those version stamps before committing
changes to the database.

Of course, you can also implement such a system your self fairly easily
in your table data gateways.

@Benjamin: could you add some more detail about how you see this working
in Zend_Db_Mapper?

Regards,
Bryce Lohr

[1] http://martinfowler.com/eaaCatalog/optimisticOfflineLock.html


Moritz Mertinkat wrote:
> @Zend_Db_Mapper: Yes, I thought of that approach and transactions are
> not the problem. The problems here are concurrency and race
> conditions. Imagine I increase the numberOfMessages property of the
> Folder entity object from 100 to 101 and another process does exactly
> the same at the same time.... Then we would have 102 messages, but the
> counter would have been updated two times to 101. Thus I would have to
> lock the folder row (SELECT ... FOR UPDATE) at the start of the
> transaction and hell ... :-)
>
> Maybe it's possible to add something like _post(Insert|Update|Delete)
> to Zend_Db_Mapper, but I'm not sure if that would break the whole thing.
>
> Regards,
> Moritz
>
> Bryce Lohr schrieb:
>> With respect to Zend_Db_Mapper, the most likely approach I can think
>> of would be where you'd have "numberOfMessages" as a property of a
>> "Folder" entity object. You would code your logic to calculate the
>> correct value for this property, assign it, and then let the mapper
>> update the DB just as it would with any other property. The catch
>> with this approach is that the logic for keeping up with the count
>> must be entirely within the object model, therefore, any operation
>> which directly updates the database would bypass that. If you really
>> want to guarantee that field stays in sync in the database, you
>> really do need triggers and proper transaction isolation.
>>
>> Regards,
>> Bryce Lohr
>>
>>
>> Moritz Mertinkat wrote:
>>> Hi there,
>>>
>>> I've a question regarding best practices for updating redundant
>>> information without using triggers. I know I could use triggers for
>>> simple tasks, but it's not always an option.
>>>
>>> Let's assume I have folders and messages with each folder having a
>>> numberOfMessages property. Thus, everytime I'm adding or deleting a
>>> message I have to adjust this property (also when moving a message
>>> from one folder to another).
>>>
>>> Currently I'm working with Zend_Db_Table_Row_Abstract derived "value
>>> objects" (Row_Message and Row_Folder) and Zend_Db_Table_Abstract
>>> derived "gateway objects" (Table_Message and Table_Folder).
>>> I'm also using two models called Model_Message and (surprise!)
>>> Model_Folder.
>>>
>>> The message model has methods like
>>> - add(array $data) : void
>>> - delete($primaryKey) : void
>>> - get($primaryKey) : Message_Row
>>> - move(Row_Message $message, $folderId) : void
>>> - moveToSpam(Row_Message $message) : void
>>>
>>> Now the question is: where should I update the folder's message count?
>>>
>>> First I implemented it in Model_Message's add(), delete() and move()
>>> methods, but that seemed to be a bit naive, because one could simple
>>> do something like
>>> $message = $messageModel->get(17);
>>> $message->folder_id = 3;
>>> $message->save();
>>> and nothing got updated in the old and new folder records.
>>>
>>> So I moved the count update stuff to Row_Message using
>>> _postDelete(), _postInsert() and _postUpdate() methods and doing
>>> some plain vanilla queries to update the folder record(s). (I
>>> could've used Row_Folder, but that would be a bit like using a
>>> sledgehammer to crack a nut, I thought).
>>>
>>> What do you think about this approach? Is it "common"?
>>>
>>> And what about this issue regarding the proposed Zend_Db_Mapper?
>>> http://framework.zend.com/wiki/display/ZFPROP/Zend_Db_Mapper+-+Benjamin+Eberlei
>>>
>>> Will there be a possibility to achieve things like these?
>>>
>>> Looking forward to your feedback :-)
>>>
>>> Best regards,
>>> Moritz
>>>
>>

没有评论: