为什么生成的 EF 6.4 SQL 有问题?
Why is the EF 6.4 generated SQL faulty?
我有一个看起来像这样的查询。
UserId 是随机字母串。
searchCritera 是要搜索的模型。
searchCriteria.MainRoleValueList 包含搜索的角色(枚举)
var criteria = DBContext.People.Include(w => w.Main).AsQueryable();
//A lot of code that doesnt affect this senario.
if (!string.IsNullOrEmpty(searchCriteria.UserIdLike))
{
criteria = criteria.Where(i => i.UserId.Contains(searchCriteria.UserIdLike));
}
if (searchCriteria.MainRoleValueList != null && searchCriteria.MainRoleValueList.Count > 0)
{
var MainMembership = DBContext.MainMemberships.Where(p => searchCriteria.MainRoleValueList.Contains(p.MainRoleValue) && p.ValidTo == null).Join(criteria,
main => new { main.UserId, main.Main_Id }, current => new { current.UserId, current.Main_Id }, (main, current) => main);
var tmp = MainMembership.ToList(); //Added line to trigger communication with SQL server
}
生成的sql代码为
SELECT
[Extent1].[Id] AS [Id],
[Extent1].[UserId] AS [UserId],
[Extent1].[Main_Id] AS [Main_Id],
[Extent1].[MainRoleValue] AS [MainRoleValue],
[Extent1].[ValidFrom] AS [ValidFrom],
[Extent1].[ValidTo] AS [ValidTo]
FROM [dbo].[MainRoleMembership] AS [Extent1]
INNER JOIN [dbo].[Person] AS [Extent2] ON ([Extent1].[UserId] = [Extent2].[UserId]) AND ([Extent1].[Main_Id] = [Extent2].[Main_Id])
WHERE ([Extent1].[MainRoleValue] IN (300, 400, 200, 410)) AND ([Extent1].[ValidTo] IS NULL) AND (([Extent2].[FullName] LIKE '%rty12tt%' ESCAPE N'~')
OR ([Extent2].[UserId] LIKE '%rty12tt%' ESCAPE N'~')) AND
( EXISTS (SELECT
1 AS [C1]
FROM ( SELECT 1 AS X ) AS [SingleRowTable1]
WHERE 1 = 0
))
除了最后一部分,它还有效
EXISTS (SELECT
1 AS [C1]
FROM ( SELECT 1 AS X ) AS [SingleRowTable1]
WHERE 1 = 0
为什么要添加这个?因为它删除了我想要的正确结果。
如果我删除那部分和 运行 SQL 服务器上的查询,我就会得到我想要的用户。
我应该如何重写我的查询以便不包括在内?
已添加:是的,具有 UserId 的两个表没有外键
用户身份。这是系统中的一个糟糕设计,但我暂时无法修复。
已添加:在表之间为 UserId 添加了一个外键,但没有帮助
我添加了一个空列表并进行了比较..这就是为什么
EXISTS (SELECT
1 AS [C1]
FROM ( SELECT 1 AS X ) AS [SingleRowTable1]
WHERE 1 = 0
已添加。为列表添加了计数检查,问题消失了
我有一个看起来像这样的查询。 UserId 是随机字母串。 searchCritera 是要搜索的模型。 searchCriteria.MainRoleValueList 包含搜索的角色(枚举)
var criteria = DBContext.People.Include(w => w.Main).AsQueryable();
//A lot of code that doesnt affect this senario.
if (!string.IsNullOrEmpty(searchCriteria.UserIdLike))
{
criteria = criteria.Where(i => i.UserId.Contains(searchCriteria.UserIdLike));
}
if (searchCriteria.MainRoleValueList != null && searchCriteria.MainRoleValueList.Count > 0)
{
var MainMembership = DBContext.MainMemberships.Where(p => searchCriteria.MainRoleValueList.Contains(p.MainRoleValue) && p.ValidTo == null).Join(criteria,
main => new { main.UserId, main.Main_Id }, current => new { current.UserId, current.Main_Id }, (main, current) => main);
var tmp = MainMembership.ToList(); //Added line to trigger communication with SQL server
}
生成的sql代码为
SELECT
[Extent1].[Id] AS [Id],
[Extent1].[UserId] AS [UserId],
[Extent1].[Main_Id] AS [Main_Id],
[Extent1].[MainRoleValue] AS [MainRoleValue],
[Extent1].[ValidFrom] AS [ValidFrom],
[Extent1].[ValidTo] AS [ValidTo]
FROM [dbo].[MainRoleMembership] AS [Extent1]
INNER JOIN [dbo].[Person] AS [Extent2] ON ([Extent1].[UserId] = [Extent2].[UserId]) AND ([Extent1].[Main_Id] = [Extent2].[Main_Id])
WHERE ([Extent1].[MainRoleValue] IN (300, 400, 200, 410)) AND ([Extent1].[ValidTo] IS NULL) AND (([Extent2].[FullName] LIKE '%rty12tt%' ESCAPE N'~')
OR ([Extent2].[UserId] LIKE '%rty12tt%' ESCAPE N'~')) AND
( EXISTS (SELECT
1 AS [C1]
FROM ( SELECT 1 AS X ) AS [SingleRowTable1]
WHERE 1 = 0
))
除了最后一部分,它还有效
EXISTS (SELECT
1 AS [C1]
FROM ( SELECT 1 AS X ) AS [SingleRowTable1]
WHERE 1 = 0
为什么要添加这个?因为它删除了我想要的正确结果。 如果我删除那部分和 运行 SQL 服务器上的查询,我就会得到我想要的用户。 我应该如何重写我的查询以便不包括在内?
已添加:是的,具有 UserId 的两个表没有外键 用户身份。这是系统中的一个糟糕设计,但我暂时无法修复。
已添加:在表之间为 UserId 添加了一个外键,但没有帮助
我添加了一个空列表并进行了比较..这就是为什么
EXISTS (SELECT
1 AS [C1]
FROM ( SELECT 1 AS X ) AS [SingleRowTable1]
WHERE 1 = 0
已添加。为列表添加了计数检查,问题消失了