簡體   English   中英

EF Core 導航屬性自行加載

[英]EF Core navigation properties loads itself

我的 DB_Context 中有以下類作為實體。

public class Glossary
{
    #region Properties
    public Guid GlossaryId { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }


    #region NavigationProperties
    public virtual ICollection<Item> Items { get; set; }
    #endregion
}
public class Item
{
    #region Properties
    public Guid ItemId { get; set; }
    public string Name { get; set; }
    public string Definition { get; set; }

    #region ForeignKeys
    public Guid GlossaryId { get; set; }
    #endregion
    #endregion

    #region Navigation Properties
    public virtual Glossary Glossary { get; set; }
    #endregion
}

當我嘗試使用詞匯表類型的實體的項目

public async Task<IEnumerable<Glossary>> Get()
    {
        return await _context.Glossaries
                    .Include(x => x.Items)
                    .OrderBy(x => x.CreatedAt)
                    .ToListAsync();
    }

我從我的 API 得到以下 JSOn:

{
    "glossaryId": "674c1358-861b-11ea-9370-e45a1762a61b",
    "name": "Test1",
    "description": "Description of Test1",
    "items": [
        {
            "itemId": "f2847601-86db-11ea-9370-e45a1762a61b",
            "name": "TestItem",
            "definition": "TestDefinition",
            "glossaryId": "674c1358-861b-11ea-9370-e45a1762a61b",
            "glossary": {
                "glossaryId": "674c1358-861b-11ea-9370-e45a1762a61b",
                "name": "Test1",
                "description": "Description of Test1",
                "items": []
            }
        }
    ]
}

我的問題是,詞匯表的項目也包括它的詞匯表,我不想要。

有什么方法可以只包含一個導航屬性而不再次包含相同的導航屬性?

為了避免這個問題,在每個項目中,我總是使用 DTO 和 Automapper。 通常,從來沒有必要按原樣歸還數據庫 model:只提供解決功能所需的內容。 在您的情況下,您需要歸還所有詞匯表。

在您的情況下,我會介紹 Automapper。 在您的 Net.Core 項目上安裝Automapper后,我將創建 2 個 DTO,稱為:

public class GlossaryDto : ICustomMapping

    public Guid GlossaryId { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }      

    public ICollection<ItemDto> Items { get; set; }

    public void CreateMappings(Profile configuration)
    {
        configuration.CreateMap<Glossary, GlossaryDto>();
    }

public class ItemDto  : ICustomMapping
{
    public Guid ItemId { get; set; }
    public string Name { get; set; }
    public string Definition { get; set; }

    public Guid GlossaryId { get; set; }

    public void CreateMappings(Profile configuration)
    {
        configuration.CreateMap<Item, ItemDto>();
    }

}

現在您可以簡單地重寫您的 Get 以返回 Dto 而不是數據庫 model(實體):

public async Task<IEnumerable<GlossaryDto>> Get()
    {
        var result = await _context.Glossaries
                    .Include(x => x.Items)
                    .OrderBy(x => x.CreatedAt)
                    .ToListAsync()
        return await mapper.Map<IEnumerable<GlossaryDto>(result);
    }

通過這種方式,我們從 Dto 中刪除了循環引用,您不會有任何問題:由於 ItemDto 沒有 GlossaryDto 的“導航”屬性,因此鏈已正確關閉。 您的 JSON 擁有所有必要的信息。 將來,如果您需要返回帶有 GlossaryDto 導航屬性的 ItemDto,請創建一個具有不同名稱的新屬性。 您還可以創建一個等於數據庫 Model 的 DTO,然后通過指定MaxDepth()使用自動映射器“剪切”循環引用,但我更喜歡為真正需要的內容創建特定的 DTO。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM