我有一个使用实体框架的ASP.NET MVC应用程序。我已经开发了两个模型,使用SQL Server 2008 R2数据库的数据库优先(代码)方法。一个模型本质上是父模型,另一个是子模型,其中包含父模型的数据库生成列的外键。
伪代码:
CREATE TABLE PARENT
(
ROWID BIGINT IDENTITY(1,1) NOT NULL,
VALUE NVARCHAR(255) NOT NULL,
PRIMARY KEY(ROWID)
);
CREATE TABLE CHILD
(
ROWID BIGINT IDENTITY(1,1) NOT NULL,
PARENT_ROWID BIGINT NOT NULL,
VALUE NVARCHAR(255) NOT NULL,
PRIMARY KEY(ROWID),
FOREIGN KEY(PARENT_ROWID) REFERENCES PARENT(ROWID)
);
所有这些工作都很好,我可以将数据绑定到我的模型,编辑字段等等。我的问题是,如果我试图为这些模型创建记录,那么当子模型的外键在父模型中时,如果我同时创建它们,那么如何才能做到这一点呢?
所以,我目前的基本步骤是:
-
获取
PARENT
要插入数据库的模型
-
插入
起源
模型
-
呼叫
SaveChanges()
-
对于每个家长:
-
为父级获取FK
-
获取要插入数据库的子模型列表
-
对于每个子模型,使用该FK插入子模型
-
呼叫
SaveCechange()
-
其他模型的其他操作和数据库更新
-
呼叫
SaveCechange()
我相信我可以优化它,但这不是我关心的。在我看来,有一些方法可以做到这一点,而无需手动查找FK或手动设置FK。如果必须的话,我可以这样做,但我只想用一个
SaveCechange()
调用在单个事务中强制执行这些命令。我在找一些符合以下条件的东西:
-
获取要插入数据库的父模型列表
-
为每一位家长
-
插入父项并返回新FK(不保存)
-
获取要插入数据库的子模型列表
-
对于每个子模型,使用该FK插入子模型
-
其他模型的其他操作和数据库更新
-
呼叫
SaveCechange()
为了提供一些上下文,我的实际表中有许多列不能保证是唯一的(这就是pk在rowid上的原因),并且这些行中的每一行与子表之间都有一个“无对多”关系,其中子表也可能有非唯一行。不是很理想,但这是我们现在的业务需求。我在这里加入了伪代码,因为实际的代码是专有的,但是如果需要的话,我可能会创建一个真正的模型。
有什么建议吗?
谢谢你
编辑:
所以我按照建议修改了代码以使用导航属性。这几乎奏效了。这是我的代码:
List<PARENT> parents = getParents();
List<CHILD> children = getChildren();
foreach (PARENT parent in parents)
{
db.PARENT.add(parent);
foreach (CHILD child in children)
{
child.PARENT = parent;
db.CHILD.add(child);
}
}
db.SaveChanges();
乍一看,这正是我要找的。但是,当我运行它时,子记录只为第一个父记录插入。例如,如果我有3个父记录和3个子记录,那么我的子表中应该有9个新记录。但是,在这段代码之后,对于第一个父级,我只有3条记录。
我假设这与我重复使用相同的子列表有关,并且实体框架以某种方式将它们视为重复项。我将它移动到父for循环中,如下所示,它按预期工作:
List<PARENT> parents = getParents();
foreach (PARENT parent in parents)
{
db.PARENT.add(parent);
List<CHILD> children = getChildren();
foreach (CHILD child in children)
{
child.PARENT = parent;
db.CHILD.add(child);
}
}
db.SaveChanges();
但是,我不希望这样做,因为getchildren()函数相当麻烦。有什么想法吗?