我有一个使用Entity Framework查询数据库的方法,并返回EF对象(ApplicationUser)。如果我有一个ApplicationUser的构造函数试图使用此方法来填充其属性,那么该对象的复杂属性是否会在设置时触发数据库的调用?在原始对象中它们是代理,因此会延迟加载,但只是将这些属性设置为同一对象的新实例的属性调用数据库?
这是一个简单的例子:
public class ApplicationUser
{
public ApplicationUser(int userId)
{
ApplicationUser user = ApplicationUser.Select(userId);
this.FirstName = user.FirstName //this is fine
this.ApplicationRole = user.ApplicationRole //This is a complex object. Is it still going to be lazily loaded and called only if this.ApplicationRole is referenced?
}
public static ApplicationUser Select(int userId)
{
//this uses EF to return an Application User object
}
}
答案 0 :(得分:2)
将在此行中调用数据库:
$( ".list-group-item[data-text='Banana'] .badge" ).text(); //50
然后,您的对象将被提取,不再延迟加载。
要确保这种情况发生,您必须进行一些配置:
必须启用延迟加载和代理创建:
this.ApplicationRole = user.ApplicationRole;
导航属性必须声明为public Context()
: base("YourConnectionString")
{
Configuration.LazyLoadingEnabled = true;
Configuration.ProxyCreationEnabled = true;
}
:
virutal
行动中的示例
假设你有这些课程
public class ApplicationUser
{
//...
public virtual ApplicationRole ApplicationRole { get; set; }
//...
}
第一击:
public class ApplicationUser
{
public int ApplicationUserId { get; set; }
public string FirstName { get; set; }
public virtual ApplicationRole ApplicationRole { get; set; }
public static Context db { get; set; }
public ApplicationUser()
{
}
public ApplicationUser(int userId)
{
ApplicationUser user = ApplicationUser.Select(userId);
this.FirstName = user.FirstName;
this.ApplicationRole = user.ApplicationRole; //database will be hit here
}
public static ApplicationUser Select(int userId)
{
//this uses EF to return an Application User object
return db.Users.Find(userId);
}
}
public class ApplicationRole
{
public int ApplicationRoleId { get; set;}
public string Name { get; set; }
}
生成的SQL:
return db.Users.Find(userId);
Second Hit
SELECT
[Limit1].[ApplicationUserId] AS [ApplicationUserId],
[Limit1].[FirstName] AS [FirstName],
[Limit1].[ApplicationRole_ApplicationRoleId] AS [ApplicationRole_Application
RoleId]
FROM ( SELECT TOP (2)
[Extent1].[ApplicationUserId] AS [ApplicationUserId],
[Extent1].[FirstName] AS [FirstName],
[Extent1].[ApplicationRole_ApplicationRoleId] AS [ApplicationRole_Applic
ationRoleId]
FROM [dbo].[ApplicationUsers] AS [Extent1]
WHERE [Extent1].[ApplicationUserId] = @p0
) AS [Limit1]
-- p0: '1' (Type = Int32)
生成SQL
this.ApplicationRole = user.ApplicationRole
如果SELECT
[Extent2].[ApplicationRoleId] AS [ApplicationRoleId],
[Extent2].[Name] AS [Name]
FROM [dbo].[ApplicationUsers] AS [Extent1]
INNER JOIN [dbo].[ApplicationRoles] AS [Extent2] ON [Extent1].[ApplicationRo
le_ApplicationRoleId] = [Extent2].[ApplicationRoleId]
WHERE ([Extent1].[ApplicationRole_ApplicationRoleId] IS NOT NULL) AND ([Exte
nt1].[ApplicationUserId] = @EntityKeyValue1)
-- EntityKeyValue1: '1' (Type = Int32, IsNullable = false)
对象具有其他导航属性,它们仍然会延迟加载,没有问题。
这里有一个可能有用的提示。要查看EF何时访问数据库,请创建一个控制台应用程序,添加解决方案的引用,然后使用ApplicationRole
。要查看有关日志记录的更多信息,请查看此链接https://msdn.microsoft.com/en-us/data/dn469464.aspx