如何使用C#/Dapper插入多重嵌套项目?

问题描述 投票:0回答:1

我有一系列如下所示的课程:

public class SignUpList {
    public int? SignUpListId { get; set; }
    public IEnumerable<SignUpItem> Items { get; set; }
}

public class SignUpItem {
    public int? SignUpItemId { get; set; }
    public int? SignUpListId { get; set; }
    public IEnumerable<ItemPerson> Persons { get; set; }
}

public class ItemPerson {
    public int? ItemPersonId { get; set; }
    public int? SignUpItemId { get; set; }
    public int PersonId { get; set; } //fk reference to another table
}

(想象一下“注册天才”这样的场景:我创建了一个名为“课堂聚会”的列表。列表中我有“盘子”、“叉子”和“餐巾”。然后每个 4 人可以注册)。

现在,当我使用

SignUpList
的 API 端点被命中时,我很高兴使用一些 UDT 作为参数并将所有记录合并到现有表中。

当我在

ItemPersonId
上还没有
ItemPerson
时,我对如何首次插入记录的逻辑有疑问。

例如:

我可以使用 Dapper 来保存我的

SignUpList
并取回
SignUpListId

    var listId = ExecuteScalar<int>("dbo.SaveList", parameters, commandType: StoredProcedure) 

然后我可以将其填充到 UDT 中以插入

SignUpLists
(或者甚至将它们插入到同一查询中)。我的问题来自下一层嵌套:

如何将

SignUpItemId
戴在我身上?我不能只是将它们塞入 UDT,因为我无法知道该人连接到哪个
SignUpItem

我可以做一些

foreach
循环恶作剧 -

    foreach (var item in SignUpList.Item) {
        var itemId = ExecuteScalar("[dbo].[SaveItem]", parameters); //assume I've created appropriate parameters
        //Insert into my DataTable based off the UDT for ItemPerson
    }
    _ = ExecuteAsync("dbo.SavePersons", params) //(params being UDT table populated in the foreach above)

但就数据库操作而言,这种方法成本高昂。

我考虑过的另一个选择是一次性批量插入所有

SignUpItems
,但是如何将这些 ID 绑定回我现有的列表呢? (我认为我无法根据退货制作一个新的
SignUpItem
列表,因为它不会将
Person
与项目绑定在一起,这就是整个问题)。

我还考虑使用“行号”并将其用作伪ID来链接它们。这需要向父项添加一个新字段,但如果我试图最小化数据库连接,这可能是合适的选择?

我在 Dapper 中缺少一些非常简单的东西可以更有效地处理这个问题吗?

不幸的是,由于应用程序的性质,要求单独保存列表与项目并不是一个可行的选择,否则这将是我的首选方法。

如果不同的数据结构会更好,我也愿意考虑它,但我很难想象一种方法来使这个逻辑在没有三重嵌套的情况下工作。我还考虑过将 ItemPerson 作为 SignUpItem 上的序列化 JSON 字段,但我也需要能够从中查询。

c# dapper
1个回答
0
投票

对于您的情况,我建议如下:

  1. 定义3个用户定义的表类型,对应您的实体类型
  2. 创建采用上述类型的三个参数的过程
  3. 将数据扁平化为 3 个不嵌套的集合,并在单个过程执行中将它们传递给前面提到的过程
  4. 现在,要解决链接问题,请使用人工 ID 扩展数据库类型和 C# 类,以模拟实体的父子链接/关系
  5. 在某种循环中分配它们
  6. 在存储过程中,您将能够关联适当的记录

我用过这种方法几次,它总是对我有用

© www.soinside.com 2019 - 2024. All rights reserved.