You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

EF Core多对多关系配置:如何在Web API Swagger中获取书籍关联出版商

解决EF Core多对多关系中Book返回关联Publisher的问题

1. 完善实体类的导航属性

当前实体缺少两个关键导航属性,需要补充以支持双向关联查询:

public class Book
{
    [Key]
    public int BookId { get; set; }
    public string? BookName { get; set; }
    // 添加关联中间表的集合属性
    public ICollection<BookPublisher>? BookPublishers { get; set; }
}

public class Publisher
{
    [Key]
    public int PublisherId { get; set; }
    public string? PublisherName { get; set; }
    public ICollection<BookPublisher>? BookPublishers { get; set; }
}

public class BookPublisher
{
    [Key]
    public int BookPublisherId { get; set; }
    public int BookId { get; set; }
    public int PublisherId { get; set; }

    public Book? Book { get; set; }
    // 添加关联Publisher的导航属性
    public Publisher? Publisher { get; set; }
}

2. 显式配置多对多关系(可选但推荐)

在DbContext的OnModelCreating方法中,显式配置中间表的外键关联,确保EF Core正确识别关系:

protected override void OnModelCreating(ModelBuilder builder)
{
    builder.Entity<Publisher>().ToTable("TAB_Publisher", "dbo");
    builder.Entity<BookPublisher>().ToTable("TAB_BookPublisher", "dbo");
    builder.Entity<Book>().ToTable("TAB_Book", "dbo");

    // 配置Book与BookPublisher的外键关联
    builder.Entity<BookPublisher>()
        .HasOne(bp => bp.Book)
        .WithMany(b => b.BookPublishers)
        .HasForeignKey(bp => bp.BookId);

    // 配置Publisher与BookPublisher的外键关联
    builder.Entity<BookPublisher>()
        .HasOne(bp => bp.Publisher)
        .WithMany(p => p.BookPublishers)
        .HasForeignKey(bp => bp.PublisherId);
}

3. 添加查询书籍及关联出版商的方法

在DbContext中新增GetBooks方法,与GetPublishers逻辑对称,通过Include+ThenInclude加载关联数据:

public List<Book>? GetBooks()
{
    if (Books != null)
        return Books
               .Include(b => b.BookPublishers)
               .ThenInclude(bp => bp.Publisher)
               .ToList<Book>();
    else
        return null;
}

4. 解决序列化循环引用问题

由于实体间存在双向导航,直接返回会触发Json序列化循环引用错误,需在Web API配置中忽略循环引用:
在Program.cs的服务配置中添加:

builder.Services.AddControllers()
    .AddJsonOptions(options =>
    {
        options.JsonSerializerOptions.ReferenceHandler = System.Text.Json.Serialization.ReferenceHandler.IgnoreCycles;
    });

最终返回示例

调用GetBooks后,Swagger将返回如下结构的结果:

[
  {
    "BookId": 1,
    "BookName": "TEST1",
    "BookPublishers": [
      {
        "BookPublisherId": 1,
        "BookId": 1,
        "PublisherId": 1,
        "Book": null,
        "Publisher": {
          "PublisherId": 1,
          "PublisherName": "Publisher1",
          "BookPublishers": null
        }
      }
    ]
  }
]

内容的提问来源于stack exchange,提问作者Newbie_thefirst

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.15 07:04:53