为什么我的导航属性在Entity Framework 4中为空?

问题描述:

代码:为什么我的导航属性在Entity Framework 4中为空?

public ChatMessage[] GetAllMessages(int chatRoomId) 
{ 
    using (ChatModelContainer context = new ChatModelContainer(CS)) 
    { 
    //var temp = context.ChatMessages.ToArray(); 
    ChatRoom cr = context.ChatRooms.FirstOrDefault(c => c.Id == chatRoomId); 
    if (cr == null) return null; 
    return cr.ChatMessages.ToArray(); 
    } 
} 

问题:

的方法(WCF服务的一部分)返回一个空数组。如果我取消对注释行的注释,它会按预期开始工作。我试过转动懒加载,但它没有帮助。

此外,当它工作时,我得到ChatMessages与ChatRoom填充引用,但不是ChatParticipant。它们都由具有Id和导航属性的架构中的ChatMessage实体引用。已设置ID并指向正确的实体,但在客户端只有ChatRoom参考已填充。

相关的问题:

  1. 是一个数组返回EF-实体集合这样的首选方法?
  2. 在我的模型(edmx)中进行更改时,在运行context.CreateDatabase()之前,需要运行“从模型生成数据库...”选项。为什么?我收到了一些指向旧SSDL的错误消息,但我无法找到SSDL的存储位置。这是当我运行这个“生成数据库...” - 选项创建的?
  3. 将整个实体图返回给客户端是否安全?我已阅读了一些关于“循环参考豁免”的内容,但这是EF4中修复的吗?
  4. 如何以及何时在EF4中填入参考?如果我打开懒惰加载,我怀疑只有我触摸的实体被填充?但是在关闭延迟加载的情况下,应该始终填充整个图表吗?
  5. 在EF4中使用自更新实体而不是普通实体有什么缺点?我现在不需要自我更新,但我可能会稍后再做。我可以轻松升级,还是应该从一开始就自行更新?
  6. 为什么不能使用带有字符串类型的实体键?
+0

我猜每个“相关问题“足以成为一个单独的问题。 – 2010-10-10 17:40:43

+0

您使用POCO或EntityObjects吗? – 2010-10-10 17:42:11

+0

即时通讯使用自我更新的实体对象 – 2010-10-10 20:01:38

您的每个问题都需要一个单独的答案,但我会尽可能简短地回答它们。

首先,在您提供的代码示例中,您将获得一个ChatRoom对象,然后尝试访问未包含在您的查询(ChatMessages)中的相关对象。如果延迟加载截止时,你所建议的,那么你将需要包括在你的查询(“ChatMessages”)调用,所以你的LINQ查询应该是这样的:

ChatRoom cr = context.ChatRooms.Include("ChatMessages").FirstOrDefault(c => c.Id == chatRoomId);

请确保您连接字符串也在你的配置文件中。

对于相关的问题:

  1. 您可以在任何你选择的方式返回集合的 - 我还通常做他们在一个List对象(我认为这是常用的方法),但你可以使用数组如果你想。要以列表形式返回,请在查询中使用.ToList()方法调用。

  2. 我不明白你要在这里做什么,你是使用代码从你的EDMX文件或其他东西创建数据库?我通常使用数据库优先的方法,所以我创建我的表等,然后从数据库更新我的EDMX。即使您从模型生成数据库,也不必在代码中运行CreateDatabase,您应该能够针对数据库运行生成的脚本。如果您只使用代码,那么您需要转储EDMX文件。

  3. 您通常可以将实体图返回给客户端,应该处理好。

  4. EF4应该只填充你需要的东西。如果使用延迟加载,当您引用它们并执行查询(例如执行ToList()操作)时,它会自动加载您不包含在LINQ查询中的内容。如果你的客户端在物理边界(例如服务边界)显然是这样,那么这将不会很好。如果你不使用延迟加载,它会加载你在查询中告诉它的内容,这就是全部。

  5. 自我跟踪实体用于n层应用程序,其中对象必须通过物理边界(例如服务)传递。它们为每个对象生成代码的开销以跟踪其变化,还生成不依赖于EF4的POCO对象(但显然包含将使跟踪的更改与EF4跟踪器一起工作的生成代码)。我认为这取决于你的使用情况,如果你正在构建一个非常独立的小应用程序,并且不关心没有基础设施的可测试性分离,那么你就不需要使用自我跟踪实体。我只说当你需要它们时使用框架功能,所以如果你不写一个企业级的应用程序(企业不一定要很大,但是可扩展性,高度可测试性,高质量等),那么不需要为自己跟踪POCO。

  6. 我还没有尝试过,但你应该能够做到这一点 - 这将是一个单独的问题的候选人,如果你不能得到它的工作:)

+0

谢谢!我不知道Include() - 方法。它解决了我的问题。关于你的其他答案:1.很好 - 2.我使用模型优先方法(EDMX),我想在应用程序安装时从代码创建数据库,所以我需要使用CreateDatabase,除非我想以其他方式执行DDL ,但它不会工作,除非我首先运行“Generate Database DDL”,这似乎有点奇怪,因为我认为这是CreateDatabase方法所做的。 - 3. Ok - 4.我看到 - 5.我认为不管怎么样,POCO都会去,他们似乎更好 - 6.我得到了这个工作,不知道以前有什么不对。 – 2010-10-11 20:24:24