C# 实体框架-更新没有Id的实体
我在网上找到了很多问题和文章,但没有一篇真正解决了我的问题 我的模型如下所示(我将所有非基本属性分条): 每天都会更新“Play”(通过包含信息的XML文件)C# 实体框架-更新没有Id的实体,c#,entity-framework,C#,Entity Framework,我在网上找到了很多问题和文章,但没有一篇真正解决了我的问题 我的模型如下所示(我将所有非基本属性分条): 每天都会更新“Play”(通过包含信息的XML文件) 内部播放解析播放信息(XDocument文档) { Play Play=(来自文档子体(“Play”)中的p) 选择新剧本 { 剧院=新剧院 { //性质 }, //性质 LastUpdate=DateTime.Now }).SingleOrDefault(); var actors=(来自doc.XPathSelectElement(
内部播放解析播放信息(XDocument文档)
{
Play Play=(来自文档子体(“Play”)中的p)
选择新剧本
{
剧院=新剧院
{
//性质
},
//性质
LastUpdate=DateTime.Now
}).SingleOrDefault();
var actors=(来自doc.XPathSelectElement(“.//Play//actors”).Nodes()中的
选择新讲师()
{
//性质
});
var parts=(来自doc.XPathSelectElement(“.//Play//parts”).Nodes()中的p)
选择新零件()
{
//性质
}).ToList();
foreach(部分var项目)
{
play.Parts.Add(项目);
}
var reviews=(来自doc.XPathSelectElement(“.//Play//reviews”).Nodes()中的r)
选择新评论
{
//性质
}).ToList();
for(int i=0;i
如果我通过add()添加这个“play”,则将插入play的每个Childobject——不管是否已经存在。因为我需要更新现有的条目,所以我必须做一些事情。我想这里的问题是我在XML中没有Id
据我所知,我有以下选择:
如果有人能在这个问题上为我指明正确的方向,我将不胜感激。好吧,既然还没有答案,我就自己写一封 对于那些想知道的人来说,我成功了——代码看起来非常难看,我想性能更差。但是因为不会有太多的用户,而且这个方法每天晚上只调用一次,所以我现在还可以 我做了什么 好吧,我选择了选项2和3
private Play UpdatePlay()
{
using (RepositoryContext context = new RepositoryContext())
{
HttpRequest http = new HttpRequest();
PlayRepository rep = new PlayRepository(context);
ActorRepository actRep = new ActorRepository(context);
ReviewsRepository revRep = new ReviewsRepository(context);
TheatreRepository insRep = new TheatreRepository(context);
PartRepository partRep = new PartRepository(context);
Parser p = new Parser();
XDocument doc = http.GetPlayInfo();
Theatre theatre = p.ParseTheatreInfo(doc);
List<Actor> actors = p.ParseActorInfo(doc);
List<PlayReviews> playReviews = p.ParseReviewsInfo(doc);
for (int i = 0; i < actors.Count; i++)
{
actors[i] = actRep.AddOrUpdate(actors[i]);
}
for (int i = 0; i < playReviews.Count; i++)
{
playReviews[i].Reviews = revRep.AddOrUpdate(playReviews[i].Reviews);
}
theatre = insRep.AddOrUpdate(theatre);
Play play = p.ParsePlayInfo(doc);
List<Part> parts = GetParts(play);
for (int i = 0; i < parts.Count; i++)
{
List<Actor> lec = (List<Actor>)parts[i].Actors;
for (int j = 0; j < lec.Count; j++)
{
lec[j] = actRep.AddOrUpdate(lec[j]);
}
}
play = rep.AddOrUpdate(play);
context.LoadProperty(play, o => o.Theatre);
context.LoadProperty(play, o => o.Actors);
context.LoadProperty(play, o => o.PlayReviewss);
context.LoadProperty(play, o => o.Parts);
rep.Save();
if (play.Theatre != theatre)
play.Theatre = theatre;
play = rep.AddParts(parts, play);
play = rep.AddActor(actors, play);
for (int i = 0; i < playReviews.Count; i++)
{
playReviews[i].Play = play;
playReviews[i] = revRep.AddPlayInformation(playReviews[i]);
}
rep.Save();
return play;
}
}
我不敢相信这是“正确”的方法。
它感觉和看起来都不对。也许EF也应该受到责备,拿吧
FirstEntityType first = new FirstEntityType();
first.Id = 2;
List<SecondType> list = CreateList(); //Let's say this returns a List with 10 elements
context.FirstEntityType.AddObject(first);
for (int i = 0; i < list.Count; i++)
{
list[i].First = first;
}
//just for arguments sake a second for
for (int i = 0; i < list.Count; i++)
{
context.SecondType.AddObject(list);
}
context.SaveChanges();
FirstEntityType first=新的FirstEntityType();
第一,Id=2;
List=CreateList()//假设它返回一个包含10个元素的列表
context.FirstEntityType.AddObject(第一个);
for(int i=0;i
我还没有测试过这段特定的代码,但根据我的经验,SecondType将有10个新条目,如果我没有错的话,FirstEntityType将有11个条目
为什么??为什么EF中没有一个机制会说“嘿,等等,这些都是一样的!”
我是否认为EF的行为应该像我直接使用db那样错误?在我的示例中,我添加了“first”,这样我就可以假设每当我使用“first”时,它都会被引用。
(我真的希望我的示例能如所述工作-没有时间也不想测试它)不,FirstEntityType不会有11个条目,只有数据库中的一个条目。只要您在一个ObjectContext中,在向上下文添加对象时,将保留标识。但是,当您第二次执行此代码时(在新上下文中),您确实会得到第二个FirstEntityType(或者当FirstEntityType.id是非自动递增主键时出现DABASE异常)。所以:实体框架实际上说:“它们是相同的!”,但这并不是因为相同的id字段,而是因为AddObject创建了一个(临时)EntityKey,它在一个ObjectContext中唯一地标识对象。我希望我仍然有那个代码,因为我做了类似的事情,并最终得到了许多条目。由于所有内容都很好地包装在一个using(context){}中,我非常确定我使用了相同的上下文。也许是不同的原因导致了这种行为,或者是我把事情搞砸了。过了一段时间,我真的很沮丧,想把工作做完。如果我有时间,也许我会做一些测试。很高兴看到有人读了这一切:)
public Actor AddOrUpdate(Actor entity)
{
Actor cur = context.Actors.Where(l => l.Name == entity.Name && l.Last_Name == entity.Last_Name).FirstOrDefault();
if (cur == null)
{
context.Actors.AddObject(entity);
return entity;
}
else
{
if (!entity.Mail.IsNullOrEmptyOrWhitespace() && cur.Mail != entity.Mail)
cur.Mail = entity.Mail;
//there are more of these...
return cur;
}
}
FirstEntityType first = new FirstEntityType();
first.Id = 2;
List<SecondType> list = CreateList(); //Let's say this returns a List with 10 elements
context.FirstEntityType.AddObject(first);
for (int i = 0; i < list.Count; i++)
{
list[i].First = first;
}
//just for arguments sake a second for
for (int i = 0; i < list.Count; i++)
{
context.SecondType.AddObject(list);
}
context.SaveChanges();