where子句中的动态linq反斜杠

时间:2018-09-25 14:25:57

标签: c# linq escaping system.linq.dynamic

我使用System.Linq.Dynamic来查询带有动态“ where”表达式的实体。我正在查询具有字符串类型的属性“ newValue”的对象。示例性值将是:“ {\” ProcessId \“:764,\” ProcessLength \“:1000}”。 我不能使用==,因为无论字符串的其余部分如何,我都希望找到该属性包含“ ProcessId:764”的所有匹配。事实是,该存储的字符串包含转义符“ \”和双引号,但我无法弄清楚它到底应该是什么。

dbContext.Processes.Where("@newValue.Contains(\"ProcessId\":764\")")带来了错误,但是dbContext.Processes.Where("@newValue.Contains(\":764\")")可以正常工作。我想我的查询中肯定有反斜杠或双引号,但我自己无法解决。.

2 个答案:

答案 0 :(得分:0)

这里有两件事要注意:

  1. 如果您在编译时知道应查询的列(即newValue),只需使用标准的Linq:var list = items.Where(i => i.NewValue.Contains("904")).ToList()

  2. 如果您想使用动态Linq,通常需要在某列上应用Where,例如Where("SomeColumn.Contains("something")")Where("SomeColumn.Contains(@0)", new string[] {"something"})

    因此,在您的情况下,这应该可行:items.Where("newValue.Contains(\"904\")")

    执行Where("@newValue.Contains("something")")并没有什么意义,因为@newValue会被解析为字符串文字。另请参阅类似的问题comment

这是一个简单的例子:

public static void Main(string[] args)
{
    var items = new [] 
    { 
       new { Id = "1", Title = "ProcessId: 123"}, 
       new { Id = "4", Title = "ProcessId: 456"}, 
       new { Id = "7", Title = "ProcessId: 789"}, 
    }.ToList();

    // returns null, because the string "Title" doesn't contain the string "7"
    var res1 = items.Where("@0.Contains(\"7\")", new string[] {"Title"}).FirstOrDefault();     

    // works - returns the 3rd element of the array
    var res2a = items.Where("Title.Contains(@0)", new string[] {"ProcessId: 789"}).FirstOrDefault();                 
    var res2b = items.Where("Title.Contains(\"ProcessId: 789\")").FirstOrDefault();
}

答案 1 :(得分:0)

@HeyJude感谢您的努力,但仍然无法正常工作。它以某种方式变得错误,现在我什至无法获取仅给出ProcessId号的正确行。

让我为您提供有关我的设置的详细说明。在数据库中有一个带有“ NewValue”列的表,我使用此列存储某些对象的当前(在表中创建行时)表示形式的json字符串。对象 Process 。因此,该列存储例如 {“ ProcessId”:904,“ ProcessLength”:1000} 的字符串。为了从db中获取此数据,我创建了表记录的集合:var items = (from l in db.JDE_Logs join u in db.JDE_Users on l.UserId equals u.UserId join t in db.JDE_Tenants on l.TenantId equals t.TenantId where l.TenantId == tenants.FirstOrDefault().TenantId && l.Timestamp >= dFrom && l.Timestamp <= dTo orderby l.Timestamp descending select new //ExtLog { LogId = l.LogId, TimeStamp = l.Timestamp, TenantId = t.TenantId, TenantName = t.TenantName, UserId = l.UserId, UserName = u.Name + " " + u.Surname, Description = l.Description, OldValue = l.OldValue, NewValue = l.NewValue });。然后我查询它以找到给定ProcessId号的匹配行,例如query = "@NewValue.Contains(\"904,)\")"; items = items.Where(query); 这应该取回所有记录,其中NewValue列包含查询字符串,但这不起作用。它编译并“工作”,但没有数据被提取或仅提取那些后来出现在字符串904中的记录。听起来很蠢,但这就是事实。

要获取包含"ProcessId":904的所有记录,查询字符串应该是什么样?