2

想象一下2個實體 - 用戶和組。用戶總是在一個組中,而一個組總是有一個超級用戶。這些實體類只保存數據(沒有邏輯)。使用Symfony的依賴注入組件在數據映射模式中循環依賴

兩個實體都有Mapper類(處理SQL查詢):UserMapper和GroupMapper。兩者都依賴於對方的時候查詢它的實體:

  • 查詢用戶時UserMapper需要GroupMapper來獲取用戶的$組
  • 查詢組時GroupMapper需要UserMapper檢索集團$超級

我一直在使用Symfony的依賴注入組件在構造函數中注入依賴關係。但在這種情況下,我遇到了這種方法的麻煩。我知道我可以使用像Doctrine這樣的ORM來處理這個問題,但目前這不是一個選項。這個問題最乾淨/最好的解決方案是什麼?

這裏是方案的圖示:

Problem illustration

回答

0

一個可能用於這種方法是引入第三服務SL和注入它,這樣的:

  • 映射器是一個接口
  • GroupMapper實現Mapper,通過注入接收SL
  • UserMapper實現Mapper,通過in接收SL jection
  • SL擁有一些方法:
    • 功能寄存器($名,映射M)
    • 功能的get($名):映射
  • GroupMapper :: __結構(SL $ SL,... )包括如下:
    • $ this-> sl = $ sl;
    • $ this-> sl-> register('group',$ this);
  • UserMapper :: __結構(SL $ SL,...)的類似:
    • $這個 - > SL = $ SL;
    • $這 - > SL->寄存器( '用戶',這$)

然後,假定$嗯是獲得UserMapper的一個實例的DIC,並且它需要使用的組映射器服務:$ um-> sl-> get('user')返回組映射器。

實質上,這個歸結爲實現一個服務定位器,它不是很好,但它的優點是它很小,本質上是一個完整的DIC的過濾子集。只要您在所有相互依賴的服務初始化之前都沒有開始使用這兩種服務,這種方法就行得通,這可能不適合某些情況。

另一種可能是讓你的服務ContainerAware並在同一使用它,但恕我直言,這是糟糕的,雖然有點短,因爲你基本上是允許使用來自DIC東西沒有任何控制。我建議的模式使「接觸表面」最小化。

+0

是的,我的解決方案几乎與當時相同。我有一段時間來思考它(一年多了,呵呵),我相信還有第三種解決方案 - 使用Lazy Load Proxy。我認爲最終的解決方案將是一個2階段setter注入,但這將需要修改DI組件來源。 –