Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/entity-framework/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 已将ObjectContext更新为实体框架6。与导航属性的工作方式太不同_C#_Entity Framework - Fatal编程技术网

C# 已将ObjectContext更新为实体框架6。与导航属性的工作方式太不同

C# 已将ObjectContext更新为实体框架6。与导航属性的工作方式太不同,c#,entity-framework,C#,Entity Framework,我使用的是.EDMX文件版本2,使用的是遗留ObjectContext 我更新了代码策略T4,并更新了实体框架6.2的参考和配置文件 我使用LazyLoadingEnabled=true(升级前后) 旧对象上下文: ret = new PropertySet { display_name = DisplayName, id_product = IdProduct // this is a foreign key to the entity Product }; context.P

我使用的是.EDMX文件版本2,使用的是遗留ObjectContext

我更新了代码策略T4,并更新了实体框架6.2的参考和配置文件

我使用LazyLoadingEnabled=true(升级前后)

旧对象上下文:

ret = new PropertySet {
    display_name = DisplayName,
    id_product = IdProduct // this is a foreign key to the entity Product
};
context.PropertySets.Add(ret);
context.SaveChanges();
// calling ret.Product returns the product object with all properties filled.
新数据库上下文:

ret = new PropertySet {
    display_name = DisplayName,
    id_product = IdProduct // this is a foreign key to the entity Product
};
context.PropertySets.Add(ret);
context.SaveChanges();
// calling ret.Product returns null. (HERE IS THE PROBLEM)
// calling context.Entry(ret).Product.Load() loads the correct Product.
我担心这种“新”行为,因为它会破坏现有代码,并导致运行时错误。这是一个大的应用程序,我们没有针对EF的测试

我想知道是不是有什么选择或者什么错误,或者这只是一种新的做事方式?我错过什么了吗


谢谢,我真的很感激任何线索,我整天都在四处寻找,因为由于这种不同的行为,应用程序中引入了很多bug。

您不仅升级了,还从ObjectContext更改为DbContext。这也意味着从更改为DbSet。它们的行为不同,因为DbContext旨在简化事情

问题在于ObjectContext默认使用自跟踪实体(STE),这些实体已被弃用,并且在EF6中不再得到官方支持(但是,您可以从EF5下载STE模板,并尝试将其适应EF6)

另外,您的属性名称违反了标准的EF命名约定,这意味着您无法从约定中获得比配置更多的好处。也就是说,你被迫配置一些你不应该配置的东西

如果这是你唯一的问题,那么有一些解决办法。。如果不是,您可能想投资尝试将EF5 t4模板用于STE

这里有一篇关于使用STE的文章

对于解决方法,您可以像前面一样添加Reload()方法,也可以像下面这样创建代理实体:

ret = context.PropertySets.Create();  // creates proxied entity
ret.display_name = DisplayName;
ret.id_product = IdProduct // this is a foreign key to the entity Product

context.PropertySets.Add(ret);
context.SaveChanges();

var name = ret.Product.Name; // should now work.

无论哪种方式,如果您想使用EF6,都必须对代码进行更改。问题是,你想在哪里做这件事?

是的,这是我唯一的问题。即使我没有使用EF命名约定(MySQL数据库),我也会首先使用带有外键的数据库,并使用EF6DBContext生成器为我完成所有代码。你认为我能进入一些其他的“问题”吗?现在尝试代理。是的,执行context.PropertySets.Create()确实有效。我发现我必须使用context.PropertySets.Add()将其添加到上下文中。这究竟创建了什么()?如果我不知道属性是否存在,我可以使用Create()然后使用ret=context.PropertySets.Find(),如果为null,则填充值吗?DbContext中的工作流如何?我非常熟悉ObjectContext,这对我的代码来说是“破坏性的”:(@Bart-EF通过名为
ObjectStateManager
的东西跟踪实体中的更改,默认情况下,它将实体包装在“代理”中类,该类检测何时进行更改。当您使用
new
创建对象时,ObjectStateManager对此类一无所知,因为它尚未包装在代理中。当您使用create时,它会创建一个实体并将其包装在更改跟踪代理中。延迟加载虚拟方法时会使用此代理还有收藏。@Bart-我不知道你说的“不知道”是什么意思如果该属性存在,是否意味着您不知道该行是否存在?如果使用Find,则不需要使用Create,因为Find已返回代理属性集,它应该已连接。如果您在Find后填写ID,然后调用SaveChanges,则EF将使用新ID\u产品保存修改后的记录。@Bart-Create c创建一个新实例,这样将导致递归循环,从而导致堆栈溢出。每个新实例将调用构造函数,该构造函数将调用create,该构造函数将调用构造函数…等等。。