用于在SQL Server中查询JSON字符串的实体框架

本文关键字:字符串 实体 框架 JSON 查询 SQL Server 用于 | 更新日期: 2023-09-27 18:20:57

我正在寻找那些在使用实体框架查询JSON字符串方面做过任何事情的人。

我应该介绍一下我想在这里做什么的背景。我使用的数据库用于我正在开发的工作流引擎。它处理所有的工作流数据,还允许您将一些自定义数据存储为JSON字符串。我使用的工作流引擎根据每个请求处理JSON字符串的序列化和反序列化,但如果我想根据JSON字符串中的值进行查询和筛选,我必须将整个表拉入内存,反序列化所有条目,然后进行筛选。出于显而易见的原因,这是不可接受的。这样做的原因是,我们想要一个可以用于所有使用此工作流引擎的应用程序的单一工作流数据库,并且我们正在努力避免必须进行跨数据库视图来分离特定于应用程序的数据库以获得自定义数据。因为在大多数情况下,存储为JSON字符串的自定义请求数据相对简单,而且在大多数情况中,查询时不需要,这是设计的。但是,如果我们确实需要进行自定义搜索,我们需要一种能够解析这些自定义JSON对象的方法。我希望这可以用Entity动态地完成,这样我就不必编写额外的存储proc来查询特定类型的对象。理想情况下,我只需要一个使用实体来允许查询任何JSON数据结构的库。

我从一个数据库函数开始,该函数解析JSON并返回一个包含值(父对象id、名称、值和类型)的扁平表。然后将该函数导入到我的实体模型中。这是我获取代码的链接。很有趣的文章。

在SQL Server 中使用JSON字符串

以下是我的基本情况。

using (var db = new WorkflowEntities()) {
    var objects = db.Requests.RequestData();
}

在上面的代码示例中,Request对象是我的基本工作流Request对象。RequestData()是类型的扩展方法

DbSet<Request>

parseJSON是我的数据库函数的名称。

我的计划是编写一系列扩展方法,过滤Queryables

IQueryable<parseJSON_result>

举个例子,如果我有一个像这样的物体。

RequestDetail : {
    RequestNumber: '123',
    RequestType: 1,
    CustomerId: 1
}

我可以做一些类似的事情

db.Request.RequestData().Where("RequestType", 1);

或者类似的东西。Where方法将Take RequestData(),这是一个包含解析的JSON的IQueryable,它将过滤并返回新的IQueriable结果。

所以我的问题是,有人做过这样的事吗?如果是,你采取了什么样的方法?我的初衷是做一些字典式的事情,但似乎太难了。任何想法、想法、建议、智慧都将不胜感激。我做了一段时间,我觉得我真的没有走那么远。这主要是因为我无法决定语法的外观,也不确定是否应该在数据库端做更多的工作。

这是我最初的语法想法,但如果不对对象进行水合,我就无法运行[]运算符。

db.Request.Where(req => req.RequestData()["RequestType"] == 1).Select(req => req.RequestData()["CustomerInfo"]);

我知道这是一篇很长的帖子,所以如果你读到这里,谢谢你花时间阅读整篇文章。

用于在SQL Server中查询JSON字符串的实体框架

从SQL Server 2016开始,存在FOR JSON和OPENJSON,相当于FOR XML和OPENXML。您可以对引用存储在NVARCHAR列中的JSON的表达式进行索引。

这是一个非常晚的答案,但对于任何仍在搜索的人来说。。。

正如@Emyr所说,SQL 2016支持使用JSON_VALUE或OPENJSON语句在JSON列中进行查询。

Entity Framework仍然不直接支持这一点,但您可以使用SqlQuery方法直接对数据库运行原始SQL命令,该数据库可以在JSON列中进行查询,并保存对每一行的查询和反序列化,以便运行简单的查询。

您可以创建一个CLR SQL Server用户定义函数,然后从查询中使用它。

查看此链接https://msdn.microsoft.com/en-us/library/ms131077.aspx

我认为表值函数更适合您的情况。