我正在尋找一種方法來將UnitOfWork返回到乾淨的狀態,而無需清除整個事物。我仍然想訪問我已經加載的實體。這是我所擁有的基礎,但我不確定這是否會以奇怪的方式打破主義。重置Doctrine中的所有UnitOfWork更改
$uow = $em->getUnitOfWork();
$uow->computeChangeSets();//Can this be called once here, or should it be called in the inside loop so we get fresh information after a potential cascading refresh or persist?
foreach ($uow->getIdentityMap() as $className => $entities) {
foreach ($entities as $oid => $entity) {
if ($uow->isEntityScheduled($entity)) {
if ($uow->isScheduledForInsert($entity)) {
$uow->scheduleForDelete($entity);//Removes from the insert list without cascading delete or calling removal events
} elseif ($uow->isScheduledForUpdate($entity)) {
$em->refresh($entity);
} elseif ($uow->isScheduledForDelete($entity)) {
$em->persist($entity);
$em->refresh($entity);//Should I re-call computeChangeSets() here so I can check if the entity is now scheduled for update?
}
}
}
}
對於上下文:我正在運行一個批處理操作,其中每個記錄處理後都會持續進行所需的更改。如果一個記錄中的錯誤失敗,因爲,失敗是處理,但它可以用這種類型的異常打破批次的休息:
A new entity was found through the relationship FOO#bar that was not configured to cascade persist operations for entity: otherFooBar .
因爲我並不需要從處理記錄保存更改如果失敗,我想簡單地清理所有更改並保持對象圖形不變,同時繼續處理批處理。
我已經閱讀了教條源,看起來這應該可以正常工作,但我對Doctrine的內部並不熟悉。有沒有人看到或知道這種方法的缺陷/陷阱或知道更好的方法來實現這一目標?
編輯:澄清這個問題背後的原因。
當處理記錄時發生錯誤時,這可能會使UoW/EntityManger處於不能被清除而不能保留的位置。在我的特殊情況下,錯誤留下了現有的已更改的實體,並且鏈接未保持實體的關係未配置爲級聯持久化,導致所有後續持久化失敗。此時,如果我想繼續處理批次並跳過失敗的記錄,我有兩個選擇:
1)清除EntityManager並從數據庫中重新加載所有業務邏輯實體。但這意味着恢復功能不能是通用的,必須定製以知道每次更改時要重新加載和調整哪些實體。
2)清潔使用的UnitOfWork的現有能力EntityManager的,這使得代碼是通用的,不需要進行持續改進。
清除實體管理器的問題是我試圖從錯誤中恢復。有些實體在發生錯誤時加載,代碼仍然存在,並且不會從EntityManager中分離出來。我讀到的有關'computeChangeSets'的所有內容都表明,自己調用它會打破堅持的行爲。由於我試圖阻止圖中的任何新項目持續存在,這不是問題。 http://stackoverflow.com/a/16554133/1153227 – Omn
我真的不明白你的使用情況。您是否嘗試處理Doctrine持續循環期間發生的錯誤,或者您是否正在處理應用中其他位置的錯誤? –
我處理這使了EntityManager在所有未來持續,直到被清除會導致一個錯誤的狀態的非學說有關的錯誤。我已經編輯了我的問題,並進一步澄清了爲什麼我以這種方式解決問題。 – Omn