在我爲我的項目提供新功能的工作中,我決定擴展模型。我決定使用基類,將通用的方法分組,並且只有很少的子類,都保存在一個集合中。Doctrine ODM返回代理對象的基類,而不是子分類的文檔
基地,抽象類:
/**
* @MongoDB\Document(repositoryClass="EntryRepository")
* @MongoDB\MappedSuperclass
* @MongoDB\InheritanceType("SINGLE_COLLECTION")
* @MongoDB\DiscriminatorField(fieldName="type")
* @MongoDB\DiscriminatorMap({"entry"="Application_Model_Entry", "image"="Application_Model_Image", "movie"="Application_Model_Movie"})
*/
abstract class Application_Model_Entry
{
abstract function foo();
}
一些具體類(我有幾個人,類似的,但有些是抽象的):
<?php
/** @MongoDB\Document */
class Application_Model_Image extends Application_Model_Entry
{
function foo()
{
return 'foo';
}
}
過渡後,我打開我的索引頁面,並出現一個錯誤 - PHP試圖調用抽象方法,因爲Doctrine返回的對象是基類類的代理。我想這是因爲我改名從Application_Model_Image
收集到Application_Model_Entry
和內部對象引用(的DBRef
$ref
領域)仍然指向Application_Model_Image
,但我注意到一些有趣的:總是第一個查詢結果的具體類的適當的文件,其餘的都是基類代理 - 在我從數據庫中刪除第一個對象後,第二個對象變好了。
在單個對象顯示頁面上,所有對象都可以正常工作,所以我想也許這是Zend Framework的頁面類迭代結果的一些問題,所以我跳過了尋呼機並直接從查詢中刪除對象。我打印了100個第一個結果的類,其中一些有適當的類(Snippet of that list on pastebin)。我查看了數據庫,但我沒有注意到這些數據(working vs not working)。我想也許這是引用錯誤,但正如我上面寫的,如果它是第一個結果列表中的相同的對象可以工作。
任何想法或提示?我可以調試更多,但我需要被告知在Doctrine的代碼裏面看什麼。
'Document'註釋不應該與'MappedSuperclass'一起使用。前者用於具體實現,後者用於抽象類。我不理解有關查詢結果超出第一個代理對象的位,因爲代理只能在ReferenceOne/Many關係的上下文中創建爲佔位符。 – jmikola 2013-02-25 16:11:38
查詢結果就像我在第一個pastebin鏈接中顯示的一樣 - 第一個是具體類,其餘大部分是代理(ProjectProxy \ __ CG __ \ Application_Model_Entry具體)。刪除''文檔''註釋後,一切似乎都很好,非常感謝。 目前情況並非如此,但如果我想,我還可以指示整個繼承樹的集合名稱嗎? – leafnode 2013-02-25 19:42:58
我不相信'MappedSuperclass'支持任何選項,所以你必須做實驗。所有繼承類仍然應該按照單個集合繼承映射存儲在同一個集合中,但名稱本身可能最終將從抽象類的名稱派生。 – jmikola 2013-02-25 20:02:59